CHAPTER 02
2. descriptor format과 buffer lifetime을 word 단위로 읽는다
normal, enhanced, extended descriptor와 GMAC4 descriptor를 구분하고 각 word의 buffer address, length, status, context와 ownership을 driver가 채우는 시점대로 추적합니다.
descriptor memory
ring은 보통 coherent DMA memory이지만 packet buffer는 streaming mapping일 수 있습니다. 두 memory의 cache 계약이 다릅니다.
OWN
CPU가 모든 field와 buffer를 준비한 뒤 마지막으로 device ownership을 넘깁니다. 회수 후에는 status를 읽고 buffer를 unmap/recycle합니다.
context descriptor
TSO, timestamp, VLAN 같은 metadata가 별도 context descriptor를 사용할 수 있습니다. data descriptor 수와 packet 수가 같지 않을 수 있습니다.
wrap
ring index wrap과 hardware tail pointer 단위가 descriptor 개수인지 주소인지 확인합니다.
레지스터와 관측값을 함께 읽는 표
| 항목 | 소유 블록 | 설정 또는 의미 | 정상 증거 | 실패 해석 |
|---|---|---|---|---|
| DES0 status/OWN | descriptor | device/CPU 소유와 completion status | handoff 후 1, completion 후 0 | stuck OWN은 DMA/channel/address 확인 |
| DES1 control/length | descriptor | buffer length, interrupt, first/last | skb fragment 구성과 일치 | length/segment 경계 오류 |
| DES2/3 address | descriptor | buffer 또는 next descriptor 주소 | dma_map 결과와 정확히 일치 | CPU VA 또는 truncated IOVA |
| extended/context words | descriptor | timestamp/offload metadata | feature가 켜진 packet에만 유효 | format 선택과 capability 불일치 |
| ring base/length | DMA channel | descriptor DMA base와 개수 | allocation과 alignment 일치 | base high bits/length off-by-one |
| head/tail/current | DMA channel | hardware 진행 위치 | software producer/consumer 사이 | wrap 단위 또는 stale read |
증상에서 첫 실패 경계를 찾는 표
| 관측 증상 | 직전 통과 증거 | 우선 확인 | 반증 시험 | 판정 |
|---|---|---|---|---|
| 첫 descriptor부터 OWN 고정 | channel run bit set | ring base와 bus access | DMA address/IOMMU fault 확인 | descriptor fetch 경계 |
| 몇 바퀴 뒤 멈춤 | 초기 packet 성공 | wrap/length/tail 계산 | 작은 ring으로 index trace | ring 경계조건 |
| 큰 packet만 깨짐 | single descriptor 정상 | first/last와 fragment length | linearize 후 비교 | multi-descriptor 조립 |
| timestamp/offload에서만 실패 | normal descriptor 정상 | context/extended format | feature를 끄고 descriptor diff | format 전환 경계 |
| DMA 주소 상위 bit 유실 | 저주소 정상 | address width와 DES high field | IOMMU로 32-bit IOVA 강제 | 주소 폭 |
| 회수 후 use-after-free | hardware completion 보임 | unmap/recycle/refcount 순서 | KASAN과 descriptor index trace | buffer lifetime |
실제 검증 절차
| 순서 | 실행 | 남길 증거 | 판정 목적 |
|---|---|---|---|
| 1 | 선택된 descriptor ops와 descriptor 크기를 boot log에 남깁니다. | format/size/capability | 해석표 고정 |
| 2 | packet 하나를 전송하며 handoff 전후 raw word를 dump합니다. | word별 변화 | OWN과 field 순서 확인 |
| 3 | ring base와 각 buffer DMA address를 IOMMU mapping과 대조합니다. | IOVA/PA ledger | 주소 변환 검증 |
| 4 | ring wrap 직전/직후 index와 descriptor를 capture합니다. | producer/consumer/tail | off-by-one 검출 |
주의device ownership인 descriptor를 CPU가 수정하면 안 됩니다. debug dump도 cache sync와 ownership 규칙을 지켜야 합니다.
공개적으로 다시 확인할 수 있는 자료
공개되지 않은 vendor register나 integration별 offset을 추측해서 채우지 않았습니다. 아래 제조사 자료, architecture 문서와 Linux v6.18.37 원본에서 다시 확인할 수 있는 범위만 사용했습니다.
Linux stmmac driver
Synopsys GMAC/GMAC4/XGMAC, descriptor, NAPI, PTP와 offload 공개 설명
Linux NAPI
schedule, poll budget, completion과 IRQ 재활성화 계약
Linux v6.18.37 stmmac_main.c
open, xmit, RX, ISR와 NAPI poll 원본
Linux v6.18.37 dwmac4_dma.c
DMA channel, ring length, tail pointer와 interrupt enable
Linux v6.18.37 net/core/dev.c
NAPI core, NET_RX_SOFTIRQ와 receive stack 진입
Linux DMA API HOWTO
descriptor와 packet buffer의 CPU/device ownership, mapping과 barrier