- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
维基百科提供的使用 x86 XCHG 命令的自旋锁的示例实现是:
; Intel syntax
locked: ; The lock variable. 1 = locked, 0 = unlocked.
dd 0
spin_lock:
mov eax, 1 ; Set the EAX register to 1.
xchg eax, [locked] ; Atomically swap the EAX register with
; the lock variable.
; This will always store 1 to the lock, leaving
; the previous value in the EAX register.
test eax, eax ; Test EAX with itself. Among other things, this will
; set the processor's Zero Flag if EAX is 0.
; If EAX is 0, then the lock was unlocked and
; we just locked it.
; Otherwise, EAX is 1 and we didn't acquire the lock.
jnz spin_lock ; Jump back to the MOV instruction if the Zero Flag is
; not set; the lock was previously locked, and so
; we need to spin until it becomes unlocked.
ret ; The lock has been acquired, return to the calling
; function.
spin_unlock:
mov eax, 0 ; Set the EAX register to 0.
xchg eax, [locked] ; Atomically swap the EAX register with
; the lock variable.
ret ; The lock has been released.
从这里开始https://en.wikipedia.org/wiki/Spinlock#Example_implementation
我不明白为什么解锁需要是原子的。出了什么问题
spin_unlock:
mov [locked], 0
最佳答案
解锁确实需要have release semantics才能正确保护关键部分。但它不需要顺序一致性。原子性并不是真正的问题(见下文)。
所以,是的,在 x86 上,一个简单的存储是安全的,并且 glibc's pthread_spin_unlock
does so: :
movl $1, (%rdi)
xorl %eax, %eax
retq
另请参阅一个简单但可能可用的 x86 spinlock implementation I wrote in this answer ,它使用带有 pause
指令的只读自旋循环。
该代码可能是根据位字段版本改编的。
使用 btr
解锁位域中的一个标志将其归零并不安全,因为它是对包含字节 (or the containing naturally-aligned 4 byte dword or 2 byte word) 的非原子读取-修改-写入。
所以也许写它的人没有意识到 simple stores to aligned addresses are atomic on x86, like on most ISAs 。但 x86 具有弱序 ISA 所不具备的特点,那就是每个存储区都有 release semantics 。用于释放锁的 xchg 使每次解锁都成为完整的内存屏障,这超出了正常的锁定语义。 (尽管在 x86 上,获取锁将是一个完全障碍,因为没有 xchg
或其他 lock
就无法执行原子 RMW 或原子比较和交换ed 指令,这些都是像 mfence
这样的完整屏障。)
解锁存储在技术上不需要是原子的,因为我们只存储零或1,所以只有低字节重要。例如我认为如果锁未对齐并跨缓存行边界分割,它仍然可以工作。撕裂可能会发生,但并不重要,真正发生的是锁的低字节被原子地修改,操作总是将零放入高 3 个字节。
<小时/>如果你想返回旧值来捕获双重解锁错误,更好的实现是单独加载和存储:
spin_unlock:
;; pre-condition: [locked] is non-zero
mov eax, [locked] ; old value, for debugging
mov dword [locked], 0 ; On x86, this is an atomic store with "release" semantics.
;test eax,eax
;jz double_unlocking_detected ; or leave this to the caller
ret
关于assembly - 使用 XCHG 解锁的自旋锁,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36731166/
我注意到,当我打开我的应用程序并等待足够长的时间让我的手机自行锁定时,当我解锁它时,当前内容 View 未处于全屏模式。它不显示顶部栏,而是全黑线...如果我去另一个 Activity 并返回它再次修
我必须处理设计限制(依赖性问题)以不对互斥体使用范围保护。 示例代码: template class Test { MutexType myMutex; public: void f(
我正在尝试像这样使 my_class 线程安全。 class my_class { const std::vector& get_data() const { //lock so that
我想让手机在手机被锁定(锁定 = 键盘被锁定)并且用户想要解锁时询问一个问题(来自数据库)。如果答案正确,则手机解锁,否则手机会询问另一个问题。 我不知道如何检测解锁并在需要时解锁/锁定手机。 请帮帮
我有一个对 accept() 的阻塞调用。我从另一个线程关闭套接字,希望它能解除对 accept() 调用的阻塞,它确实如此,但我有一个情况,它没有:例如线程A进入accept(),线程B关闭sock
我在 C# 中有一个可以从多个线程调用多次的函数,我希望它只执行一次,所以我想到了这个: class MyClass { bool done = false; public void
锁定数据库的一个表 复制代码 代码如下: SELECT * FROM table WITH (HOLDLOCK) 注意: 锁定数据库的一个表的区别
我已经使用腻子在我的 ec2 实例上安装了 jenkins,从我的 Windows 系统 当我尝试通过网络访问 jenkins 时,我使用/var/lib/jenkins/secrets/initia
每次我打开我的电脑并尝试连接到 HR 数据库时,都会弹出一个错误提示被阻止,然后我转到 SQLPLUS 并以 SYSDBA 身份登录,并执行以下脚本: 我的问题是,我是否总是必须这样做?有什么办法让它
所以我的手机在引导加载程序中,我想解锁它 所以我输入 fastboot oem unlock 我明白了 D:\Minimal ADB and Fastboot>fastboot oem unlock
在我的应用程序中,我希望即使在应用程序终止后我的应用程序仍处于事件状态。我希望当“滑动解锁”我的应用程序启动时。 有可能吗?我怎样才能在不越狱的情况下做到这一点...... 这是为用户提供便利的功能。
即使我的 iPhone 使用电缆连接并解锁,它也会显示警告“Xcode 9.3 无法在 iPhone 上启动应用程序,因为设备已锁定”。我不知道该怎么办?有人对此有适当的解决方案吗?请 最佳答案 只需
我看到一个非常奇怪的行为,我试图了解它是否是这样设计的,或者只是没有从我的应用程序中正确处理。 我的应用程序以 UIAlertViews 的形式发送推送通知。当设备未锁定时,UIAlertViews
该文档说,从一个线程进行锁定并从另一个rwlock进行解锁会导致未定义的行为。我有一个数组和两个线程,一个分配它,一个释放它,这是一个周期发生的,也有一些线程在其中进行读/写操作,但是它们从不重叠,因
解锁 Oracle 表有哪些不同的技术? 我尝试过的。 获取锁定表的对象ID: SELECT object_id FROM dba_objects WHERE object_name='YOUR TA
我运行@apxchpwd.sql并用这个脚本给帐户倒霉 alter session set current_schema = APEX_050100; declare l_workspace_id
我想在 Chrome 扩展程序中提供一些高级功能。这个想法是,只要用户通过 PayPal 捐赠了一定金额,就可以使用后者的附加功能。 目前我的策略是这样的: 1/。用户填写 PayPal 表格。 2/
我构建了一个包含 IAP(应用内购买)的应用。该应用程序是使用 UINavigationController 构建的。当用户决定购买内容时,解锁功能会解锁该内容。然后,用户点击后退按钮,他们将返回主菜
我有一个只能通过静态方法从外部访问的类。然后,这些静态方法创建该类的一个对象以在该方法中使用,然后它们返回并且该对象可能被销毁。该类是几个配置文件的 getter/setter,现在我需要在对配置文件
我可以在超出 scoped_lock 范围之前解锁互斥锁吗?我怎么能那样做? {boost::mutex::scoped_lock lock(mutex); if(conditionaA) {
我是一名优秀的程序员,十分优秀!