diff --git a/more/spin-lock/README.md b/more/spin-lock/README.md index 4d0b166..a8096d8 100644 --- a/more/spin-lock/README.md +++ b/more/spin-lock/README.md @@ -105,25 +105,24 @@ Bummer. Here is the source code to the spin-lock for ARM V8. ```text -#if defined(__APPLE__) // 1 -_Lock: // 2 -#else // 3 -Lock: // 4 -#endif // 5 - START_PROC // 6 -1: ldaxr w1, [x0] // 7 - cbnz w1, 1b // lock taken - spin. // 8 - add w1, w1, 1 // 9 - stlxr w2, w1, [x0] // 10 - cbnz w2, 1b // shucks - somebody meddled. // 11 - // considered using dmb here // 12 - ret // 13 - END_PROC // 14 +#if defined(__APPLE__) // 1 +_Lock: // 2 +#else // 3 +Lock: // 4 +#endif // 5 + START_PROC // 6 + mov w3, 1 // 7 +1: ldaxr w1, [x0] // 8 + cbnz w1, 1b // lock taken - spin. // 9 + stlxr w2, w3, [x0] // 10 + cbnz w2, 1b // shucks - somebody meddled. // 11 + ret // 12 + END_PROC // 13 ``` -Once again, line 7 does a `ldaxr` dereferencing the lock itself (once -again an `int32_t`) and marks the location of the lock as being -hopefully, exclusive. +Line 8 does a `ldaxr` dereferencing the lock itself (once again an +`int32_t`) and marks the location of the lock as being hopefully, +exclusive. Having gotten the value of the lock, on line 8, its value is inspected and if found to be non-zero, we branch back to attempting to get it @@ -149,7 +148,7 @@ Unlock: // 4 #endif // 5 START_PROC // 6 str wzr, [x0] // 7 - // considered using dmb here // 8 + dmb ish // 8 ret // 9 END_PROC // 10 ``` @@ -159,5 +158,11 @@ of the lock requires that no bad actor simply stomps on the lock by calling `Unlock` without first owning the lock. Just say no to lock stompers. +Line 8 sets up a data memory barrier across each processor - it makes +sure threads running on different cores see the update correctly. This +code seemed to work without this line but intuition suggests it could +be important. In `Lock()` the `stlxr` instruction has an implied data +memory barrier. + Please see the source code located [here](./spin_lock.S) for some additional comments regarding the implementation. diff --git a/more/spin-lock/README.pdf b/more/spin-lock/README.pdf index a8b0277..67da866 100644 Binary files a/more/spin-lock/README.pdf and b/more/spin-lock/README.pdf differ diff --git a/more/spin-lock/spin_lock.S b/more/spin-lock/spin_lock.S index 4fb727e..f4aff4f 100644 --- a/more/spin-lock/spin_lock.S +++ b/more/spin-lock/spin_lock.S @@ -33,7 +33,6 @@ Lock: cbnz w1, 1b // lock taken - spin. stlxr w2, w3, [x0] cbnz w2, 1b // shucks - somebody meddled. - // considered using dmb here ret END_PROC @@ -44,8 +43,8 @@ Unlock: #endif START_PROC str wzr, [x0] - // considered using dmb here + dmb ish // ensure all cores are aware. ret END_PROC - .end \ No newline at end of file + .end