09. CWRU 베어링 결함 감지 NPU — 실리콘 검증
08. kws_silicon의 L3 패턴 (전체 그래프 단일 IP)을 더 깊은 그래프 + 다른 도메인으로 옮긴 사례입니다. 음성 인식 → 산업용 회전 기계 상태 감시 (CBM). 같은 보드, 같은 툴체인, 다른 모델.
어떤 모델
examples/silicon_bearing/ — CWRU 베어링 데이터 센터 진동 기록 기반
4-class 1D CNN 결함 분류기.
입력 : FFT[128] INT8 (12 kHz 가속도계 → 512-pt FFT → 128 주파수 빈)
분류 : normal / inner_race / ball / outer_race
구조 : Conv1D × 3 → MaxPool × 2 → GAP → fc1 → fc2
학습 : RTX 3090, 30 epoch, val 99.62% / test 99.00%
가중치 : INT8 양자화, 60.5 KB 헤더
방산·조선·중공업에서 회전 기계 상태 감시에 실제로 쓰이는 표준 데이터셋.
silicon 결과 한 줄
40/40 CPU↔NPU 일치, NPU 11.13× 가속, 200-window 스트림 모니터에서 false alarm 0, fault detect 150/150.
| CPU | NPU | |
|---|---|---|
| inference cycles | 29.4 M cyc | 2.65 M cyc |
| inference wall (@ 666 MHz) | 44 ms | 4.0 ms |
| 가속비 | 1× | 11.13× |
P06 (KWS) 의 8.07× 보다 큽니다 — 그래프가 더 깊어 (Conv1D × 3) ARM 기준값이 더 무겁기 때문입니다.
L3 패턴 — 같은 IP 구조
P06과 동일한 단일-IP, ARM-input-only 패턴:
ARM (PS, 666 MHz)
├── FFT 입력 준비
├── ap_start 1회
├── ap_done 폴링
└── softmax + argmax
NPU (PL, 90 MHz) — bearing_npu_top
├── Conv1D × 3
├── MaxPool × 2
├── GAP
├── fc1 + ReLU
├── fc2
└── INT8 가중치 ROM (on-chip BRAM)
ap_start 한 번에 추론 한 번 — Apple ANE / Edge-TPU 패턴.
리소스 한계 — II=64 fix
첫 합성에서 II=4 로 시도했더니:
| 자원 | 1차 시도 (II=4) | XC7Z020 한계 |
|---|---|---|
| DSP | 231 % | 220 |
| LUT | 265 % | 53 K |
→ 보드 초과. ALLOCATION operation instances=fmul=4 fadd=4 pragma로 float
MAC 유닛을 4개로 제한 + II=64로 재합성:
| 자원 | 2차 시도 (II=64 + ALLOC limit=4) |
|---|---|
| Fmax | 114 MHz (90 MHz로 운용) |
| DSP | 189 (86 %) |
| BRAM | 12 % |
| LUT | < 50 % |
레이턴시는 늘었지만 CWRU 4-class 분리가 충분히 뚜렷해 정확도에는 영향 없음.
이게 소형 NPU 합성에서 빈번한 trade-off입니다: II 늘리고 ALLOC limit 걸어서 자원 안에 넣는 것. P06이 fit 했던 매개변수 (II=4)가 P07에는 안 맞을 수 있고, 그건 모델별로 다시 측정해야 합니다.
두 demo
demo1 — 정확도 게이트
4 클래스 × 10 샘플 = 40 inference. CPU와 NPU를 동시에 돌립니다.
idx truth pred(cpu) c_cpu cyc(cpu) pred(npu) c_npu cyc(npu) speedup
00 normal normal 0.999 29,439,352 normal 0.999 2,648,130 11.1×
10 inner_race inner_race 0.988 29,425,653 inner_race 0.988 2,647,073 11.1×
20 ball ball 0.998 29,427,387 ball 0.998 2,647,196 11.1×
30 outer_race outer_race 0.999 29,425,254 outer_race 0.999 2,647,133 11.1×
... (40 행)
CPU accuracy : 40/40 (100%)
NPU accuracy : 40/40 (100%)
CPU↔NPU agree : 40/40 (100%)
RESULT: PASS
demo2 — 200-window 스트리밍 모니터
50 normal → 50 inner_race → 50 ball → 50 outer_race 순서로 흘림.
conf ≥ 0.75 시 *** FAULT *** alert.
[frame 50] normal conf=0.999 cyc=2,646,863
[frame 51] inner_race conf=0.988 cyc=2,647,101 *** FAULT: inner_race ***
[frame 101] ball conf=0.998 cyc=2,647,071 *** FAULT: ball ***
[frame 151] outer_race conf=0.999 cyc=2,647,047 *** FAULT: outer_race ***
[frame 200] outer_race conf=0.999 cyc=2,647,087 *** FAULT: outer_race ***
Windows processed : 200
False alarms : 0 (50 정상 윈도우 전부 통과)
Fault alerts : 150 / 150
Avg cycles/window : 2,646,970
Total wall time : 4,884 ms
RESULT: PASS
정밀도 100%, 재현율 100%. 두 번 연속 실행 동일. 초당 252 추론 처리 가능.
재현 — P06과 동일한 한 줄
# 보드 just-reset 상태
bash examples/silicon_bearing/scripts/run_npu_test.sh
기대: 약 3분 후
demo1 : PASS (40/40)
demo2 : PASS (200/200, 0 false alarm)
솔직하게 — 두 가지
CWRU는 "쉬운 문제"
12 kHz / 0.007 inch 결함 크기 / 명확한 드라이브 엔드 가속도계 — 이 조건에서 4-class 분리는 AI가 아니어도 가능할 만큼 뚜렷합니다. 실제 산업 환경 (다양한 베어링 종류, 가변 RPM, 복합 결함)은 훨씬 어렵습니다.
이 데모의 목적은 툴체인 검증입니다. 어려운 문제보다 먼저, 같은 흐름으로 회로가 만들어지고 돌아간다는 걸 보여주는 것입니다.
100 MHz 에서 타이밍 실패
Vivado를 100 MHz로 처음 돌리면 WNS = -0.4 ns 로 타이밍 실패입니다. 클럭을 90 MHz로 낮춰 재실행하면 +0.071 ns 로 여유롭게 클로저됩니다. P06 KWS L3 검증에서도 같은 패턴이었습니다. XC7Z020의 float MAC 배치 특성이 100 MHz 에서 빡빡합니다.
자세한 자료
- examples/silicon_bearing/docs/tutorial.md — 전체 walk-through
- examples/silicon_bearing/docs/results/SUMMARY.md
- examples/silicon_bearing/docs/results/demo_combined_npu_silicon.mp4 — 35초 통합 데모 영상
다음 단계
10. llm_silicon_hybrid — P06/P07 의 L3 패턴을 의도적으로 떠나는 단계 (LLM은 가중치가 BRAM 안 들어감).