Hello everyone.. I try to observe how TLS and NPTL work on kernel side. I use Redhat 9 with stock kernel 2.4.20-19.9 and glibc-2.3.2-11.9. I create a simple pthread test program which forks 2 threads and simply print "Hello world" message. At the end, I call pthread_join two times to cleanly terminate these two threads and finally terminate the main program. Strace-ing on the program shows me these interesting outputs (i am sorry if the line wrapping screws code pasted below): mmap2(NULL, 8388608, PROT_READ|PROT_WRITE|PROT_EXEC, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x40037000 brk(0) = 0x8049824 brk(0x804a824) = 0x804a824 brk(0) = 0x804a824 brk(0x804b000) = 0x804b000 mprotect(0x40037000, 4096, PROT_NONE) = 0 clone(child_stack=0x408368d0,flags=CLONE_VM|CLONE_FS|CLONE_FILES| CLONE_SIGHAND|CLONE_THREAD|CLONE_SETTLS|CLONE_PARENT_SETTID| CLONE_CHILD_CLEARTID|CLONE_DETACHED, [4954],{entry_number:6,base_addr:0x40836cc0, limit:1048575,seg_32bit:1,contents:0, read_exec_only:0, limit_in_pages:1,seg_not_present:0, useable:1}) = 4954 On the other hand, inside arch/i386/kernel/process.c, i found codes that handles CLONE_SETTLS flag (copy_thread() function ): if (clone_flags & CLONE_SETTLS) { struct desc_struct *desc; struct user_desc info; int idx; if (copy_from_user(&info, (void *)childregs->esi, sizeof(info))) return -EFAULT; if (LDT_empty(&info)) return -EINVAL; idx = info.entry_number; if (idx < GDT_ENTRY_TLS_MIN || idx > GDT_ENTRY_TLS_MAX) return -EINVAL; desc = p->thread.tls_array + idx - GDT_ENTRY_TLS_MIN; desc->a = LDT_entry_a(&info); desc->b = LDT_entry_b(&info); } My questions is: 1. What is the purpose of allocating new LDT entry? Is it to provide new segment for freshly created thread to store its thread-local data? 2. Is the format of LDT entry 100% similar with GDT entry? If yes, what is the advantage of using LDT for this threading purpose instead of GDT? 3. Observing strace results, it seems that the user space program defines certain base address for new allocated segment along with other attributes. On the kernel side, seems like these informations are retrieved to construct new LDT entry. My early conclusions is: base address is needed because thread local data (defined by __thread) only contains offset, thus it needs base address to form a complete linear address. Is this correct? 4. I read somewhere on the Internet that gs register is used to point on the currently used LDT entry related with currently running thread. Is this just a convention which is used inside the libpthread? or is there other explanation on why using gs register for this purpose? thank your for your help...again, sorry for this long e-mail....... regards Mulyadi -- Kernelnewbies: Help each other learn about the Linux kernel. Archive: http://mail.nl.linux.org/kernelnewbies/ FAQ: http://kernelnewbies.org/faq/