- 论坛徽章:
- 0
|
回复 3# Tinnal
下面是linux-2.6.10的代码:- #define spin_lock(lock) _spin_lock(lock)
- void __lockfunc _spin_lock(spinlock_t *lock)
- {
- [color=Red]preempt_disable();
- [/color] if (unlikely(!_raw_spin_trylock(lock)))
- __preempt_spin_lock(lock);
- }
- static inline void __preempt_spin_lock(spinlock_t *lock)
- {
- if (preempt_count() > 1) {
- _raw_spin_lock(lock);
- return;
- }
- do {
- [color=Red]preempt_enable();
- [/color] while (spin_is_locked(lock))
- cpu_relax();
- [color=Red]preempt_disable();
- [/color] } while (!_raw_spin_trylock(lock));
- }
复制代码 =============================================================
下面是linux-3.10.0的代码:- static inline void spin_lock(spinlock_t *lock)
- {
- raw_spin_lock(&lock->rlock);
- }
- #define raw_spin_lock(lock) _raw_spin_lock(lock)
- void __lockfunc _raw_spin_lock(raw_spinlock_t *lock)
- {
- __raw_spin_lock(lock);
- }
- static inline void __raw_spin_lock(raw_spinlock_t *lock)
- {
- [color=Red]preempt_disable();
- [/color] spin_acquire(&lock->dep_map, 0, 0, _RET_IP_);
- LOCK_CONTENDED(lock, do_raw_spin_trylock, do_raw_spin_lock);
- }
- static inline void do_raw_spin_lock(raw_spinlock_t *lock) __acquires(lock)
- {
- __acquire(lock);
- arch_spin_lock(&lock->raw_lock);
- }
- static __always_inline void arch_spin_lock(arch_spinlock_t *lock)
- {
- register struct __raw_tickets inc = { .tail = TICKET_LOCK_INC };
- inc = xadd(&lock->tickets, inc);
- if (likely(inc.head == inc.tail))
- goto out;
- inc.tail &= ~TICKET_SLOWPATH_FLAG;
- for (;;) {
- unsigned count = SPIN_THRESHOLD;
- do {
- if (ACCESS_ONCE(lock->tickets.head) == inc.tail)
- goto out;
- cpu_relax();
- } while (--count);
- __ticket_lock_spinning(lock, inc.tail);
- }
- out: barrier(); /* make sure nothing creeps before the lock is taken */
- }
复制代码 新版本取消了自旋等待过程中的抢占使能。
|
|