임베디드 벤치마킹 기초 — 재현성·Warmup·노이즈 제거
#한 줄 요약
벤치마크는 재현성이 있어야 합니다. Warmup, isolation, N=100+가 필수입니다. 한 번 측정은 거짓말입니다.
#좋은 벤치마크의 5 조건
- Reproducible — 같은 결과가 매번 나옵니다.
- Representative — 실 워크로드를 대표합니다.
- Stable — 변동이 ±5% 이내입니다.
- Isolated — 외부 영향이 제거됩니다.
- Measurable — 명확한 metric이 있습니다.
#Warmup — 첫 측정은 버린다
첫 측정: 150 ms (cache cold, branch predictor 미학습)2-10번째: 90-110 ms (warmup 중)11번째+: 100 ms ± 5% (정상)해결책은 처음 N회 측정을 무시하는 것입니다.
for (int i = 0; i < WARMUP; i++) work(); // discardfor (int i = 0; i < N; i++) { uint32_t t = DWT->CYCCNT; work(); record(DWT->CYCCNT - t);}WARMUP은 10에서 100 사이를 권장합니다.
#Isolation — 노이즈 제거
#Linux
# CPU pinningtaskset -c 3 ./benchmark
# Disable frequency scalingecho performance | sudo tee /sys/devices/system/cpu/cpu*/cpufreq/scaling_governor
# Isolate CPU (kernel boot)isolcpus=2,3 # CPU 2,3을 scheduler에서 제외
# Network·other interrupts offsudo systemctl stop irqbalance
# Disable ASLR (predictable)echo 0 | sudo tee /proc/sys/kernel/randomize_va_space#Bare-metal
- 다른 task를 disable합니다.
- ISR을 mask합니다 (
__disable_irq()for critical region). - DMA를 정지합니다.
- Cache를 enable하고 warm합니다.
#N=1은 거짓말
한 번 측정: 100 ms실은 95-110 ms 분포 (±5%)N은 100 이상이 필요합니다. 평균·p99·max·stdev를 모두 보고해야 합니다.
struct { uint32_t min, max, sum; uint32_t hist[64];} stats;#CoreMark — EEMBC 표준
비영리 EEMBC의 임베디드 표준 벤치마크입니다. 표준화된 integer workload여서 모든 칩을 비교할 수 있습니다.
# 빌드git clone https://github.com/eembc/coremarkcd coremarkmake PORT_DIR=linux64
# 실행./coremark.exe# CoreMark 1.0 : 13841 / GCC 11.4.0 -O2 ...#결과 비교
| CPU | CoreMark | CoreMark/MHz |
|---|---|---|
| Cortex-M0+ @ 50 MHz | 100 | 2.0 |
| Cortex-M4F @ 168 MHz | 850 | 5.1 |
| Cortex-M7 @ 480 MHz | 2900 | 6.0 |
| Cortex-A53 @ 1.5 GHz | 6300 | 4.2 |
| RISC-V SiFive E31 @ 320 MHz | 1500 | 4.7 |
| ESP32-C3 @ 160 MHz | 530 | 3.3 |
CoreMark/MHz는 아키텍처 효율을 나타냅니다. Cortex-M7이 가장 높습니다.
#Dhrystone (DMIPS) — 옛 표준
1984년 Reinhold Weicker가 만든 integer workload입니다.
Cortex-M0+: 0.95 DMIPS/MHzCortex-M4: 1.25 DMIPS/MHzCortex-A53: 2.30 DMIPS/MHz다만 컴파일러 최적화에 민감하고 실 워크로드 대표성이 약하다는 비판이 있습니다. 그래서 CoreMark가 더 신뢰받습니다.
#SPEC CPU — Server/Desktop 표준
SPECint와 SPECfp가 있습니다. 라이선스가 비싸고 임베디드에는 너무 무겁습니다.
#Linux Benchmarks
| 도구 | 측정 |
|---|---|
sysbench | CPU·memory·thread·mutex |
iperf3 | network bandwidth |
UnixBench | 종합 |
fio | disk I/O |
stress-ng | 부하 발생 |
phoronix-test-suite | 자동 multi-bench |
#Micro-Benchmark 작성
#include "benchmark.h"
void bench_memcpy_1k(void) { static uint8_t src[1024], dst[1024]; memcpy(dst, src, sizeof(src));}
BENCHMARK(bench_memcpy_1k);BENCHMARK_MAIN();Google Benchmark나 Catch2를 활용합니다.
#Compiler가 최적화로 지워버리는 것 방지
volatile int sink;sink = result; // optimizer가 result 계산 제거 못 함
// 또는 __asm__ memory barrier__asm__ volatile("" : : "r"(result) : "memory");#임베디드 벤치 패턴
void run_bench(const char *name, void (*fn)(void)) { // Warmup for (int i = 0; i < 10; i++) fn();
// Measure uint32_t min = UINT32_MAX, max = 0, sum = 0; for (int i = 0; i < 100; i++) { uint32_t t = DWT->CYCCNT; fn(); uint32_t e = DWT->CYCCNT - t; if (e < min) min = e; if (e > max) max = e; sum += e; } printf("%s: avg=%u min=%u max=%u\n", name, sum/100, min, max);}#Comparative Benchmark
A/B 비교는 같은 환경에서 다른 옵션을 비교하는 방식입니다.
Baseline: 100 ms ± 5Optimization A: 85 ms ± 4 (15% 개선)Optimization B: 90 ms ± 7 (10% but jitter↑)Statistical test가 필요합니다. Mann-Whitney U test로 차이가 유의미한가를 검증합니다.
#A/B Test Pitfall
같은 코드를 자신과 비교해도 ±5% 변동이 자연스럽게 발생합니다. 10% 미만 개선은 noise일 가능성이 있습니다.
#Continuous Benchmarking
# CI/CD에서 매 PR마다 자동 benchmark- name: Benchmark run: | ./benchmark > current.txt diff baseline.txt current.txt | check_regressionProduction code의 성능 회귀를 자동으로 감지합니다.
#자주 하는 실수
⚠️ N=1 또는 N=10
Stdev를 모르므로 결론을 내릴 수 없습니다. N ≥ 100이 필요합니다.
⚠️ Warmup 없이
Cache cold 상태라 부정확합니다. 10회 이상 warmup이 필요합니다.
⚠️ Different workload 비교
apples to oranges 비교가 됩니다. 같은 input과 환경을 써야 합니다.
⚠️ Compiler가 result를 최적화로 제거
앞에서 본 것처럼 volatile이나 asm barrier로 막아야 합니다.
#정리
- 벤치마크는 재현 + 대표 + 안정 + 격리 + 측정의 다섯 가지가 핵심입니다.
- Warmup 10-100회와 **measurement N=100+**가 필요합니다.
- CoreMark가 임베디드 표준입니다 (CoreMark/MHz로 효율을 봅니다).
- Linux는 CPU pinning, frequency lock, isolcpus를 함께 씁니다.
- A/B 비교에는 statistical test가 필요합니다. 10% 미만은 noise일 수 있습니다.
다음 편은 성능 모델링입니다. Amdahl과 Roofline을 다룹니다.
#관련 항목
Embedded Performance Engineering · 7 of 57
- 1Embedded Performance Engineering — 임베디드 성능 엔지니어링 시리즈 소개
- 2임베디드 성능 분석 방법론 — Measure → Analyze → Optimize 사이클
- 3성능 지표 정의 — Latency·Throughput·Utilization 분석
- 4성능 측정의 기본 — Wall-Clock·CPU Cycle·Instruction Count
- 5성능 데이터 통계적 분석 — Percentile·Histogram·평균의 함정
- 6실시간 성능 분석 — WCET·Jitter·Deadline Miss 측정
- 7임베디드 벤치마킹 기초 — 재현성·Warmup·노이즈 제거
- 8성능 모델링 — Amdahl·Gustafson·Roofline Model 적용
- 9프로파일링 기법 개요 — Sampling vs Instrumentation·PGO·LTO
- 10CPU 파이프라인 분석 — 5-stage·Cortex-M·Cortex-A 비교
- 11Pipeline Stall 분석 — Data·Structural·Control Hazard·Forwarding
- 12Branch Prediction 분석 — Static·2-bit·BTB·BHT·Mispredict 비용
- 13Speculative Execution 분석 — OoO·Reorder Buffer·Register Renaming
- 14CPU Cache 기초 — L1·L2·L3·Set Associative·Replacement Policy
- 15Cache Miss 3C Model 분석 — Compulsory·Capacity·Conflict
- 16Cache Line 최적화 — Alignment·Prefetch·False Sharing 처리
- 17메모리 대역폭 분석 — STREAM·Roofline·Bus Saturation 측정
- 18SIMD·NEON 활용 — 128-bit Vector·Auto-Vectorization·SVE/SVE2
- 19PMU·HPM 하드웨어 카운터 분석 — 정밀 성능 진단
- 20임베디드 Bus Architecture — AHB·AXI·CHI 진화와 5-Channel
- 21Bus Contention 진단 — Arbitration·QoS·Starvation 측정
- 22DMA 성능 최적화 — Burst·Scatter-Gather·Chain·Cache 일관성
- 23DMA vs CPU Copy 성능 비교 — Break-even·Setup Overhead 실측
- 24Interrupt Latency 분석 — 진입·종료·Tail-Chaining·Late Arrival
- 25Interrupt Storm 처리 — NAPI·Rate-Limit·Polling 전환
- 26MMIO 접근 성능 — Cache Policy·Write-Combining·Volatile·Barrier
- 27Peripheral Clock 분석 — PLL·Divider·Gating·DVFS
- 28Power vs Performance 트레이드오프 — DVFS·Race-to-Idle·Big.LITTLE
- 29Thermal Throttling 분석 — Junction Temp·Trip Point·냉각
- 30CXL Interconnect 분석 — AI 시대 메모리 대역폭 확장
- 31Concurrency 기초 — Concurrency vs Parallelism·Race·Memory Model
- 32False Sharing 진단 — Cache Line Ping-Pong·Padding·측정
- 33Lock Contention 분석 — Wait·Hold·Convoy·측정 기법
- 34Spinlock 성능 분석 — Spin-Wait vs Context Switch·Ticket·MCS
- 35Mutex 성능 분석 — Futex·Adaptive·Priority Inheritance
- 36Reader-Writer Lock 성능 — Reader/Writer Priority·RCU·Seqlock
- 37Lock-Free 자료구조 성능 — CAS·ABA·Hazard Pointer·Epoch Reclamation
- 38Memory Ordering 분석 — Acquire·Release·Seq-Cst·ARM Relaxed Model
- 39Cache Coherency 프로토콜 — MESI·MOESI·Snoop·Directory
- 40SMP 성능 분석 — Per-Core·Affinity·Load Balance·Scalability
- 41Linux perf 기초 — stat·record·report 활용
- 42Linux perf 고급 — Raw Event·Tracepoint·perf script
- 43ftrace 활용 — function·function_graph·latency tracer
- 44eBPF·bpftrace 동적 트레이싱 — 커널 무수정 관측
- 45Flamegraph 분석 — On-CPU·Off-CPU·Differential
- 46ARM DS·Lauterbach 분석 — Hardware Trace 전문 도구
- 47Bare-metal 프로파일링 — GPIO·DWT·SysTick·ITM 활용
- 48NVIDIA Nsight Systems — GPU·NPU 포함 시스템 분석
- 49모던 프로파일러 비교 — Tracy·Hotspot·uftrace·Coz
- 50연속 프로파일링 — Parca·Pixie·Pyroscope·Tetragon
- 51실전 사례 — ISR Latency 100µs Deadline Miss 추적
- 52실전 사례 — Matrix Multiply가 예상의 10배 느린 이유
- 53실전 사례 — 8-core가 4-core를 넘으면 throughput이 떨어지는 이유
- 54실전 사례 — 카메라 1080p 60fps가 30fps로 떨어지는 이유
- 55CXL.mem 지연·대역폭 실측 — Direct·Switch·Pooled 토폴로지 비교
- 56CXL 성능 프로파일링 도구 — cxl-cli·DAMON·perf-mem 활용
- 57실전 사례 — CXL.mem 추가로 LLM inference KV cache 처리량 회복
관련 글
실전 사례 — CXL.mem 추가로 LLM inference KV cache 처리량 회복
70B 모델 KV cache가 HBM 한계를 넘어 throughput이 무너졌을 때, CXL.mem 256 GB pool 추가로 회복한 실전 케이스.
CXL 성능 프로파일링 도구 — cxl-cli·DAMON·perf-mem 활용
CXL.mem 환경 성능 도구 — cxl-cli 토폴로지·DAMON page activity·perf-mem로 보는 CXL 트래픽·numastat 통계.
CXL.mem 지연·대역폭 실측 — Direct·Switch·Pooled 토폴로지 비교
CXL.mem 토폴로지별 실측 — Direct attach·Single switch·Multi-host pool의 지연·대역폭 비용 측정.