Skip to content

Commit 180e69a

Browse files
cmyuiclaude
andauthored
Add benchmark suite and request timing instrumentation (#1)
Benchmark suite (make bench) measures operation latencies across all major subsystems: slab allocator, database, string utilities, JSON builder, and HTTP request parsing. Uses ARM64 Generic Timer for nanosecond-precision measurements. Request timing logs wall-clock time for every HTTP request handled by slowapi_handle, printed to UART on completion. Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
1 parent 0cb0a61 commit 180e69a

10 files changed

Lines changed: 1241 additions & 2 deletions

File tree

Makefile

Lines changed: 30 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,10 +7,12 @@ OBJCOPY = aarch64-none-elf-objcopy
77
KERNEL_ELF = kernel.elf
88
KERNEL_BIN = kernel.bin
99
TEST_ELF = kernel_test.elf
10+
BENCH_ELF = kernel_bench.elf
1011

1112
# Common source files (shared between server and tests)
1213
COMMON_SRCS = src/drivers/uart.s \
1314
src/drivers/virtio.s \
15+
src/drivers/timer.s \
1416
src/net/ethernet.s \
1517
src/net/arp.s \
1618
src/net/ipv4.s \
@@ -61,11 +63,24 @@ TEST_SRCS = src/test/test_main.s \
6163
src/app.s
6264
TEST_OBJS = $(TEST_SRCS:.s=.o)
6365

66+
# Benchmark sources
67+
BENCH_SRCS = src/bench/bench_main.s \
68+
src/bench/bench_harness.s \
69+
src/bench/bench_slab.s \
70+
src/bench/bench_db.s \
71+
src/bench/bench_string.s \
72+
src/bench/bench_json.s \
73+
src/bench/bench_request.s \
74+
$(COMMON_SRCS) \
75+
$(MEM_DB_SRCS) \
76+
$(SLOWAPI_SRCS)
77+
BENCH_OBJS = $(BENCH_SRCS:.s=.o)
78+
6479
# Flags
6580
ASFLAGS = -g
6681
LDFLAGS = -T linker.ld -nostdlib
6782

68-
.PHONY: all clean run test
83+
.PHONY: all clean run test bench
6984

7085
all: $(KERNEL_ELF)
7186

@@ -75,14 +90,17 @@ $(KERNEL_ELF): $(SERVER_OBJS) linker.ld
7590
$(TEST_ELF): $(TEST_OBJS) linker.ld
7691
$(LD) $(LDFLAGS) -o $@ $(TEST_OBJS)
7792

93+
$(BENCH_ELF): $(BENCH_OBJS) linker.ld
94+
$(LD) $(LDFLAGS) -o $@ $(BENCH_OBJS)
95+
7896
$(KERNEL_BIN): $(KERNEL_ELF)
7997
$(OBJCOPY) -O binary $< $@
8098

8199
%.o: %.s
82100
$(AS) $(ASFLAGS) -o $@ $<
83101

84102
clean:
85-
rm -f $(SERVER_OBJS) $(TEST_OBJS) $(KERNEL_ELF) $(KERNEL_BIN) $(TEST_ELF)
103+
rm -f $(SERVER_OBJS) $(TEST_OBJS) $(BENCH_OBJS) $(KERNEL_ELF) $(KERNEL_BIN) $(TEST_ELF) $(BENCH_ELF)
86104

87105
run: $(KERNEL_ELF)
88106
qemu-system-aarch64 \
@@ -103,3 +121,13 @@ test: $(TEST_ELF)
103121
-kernel $(TEST_ELF) \
104122
-device virtio-net-device,netdev=net0 \
105123
-netdev user,id=net0
124+
125+
bench: $(BENCH_ELF)
126+
qemu-system-aarch64 \
127+
-machine virt \
128+
-cpu cortex-a72 \
129+
-nographic \
130+
-global virtio-mmio.force-legacy=true \
131+
-kernel $(BENCH_ELF) \
132+
-device virtio-net-device,netdev=net0 \
133+
-netdev user,id=net0

src/bench/bench_db.s

Lines changed: 187 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,187 @@
1+
// Database Benchmarks
2+
3+
.section .text
4+
.global run_db_benchmarks
5+
6+
run_db_benchmarks:
7+
stp x29, x30, [sp, #-16]!
8+
mov x29, sp
9+
10+
ldr x0, =section_name
11+
bl bench_section
12+
13+
ldr x0, =ctx_db_create
14+
bl bench_run
15+
ldr x0, =ctx_db_get
16+
bl bench_run
17+
ldr x0, =ctx_db_delete
18+
bl bench_run
19+
ldr x0, =ctx_db_list
20+
bl bench_run
21+
22+
ldp x29, x30, [sp], #16
23+
ret
24+
25+
//=============================================================================
26+
// Benchmark functions
27+
//=============================================================================
28+
29+
// Create + delete a record (self-contained per iteration)
30+
bench_fn_db_create:
31+
stp x29, x30, [sp, #-16]!
32+
mov x29, sp
33+
34+
ldr x0, =test_record
35+
mov x1, #8
36+
bl db_create
37+
// Delete to keep db clean for next iteration
38+
bl db_delete
39+
40+
ldp x29, x30, [sp], #16
41+
ret
42+
43+
// Get a record by ID (record created in setup)
44+
bench_fn_db_get:
45+
stp x29, x30, [sp, #-16]!
46+
mov x29, sp
47+
48+
ldr x0, =db_saved_id
49+
ldr w0, [x0]
50+
bl db_get
51+
52+
ldp x29, x30, [sp], #16
53+
ret
54+
55+
// Create + delete (measures delete cost, self-contained)
56+
bench_fn_db_delete:
57+
stp x29, x30, [sp, #-16]!
58+
mov x29, sp
59+
60+
ldr x0, =test_record
61+
mov x1, #8
62+
bl db_create
63+
bl db_delete
64+
65+
ldp x29, x30, [sp], #16
66+
ret
67+
68+
// Count records
69+
bench_fn_db_list:
70+
stp x29, x30, [sp, #-16]!
71+
mov x29, sp
72+
73+
bl db_count
74+
75+
ldp x29, x30, [sp], #16
76+
ret
77+
78+
// Setup: reinit mem + db
79+
bench_db_setup_reinit:
80+
stp x29, x30, [sp, #-16]!
81+
mov x29, sp
82+
83+
bl mem_init
84+
bl db_init
85+
86+
ldp x29, x30, [sp], #16
87+
ret
88+
89+
// Setup: reinit + create one record (for get benchmark)
90+
bench_db_setup_create:
91+
stp x29, x30, [sp, #-16]!
92+
mov x29, sp
93+
94+
bl mem_init
95+
bl db_init
96+
ldr x0, =test_record
97+
mov x1, #8
98+
bl db_create
99+
ldr x1, =db_saved_id
100+
str w0, [x1]
101+
102+
ldp x29, x30, [sp], #16
103+
ret
104+
105+
// Setup: reinit + populate 10 records (for list benchmark)
106+
bench_db_setup_populate:
107+
stp x29, x30, [sp, #-16]!
108+
mov x29, sp
109+
stp x19, xzr, [sp, #-16]!
110+
111+
bl mem_init
112+
bl db_init
113+
114+
mov w19, #10
115+
.populate_loop:
116+
cbz w19, .populate_done
117+
ldr x0, =test_record
118+
mov x1, #8
119+
bl db_create
120+
sub w19, w19, #1
121+
b .populate_loop
122+
.populate_done:
123+
124+
ldp x19, xzr, [sp], #16
125+
ldp x29, x30, [sp], #16
126+
ret
127+
128+
//=============================================================================
129+
// Benchmark contexts
130+
//=============================================================================
131+
132+
.section .data
133+
.balign 8
134+
ctx_db_create:
135+
.quad name_db_create
136+
.quad bench_fn_db_create
137+
.quad bench_db_setup_reinit
138+
.quad 0
139+
.word 500
140+
.skip 28
141+
142+
.balign 8
143+
ctx_db_get:
144+
.quad name_db_get
145+
.quad bench_fn_db_get
146+
.quad bench_db_setup_create
147+
.quad 0
148+
.word 1000
149+
.skip 28
150+
151+
.balign 8
152+
ctx_db_delete:
153+
.quad name_db_delete
154+
.quad bench_fn_db_delete
155+
.quad bench_db_setup_reinit
156+
.quad 0
157+
.word 500
158+
.skip 28
159+
160+
.balign 8
161+
ctx_db_list:
162+
.quad name_db_list
163+
.quad bench_fn_db_list
164+
.quad bench_db_setup_populate
165+
.quad 0
166+
.word 100
167+
.skip 28
168+
169+
.section .rodata
170+
section_name:
171+
.asciz "database"
172+
name_db_create:
173+
.asciz "db_create"
174+
name_db_get:
175+
.asciz "db_get"
176+
name_db_delete:
177+
.asciz "db_delete"
178+
name_db_list:
179+
.asciz "db_list"
180+
181+
test_record:
182+
.ascii "testdata"
183+
184+
.section .bss
185+
.balign 4
186+
db_saved_id:
187+
.skip 4

0 commit comments

Comments
 (0)