Skip to content

Commit 6e801bf

Browse files
committed
softbkl: replace hardware k0lock with software ticket lock (SOFT_BKL)
Introduce SOFT_BKL compile-time flag that redirects all BKL lock/unlock sites from the hardware k0lock instruction to an in-memory ticket spinlock. - BKL_LOCK/BKL_UNLOCK macros in hw.h dispatch to H2K_spinlock_{lock,unlock} when SOFT_BKL is set, k0lock/k0unlock otherwise - ASM_BKL_LOCK/ASM_BKL_UNLOCK macros in asm_std.h wrap the LL/SC ticket lock for .S files; K0LOCK/K0UNLOCK (bypass poison) otherwise - Makefile poisons bare k0lock/k0unlock in .S files to enforce macro use - H2K_spinlock_t bkl field added to H2K_kg_t under SOFT_BKL - All 20 .S files converted from bare k0lock/k0unlock to ASM_BKL_LOCK/UNLOCK - ticket lock: 32-bit packed (upper 16 = next, lower 16 = now_serving), strictly fair FIFO, removes dccleana from acquire path - h2_init() sets H2K_gp (r28) so INC_KERNEL tests work without per-test change - boot.ref.S adds call 1f to establish r31 before first ASM_BKL_LOCK make testall SOFT_BKL=1: 1224 passed, 0 failed Signed-off-by: Erich Plondke <erich@qti.qualcomm.com>
1 parent 06e67bb commit 6e801bf

35 files changed

Lines changed: 252 additions & 118 deletions

File tree

kernel/Makefile

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -58,6 +58,13 @@ ifdef MULTICORE
5858
CFLAGS += -DMULTICORE
5959
endif
6060

61+
# Force all assembly to go through ASM_BKL_LOCK/ASM_BKL_UNLOCK in asm_std.h.
62+
CFLAGS += -Dk0lock=DO_NOT_USE_K0LOCK -Dk0unlock=DO_NOT_USE_K0UNLOCK
63+
64+
ifdef SOFT_BKL
65+
CFLAGS += -DSOFT_BKL
66+
endif
67+
6168
CFLAGS += -DH2K_KERNEL_PGSIZE=$(H2K_KERNEL_PGSIZE) -DH2K_KERNEL_ADDRBITS=$(H2K_KERNEL_ADDRBITS) -DH2K_GIT_COMMIT=$(H2K_GIT_COMMIT)
6269

6370
CFLAGS += $(KERNEL_CFLAGS) $(H2K_EXTRA_CFLAGS)

kernel/build/offsets/offsets.ref.c

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -147,6 +147,9 @@ int main(int argc, char **argv)
147147
PRINT_KG_OFFSET(dma_version);
148148
PRINT_KG_OFFSET(core_id);
149149
PRINT_KG_OFFSET(core_count);
150+
#ifdef SOFT_BKL
151+
PRINT_KG_OFFSET(bkl);
152+
#endif
150153

151154
PRINT_KG_SUBSTRUCT_OFFSET(time,next_ticks);
152155
PRINT_KG_SUBSTRUCT_OFFSET(time,last_ticks);

kernel/checkers/checker_kernel_locked/checker_kernel_locked.check.c

Lines changed: 2 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -10,27 +10,17 @@
1010

1111
s32_t checker_kernel_locked()
1212
{
13-
#if ARCHV >= 3
14-
u32_t syscfg = H2K_get_syscfg();
15-
if ((syscfg & (1<<12)) == 0) {
13+
if (!IS_BKL_LOCKED()) {
1614
FAIL("checker_kernel_locked: Kernel not locked.");
1715
}
18-
#else
19-
#error support less than v3
20-
#endif
2116
return 1;
2217
}
2318

2419
s32_t checker_kernel_unlocked()
2520
{
26-
#if ARCHV >= 3
27-
u32_t syscfg = H2K_get_syscfg();
28-
if ((syscfg & (1<<12)) != 0) {
21+
if (IS_BKL_LOCKED()) {
2922
FAIL("checker_kernel_unlocked: Kernel is Locked.");
3023
}
31-
#else
32-
#error support less than v3
33-
#endif
3424
return 1;
3525
}
3626

kernel/data/globals/globals.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -133,6 +133,9 @@ typedef struct {
133133
u32_t last_tlb_index_dma;
134134
u32_t tlb_size_dma;
135135
u32_t dma_tlb_start;
136+
#endif
137+
#ifdef SOFT_BKL
138+
H2K_spinlock_t bkl;
136139
#endif
137140
H2K_spinlock_t tmpmap_lock;
138141
H2K_spinlock_t asid_spinlock;

kernel/event/error/error.ref.S

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -91,7 +91,8 @@ FUNC_START H2K_fatal_crash .text.vm.error .p2align 2
9191
{
9292
memw(H2K_GP+#KG_is_nmi_soft) = #1
9393
}
94-
k0lock
94+
// FIXME SOFT_BKL: crash path must NOT block on BKL if lock is already held
95+
ASM_BKL_LOCK(r6, r7, r8, p0)
9596
r2 = htid
9697
r3 = #-1
9798
r3 = togglebit(r3,r2)
@@ -127,7 +128,7 @@ FUNC_START H2K_fatal_crash .text.vm.error .p2align 2
127128
syscfg = r1
128129
// We should now be in "Single Thread Mode": only one thread active, and that's the one executing here
129130
// Did we possibly nmi a thread holding a lock? We can fix it!
130-
k0unlock
131+
ASM_BKL_UNLOCK(r6, r7, r8, p0)
131132
tlbunlock
132133
// Bit 1: Save off TLB and flush caches
133134
// EJP: for now, let's do this all the time.

kernel/event/interrupt/interrupt.ref.S

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -181,7 +181,7 @@ FUNC_START H2K_interrupted_waitmode .text.core.interrupt .p2align 2
181181
p0 = cmp.eq(INTINFO_FN,#0) // really, we shouldn't get NULL interrupt handlers, but if we do...
182182
if (!p0) callr INTINFO_FN
183183
r1:0 = #0
184-
k0lock
184+
ASM_BKL_LOCK(r6, r7, r8, p0)
185185
jump H2K_switch
186186

187187
FUNC_END H2K_interrupted_waitmode

kernel/event/interrupt/interrupt.v3opt.S

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -77,7 +77,7 @@ FUNC_START H2K_interrupted_waitmode .text.core.interrupt .falign
7777
{
7878
callr r4
7979
}
80-
k0lock
80+
ASM_BKL_LOCK(r6, r7, r8, p0)
8181
{
8282
r1:0 = combine(#0,#0)
8383
jump H2K_switch

kernel/event/interrupt/interrupt.v4opt.S

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -178,9 +178,7 @@ FUNC_START H2K_interrupted_waitmode_or_preempt .text.core.interrupt .p2align 5
178178
jumpr r31
179179
}
180180
1: // We were idle, go back to sleep
181-
{
182-
k0lock
183-
}
181+
ASM_BKL_LOCK(r6, r7, r8, p0)
184182
{
185183
r1:0 = #0
186184
jump H2K_switch

kernel/event/interrupt/test/test.c

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@
1111
#include <setjmp.h>
1212
#include <max.h>
1313
#include <globals.h>
14+
#include <hw.h>
1415
#include <trace.h>
1516

1617
/*
@@ -97,7 +98,7 @@ void H2K_switch(H2K_thread_context *from, H2K_thread_context *to)
9798
{
9899
if (from != NULL) FAIL("Unexpected FROM");
99100
if (to != NULL) FAIL("Unexpected TO");
100-
asm volatile (" k0unlock ");
101+
BKL_UNLOCK();
101102
longjmp(env,1);
102103
}
103104

kernel/event/popup/popup.v4opt.S

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@ FUNC_START H2K_popup_int .text.int.popup .p2align 5
2525
#define NEGONE r13
2626
#define NEWPRIO r14
2727
#define PRIO r15
28-
k0lock
28+
ASM_BKL_LOCK(r6, r7, r8, p0)
2929
{
3030
WAIT_PRIOMASKS = memd(H2K_GP+#KG_lowprio_masks) // share w/ priomask?
3131
HANDLERBASE = add(H2K_GP,#KG_inthandlers)
@@ -98,7 +98,7 @@ FUNC_START H2K_popup_int .text.int.popup .p2align 5
9898
if (!p1) memd(ME) = PREV_HEAD
9999
}
100100
.Lnohandler:
101-
k0unlock
101+
ASM_BKL_UNLOCK(r6, r7, r8, p0)
102102
jumpr r31
103103
#undef INTNO
104104
#undef ME
@@ -147,7 +147,7 @@ FUNC_START H2K_popup_wait .text.int.popup .falign
147147
p1 = cmp.eq(INTNO, #L2_CORE_INTERRUPT)
148148
if (p1.new) jump:nt 9f
149149
}
150-
k0lock
150+
ASM_BKL_LOCK(r6, r7, r8, p0)
151151
#define TMP INTHANDLERS_ADDR
152152
{
153153
TMP = memub(ME+#CONTEXT_vmstatus)
@@ -208,7 +208,7 @@ FUNC_START H2K_popup_wait .text.int.popup .falign
208208
jump H2K_dosched
209209
}
210210
8:
211-
k0unlock
211+
ASM_BKL_UNLOCK(r6, r7, r8, p0)
212212
9:
213213
{
214214
r0 = #-1
@@ -219,7 +219,7 @@ FUNC_START H2K_popup_wait .text.int.popup .falign
219219
r0 = ME
220220
call H2K_vm_do_work_withlock
221221
}
222-
k0unlock
222+
ASM_BKL_UNLOCK(r6, r7, r8, p0)
223223
{
224224
r0 = #-1
225225
dealloc_return

0 commit comments

Comments
 (0)