【问题标题】:Where is the logic of comparing '__libc_multiple_threads'?比较'__libc_multiple_threads'的逻辑在哪里?
【发布时间】:2021-02-09 14:58:12
【问题描述】:

在分析 iofclose.c 文件时,我发现了其中一些奇怪的部分。

// glibc-2.23.90/libio/iofclose.c:53

 if (fp->_IO_file_flags & _IO_IS_FILEBUF)
    _IO_un_link ((struct _IO_FILE_plus *) fp);

  _IO_acquire_lock (fp); // !!!!! This part !!!!!
 ...

如您所见,fclose() 在内部调用 _IO_acquire_lock

_IO_acquire_lock 在此下方调用_IO_lock_lock

//glibc-2.23.90/sysdeps/nptl/stdio-lock.h:39

#define _IO_lock_lock(_name) \
  do {                                        \
    void *__self = THREAD_SELF;                           \
    if ((_name).owner != __self)                          \
      {                                       \
    lll_lock ((_name).lock, LLL_PRIVATE);                     \
...

_IO_lock_lockvoid *__self = THREAD_SELF;if ((_name).owner != __self)逻辑是这样出现的。

0x7f9a21eca393 <_IO_new_fclose+291>: mov    r8,QWORD PTR fs:0x10
   0x7f9a21eca39c <_IO_new_fclose+300>: cmp    r8,QWORD PTR [rdx+0x8]
   0x7f9a21eca3a0 <_IO_new_fclose+304>: je     0x7f9a21eca3e2 <_IO_new_fclose+370>
   0x7f9a21eca3a2 <_IO_new_fclose+306>: mov    esi,0x1
...

那么,如果在分支命令之后调用lll_lock((_name).lock, LLL_PRIVATE);,则lll_lock()会这样进行。

0x7f9a21eca3a2 <_IO_new_fclose+306>: mov    esi,0x1
   0x7f9a21eca3a7 <_IO_new_fclose+311>: xor    eax,eax
   0x7f9a21eca3a9 <_IO_new_fclose+313>:
    cmp    DWORD PTR [rip+0x35c390],0x0        # 0x7f9a22226740 <__libc_multiple_threads>
   0x7f9a21eca3b0 <_IO_new_fclose+320>: je     0x7f9a21eca3ba <_IO_new_fclose+330>
...

在这个程序集中,比较__libc_multiple_threads的逻辑是。

但是,当我看到lll_lock() 代码时,我找不到那个逻辑......

//glibc-2.23.90/sysdeps/unix/sysv/linux/sparc/lowlevellock.h:51

static inline void
__attribute__ ((always_inline))
__lll_lock (int *futex, int private)
{
  int val = atomic_compare_and_exchange_val_24_acq (futex, 1, 0);

  if (__glibc_unlikely (val != 0))
    {
      if (__builtin_constant_p (private) && private == LLL_PRIVATE)
    __lll_lock_wait_private (futex);
      else
    __lll_lock_wait (futex, private);
    }
}
#define lll_lock(futex, private) __lll_lock (&(futex), private)

这种情况是怎么发生的?

在这个 c 源代码中哪里可以找到这些汇编逻辑?

【问题讨论】:

    标签: c glibc


    【解决方案1】:

    您正在阅读 SPARC 锁定实现的源代码,但您显示的程序集是 x86。我认为您想要的代码在sysdeps/unix/sysv/linux/x86/lowlevellock.h 中。在那里你会看到它测试if (is_single_thread)。这将扩展为SINGLE_THREAD_P,在sysdeps/unix/sysv/linux/single-thread.h 中定义以扩展为__glibc_likely (__libc_multiple_threads == 0)

    【讨论】:

      猜你喜欢
      • 2014-03-16
      • 1970-01-01
      • 2011-09-08
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多