Understanding glibc source conventions

I looked at some source code for glibc, in particular the nptl code, and I found it a little hard to understand, as it seems to have conventions that I am not familiar with.

For example, I looked at a very small pthread_equal.c file, and there are several things that I have questions about:

22 int 23 __pthread_equal (thread1, thread2) 24 pthread_t thread1; 25 pthread_t thread2; 26 { 27 return thread1 == thread2; 28 } 29 strong_alias (__pthread_equal, pthread_equal) 
  • The declaration on lines 22 and 23 looks like something I understand. It has an int return type, then the function name __pthread_equal and a list of parameters (thread1, thread2) . But what are the declarations of lines 24 pthread_t thread1; and 25 pthread_t thread2; for? It looks like they are declared global variables, but I don't understand the purpose. I saw this template in many files in the nptl directory and could not understand why this is done.

  • What is strong_alias ? A quick Google search has examples of how to use this, but I did not find a link to any documentation.

  • What is the reason for pre-designating several names with two underscores __ , and some with one underscore _ . Most of the code I saw uses two underscores, but I think I saw some places where one underscore is used. For example, in pthreadP.h

     556 /* Old cleanup interfaces, still used in libc.so. */ 557 extern void _pthread_cleanup_push (struct _pthread_cleanup_buffer *buffer, 558 void (*routine) (void *), void *arg); 559 extern void _pthread_cleanup_pop (struct _pthread_cleanup_buffer *buffer, 560 int execute); 561 extern void _pthread_cleanup_push_defer (struct _pthread_cleanup_buffer *buffer, 562 void (*routine) (void *), void *arg); 563 extern void _pthread_cleanup_pop_restore (struct _pthread_cleanup_buffer *buffer, 564 int execute); 

Admittedly, this code is preceded by a comment that says "old cleanup interfaces", but in any case I wonder what the difference is and why one underscore is sometimes used, and sometimes two underscores are used.

Any information regarding these issues is appreciated.

+8
c pthreads libc
source share
2 answers

The function is written without a compiler compatible with C89; It will work with older compilers. This definition is not a function prototype.

 int /* Return type */ function(arg1, arg2) /* Function name and argument names (but no types) */ int arg1; /* Type of arg1 */ char *arg2; /* Type of arg2 */ { /* Body of function */ } 

Note that the argument definitions should not be in the same sequence as the function line (I had to convert the code from this K & R notation to the prototype notation, where they were out of order!). Also note that earlier you could just write:

 main(argc, argv) char **argv; { ... } 

The implied type for argc was int , as it was not specified as anything else. Glib code is unlikely to use this license. Similarly, the return type of main() was int , because no other type was specified.

strong_alias refers to hiding and exporting characters in shared libraries. I have not used it, so I am not sure about all the branches, but I believe that this means that __pthread_equal() is a different name for the pthread_equal() function.


One of the reasons underlying __pthread_equal() is because names beginning with an underscore followed by a lowercase letter or other underscore are “reserved for implementation” by the C. standard. Names such as 'pthread_equal ()' are in the user namespace in accordance with the standard C.

ISO / IEC 9899: 1990 (C99 standard) states:

7.1.3 Reserved Identifiers

Each header declares or defines all identifiers listed in the corresponding subclause, and does not necessarily declare or defines identifiers listed in the future directions of the library associated with it by subparagraphs and identifiers, which are always reserved either for any use or for use as file identifiers of regions.

- All identifiers starting with an underscore, and either an uppercase letter or another underscore, are always reserved for any use.

- All identifiers starting with an underscore are always reserved for use as identifiers with file size in both regular and tag names.

- Each macro name in any of the following subclauses (including the future referral library) is reserved for use as indicated if any of its associated headers are included; unless expressly stated otherwise (see 7.1.4).

- All identifiers with external links in any of the following subclauses (including future directions of libraries) are always reserved for use as identifiers with external links. 154)

- Each identifier with a file area specified in any of the following subclauses (including future library directions) is reserved for use as a macro name and as an identifier with a file area in the same namespace if any of the related headers are included.

No other identifiers are reserved. If a program declares or defines an identifier in the context in which it is reserved (except as permitted in accordance with clause 7.1.4), or defines a reserved identifier as a macro name, the behavior is undefined.

154) The list of reserved identifiers with external communication includes errno , math_errhandling , setjmp and va_end .

+8
source share
  • Old letter.
  • To provide the __pthread_equal type, pthread_equal also.
  • To distinguish between variable names and to distinguish between a kernel area and a user area.
+2
source share

All Articles