2022-10-06 21:44:19 +08:00

36 lines
1.8 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

(_lockref)=
# lockref
  lockref是将自旋锁与引用计数变量融合在连续、对齐的8字节内的一种技术。
## lockref结构
```c
struct lockref
{
union
{
#ifdef __LOCKREF_ENABLE_CMPXCHG__
aligned_u64 lock_count; // 通过该变量的声明使得整个lockref的地址按照8字节对齐
#endif
struct
{
spinlock_t lock;
int count;
};
};
};
```
## 特性描述
  由于在高负载的情况下,系统会频繁的执行“锁定-改变引用变量-解锁”的操作这期间很可能出现spinlock和引用计数跨缓存行的情况这将会大大降低性能。lockref通过强制对齐尽可能的降低缓存行的占用数量使得性能得到提升。
  并且在x64体系结构下还通过cmpxchg()指令,实现了无锁快速路径。不需要对自旋锁加锁即可更改引用计数的值,进一步提升性能。当快速路径不存在(对于未支持的体系结构)或者尝试超时后,将会退化成“锁定-改变引用变量-解锁”的操作。此时由于lockref强制对齐只涉及到1个缓存行因此性能比原先的spinlock+ref_count的模式要高。
## 关于cmpxchg_loop
  在改变引用计数时cmpxchg先确保没有别的线程持有锁然后改变引用计数同时通过`lock cmpxchg`指令验证在更改发生时没有其他线程持有锁并且当前的目标lockref的值与old变量中存储的一致从而将新值存储到目标lockref。这种无锁操作能极大的提升性能。如果不符合上述条件在多次尝试后将退化成传统的加锁方式来更改引用计数。
## 参考资料
  [Introducing lockrefs - LWN.net, Jonathan Corbet](https://lwn.net/Articles/565734/)