ref: 47300e194a5276a5c9b91080944c2cb0ff4dd979
parent: 7191930290637622c1a4bb50a359809e62e4bf58
author: 9ferno <[email protected]>
date: Sat Oct 23 13:08:14 EDT 2021
inferno fine tuning to 9front taslock.c
--- a/os/port/taslock.c
+++ b/os/port/taslock.c
@@ -50,6 +50,7 @@
dumpaproc(p);
}
+/* if looped to obtain a lock, return 1. Else, return 0 */
int
lock(Lock *l)
{
@@ -61,7 +62,7 @@
lockstats.locks++;
if(up)
up->nlocks++; /* prevent being scheded */
- if(tas(&l->key) == 0){
+ if(tas(&l->key) == 0){ /* got the lock on the 1st attempt, done */
if(up)
up->lastlock = l;
l->pc = pc;
@@ -81,14 +82,17 @@
lockstats.inglare++;
i = 0;
while(l->key){
- if(conf.nmach < 2 && up && up->edf && (up->edf->flags & Admitted)){
+ if(conf.nmach < 2 && up && up->state == Running && islo()
+ /* && up->edf && (up->edf->flags & Admitted)*/){
/*
* Priority inversion, yield on a uniprocessor; on a
* multiprocessor, the other processor will unlock
*/
- print("inversion %#p pc %#p proc %lud held by pc %#p proc %lud\n",
+ print("inversion %#p pc %#p proc %zud held by pc %#p proc %zud\n",
l, pc, up != nil ? up->pid : 0, l->pc, l->p != nil ? ((Proc*)l->p)->pid : 0);
- up->edf->d = todget(nil); /* yield to process with lock */
+ /* up->edf->d = todget(nil);*/ /* yield to process with lock */
+ up->pc = pc;
+ sched();
}
if(i++ > 100000000){
i = 0;
@@ -98,8 +102,11 @@
if(up)
up->nlocks++;
if(tas(&l->key) == 0){
- if(up)
+ if(up){
up->lastlock = l;
+ l->priority = up->priority;
+ up->priority = PriLock;
+ }
l->pc = pc;
l->p = up;
l->m = MACHP(m->machno);
@@ -126,6 +133,10 @@
x = splhi();
if(tas(&l->key) != 0){
lockstats.glare++;
+ if(conf.nmach < 2)
+ panic("ilock: no way out: pc 0x%zux:"
+ " lock 0x%p held by pc 0x%zux",
+ pc, l, l->pc);
/*
* Cannot also check l->pc, l->m, or l->isilock here
* because they might just not be set yet, or
@@ -160,14 +171,17 @@
{
if(up)
up->nlocks++;
- if(tas(&l->key)){
+ if(tas(&l->key) != 0){
if(up)
up->nlocks--;
return 0;
}
- if(up)
+ if(up){
up->lastlock = l;
+ l->priority = up->priority;
+ up->priority = PriLock;
+ }
l->pc = getcallerpc(&l);
l->p = up;
l->m = MACHP(m->machno);
@@ -181,6 +195,7 @@
void
unlock(Lock *l)
{
+ int pri;
#ifdef LOCKCYCLES
l->lockcycles += lcycles();
cumlockcycles += l->lockcycles;
@@ -201,16 +216,22 @@
dumpaproc(l->p);
dumpaproc(up);
}
- l->m = nil;
+ pri = l->priority;
+ l->m = l->p = nil;
+ l->pc = 0;
coherence();
l->key = 0;
- if(up && --up->nlocks == 0 && up->delaysched && islo()){
- /*
- * Call sched if the need arose while locks were held
- * But, don't do it from interrupt routines, hence the islo() test
- */
- sched();
+ if(up){
+ up->priority = pri;
+ up->lastlock = nil;
+ if(--up->nlocks == 0 && up->delaysched && islo()){
+ /*
+ * Call sched if the need arose while locks were held
+ * But, don't do it from interrupt routines, hence the islo() test
+ */
+ sched();
+ }
}
}
@@ -240,7 +261,8 @@
print("iunlock(%#p) while lo: pc %#p, held by %#p\n", l, getcallerpc(&l), l->pc);
sr = l->sr;
- l->m = nil;
+ l->m = l->p = nil;
+ l->sr = l->pc = 0;
coherence();
l->key = 0;
m->ilockdepth--;