+global spinlock_acquire:function
+global spinlock_release:function
+global spinlock_init:function
+
+; spinlock addr in rdi
+; low four bytes is ticket number
+; high four bytes is turn counter
+
+spinlock_init:
+ mov rax, 0
+ mov [rdi], rax
+ ret
+
+spinlock_acquire:
+ mov eax, 1
+ lock xadd [rdi], eax ; eax = my ticket number
+
+ cmp [rdi+4], eax ; is it my turn?
+ je .acquired ; yes
+
+.retry:
+ pause
+ cmp [rdi+4], eax ; is it my turn?
+ jne .retry ; keep waiting
+.acquired:
+ ret
+
+spinlock_release:
+ lock inc dword [rdi+4]
+ ret