Alexandre Julliard : ntdll: Move the CPU-specific handling of current TEB to the respective signal files .

Alexandre Julliard julliard at winehq.org
Wed Feb 18 10:15:28 CST 2009


Module: wine
Branch: master
Commit: 66255772fc4116f192413d56d13a49f79700ea9e
URL:    http://source.winehq.org/git/wine.git/?a=commit;h=66255772fc4116f192413d56d13a49f79700ea9e

Author: Alexandre Julliard <julliard at winehq.org>
Date:   Wed Feb 18 13:04:50 2009 +0100

ntdll: Move the CPU-specific handling of current TEB to the respective signal files.

---

 dlls/ntdll/ntdll_misc.h     |    5 ++++-
 dlls/ntdll/signal_i386.c    |   23 +++++++++++++++--------
 dlls/ntdll/signal_powerpc.c |   21 +++++++++++++++++++--
 dlls/ntdll/signal_sparc.c   |   21 ++++++++++++++++++++-
 dlls/ntdll/signal_x86_64.c  |   11 +++++++++--
 dlls/ntdll/thread.c         |   32 ++------------------------------
 6 files changed, 69 insertions(+), 44 deletions(-)

diff --git a/dlls/ntdll/ntdll_misc.h b/dlls/ntdll/ntdll_misc.h
index b42303c..90c74a9 100644
--- a/dlls/ntdll/ntdll_misc.h
+++ b/dlls/ntdll/ntdll_misc.h
@@ -22,6 +22,9 @@
 #include <stdarg.h>
 #include <signal.h>
 #include <sys/types.h>
+#ifdef HAVE_PTHREAD_H
+# include <pthread.h>
+#endif
 
 #include "windef.h"
 #include "winnt.h"
@@ -52,7 +55,7 @@ extern NTSTATUS NTDLL_wait_for_multiple_objects( UINT count, const HANDLE *handl
                                                  const LARGE_INTEGER *timeout, HANDLE signal_object );
 
 /* init routines */
-extern void signal_init_thread(void);
+extern void signal_init_thread( TEB *teb );
 extern void signal_init_process(void);
 extern size_t get_signal_stack_total_size(void);
 extern void version_init( const WCHAR *appname );
diff --git a/dlls/ntdll/signal_i386.c b/dlls/ntdll/signal_i386.c
index ffa60ad..790d9ca 100644
--- a/dlls/ntdll/signal_i386.c
+++ b/dlls/ntdll/signal_i386.c
@@ -372,6 +372,7 @@ WINE_DEFAULT_DEBUG_CHANNEL(seh);
 
 typedef int (*wine_signal_handler)(unsigned int sig);
 
+static const size_t teb_size = 4096;  /* we reserve one page for the TEB */
 static size_t signal_stack_mask;
 static size_t signal_stack_size;
 
@@ -1578,8 +1579,6 @@ static void usr1_handler( int signal, siginfo_t *siginfo, void *sigcontext )
  */
 size_t get_signal_stack_total_size(void)
 {
-    static const size_t teb_size = 4096;  /* we reserve one page for the TEB */
-
     if (!signal_stack_size)
     {
         size_t size = 8192, min_size = teb_size + max( MINSIGSTKSZ, 8192 );
@@ -1607,9 +1606,10 @@ int CDECL __wine_set_signal_handler(unsigned int sig, wine_signal_handler wsh)
 /**********************************************************************
  *		signal_init_thread
  */
-void signal_init_thread(void)
+void signal_init_thread( TEB *teb )
 {
-#ifdef HAVE_SIGALTSTACK
+    struct ntdll_thread_data *thread_data = (struct ntdll_thread_data *)teb->SystemReserved2;
+    LDT_ENTRY fs_entry;
     stack_t ss;
 
 #ifdef __APPLE__
@@ -1620,13 +1620,16 @@ void signal_init_thread(void)
     sysctl( mib, 2, NULL, NULL, &val, sizeof(val) );
 #endif
 
-    ss.ss_sp    = get_signal_stack();
+    ss.ss_sp    = (char *)teb + teb_size;
     ss.ss_size  = signal_stack_size;
     ss.ss_flags = 0;
     if (sigaltstack(&ss, NULL) == -1) perror( "sigaltstack" );
-#endif  /* HAVE_SIGALTSTACK */
 
-    ntdll_get_thread_data()->gs = wine_get_gs();
+    wine_ldt_set_base( &fs_entry, teb );
+    wine_ldt_set_limit( &fs_entry, teb_size - 1 );
+    wine_ldt_set_flags( &fs_entry, WINE_LDT_FLAGS_DATA|WINE_LDT_FLAGS_32BIT );
+    wine_ldt_init_fs( thread_data->fs, &fs_entry );
+    thread_data->gs = wine_get_gs();
 }
 
 /**********************************************************************
@@ -1670,7 +1673,6 @@ void signal_init_process(void)
     if (sigaction( SIGUSR2, &sig_act, NULL ) == -1) goto error;
 #endif
 
-    signal_init_thread();
     return;
 
  error:
@@ -1775,6 +1777,11 @@ __ASM_GLOBAL_FUNC( DbgBreakPoint, "int $3; ret")
  */
 __ASM_GLOBAL_FUNC( DbgUserBreakPoint, "int $3; ret")
 
+/**********************************************************************
+ *           NtCurrentTeb   (NTDLL.@)
+ */
+__ASM_GLOBAL_FUNC( NtCurrentTeb, ".byte 0x64\n\tmovl 0x18,%eax\n\tret" )
+
 
 /**********************************************************************
  *		EXC_CallHandler   (internal)
diff --git a/dlls/ntdll/signal_powerpc.c b/dlls/ntdll/signal_powerpc.c
index c790f84..084c351 100644
--- a/dlls/ntdll/signal_powerpc.c
+++ b/dlls/ntdll/signal_powerpc.c
@@ -60,6 +60,7 @@
 
 WINE_DEFAULT_DEBUG_CHANNEL(seh);
 
+static pthread_key_t teb_key;
 
 /***********************************************************************
  * signal context platform-specific definitions
@@ -646,10 +647,19 @@ int CDECL __wine_set_signal_handler(unsigned int sig, wine_signal_handler wsh)
 /**********************************************************************
  *		signal_init_thread
  */
-void signal_init_thread(void)
+void signal_init_thread( TEB *teb )
 {
+    static int init_done;
+
+    if (!init_done)
+    {
+        pthread_key_create( &teb_key, NULL );
+        init_done = 1;
+    }
+    pthread_setspecific( teb_key, teb );
 }
 
+
 /**********************************************************************
  *		signal_init_process
  */
@@ -668,7 +678,6 @@ void signal_init_process(void)
 #ifdef SIGTRAP
     if (set_handler( SIGTRAP, (void (*)())trap_handler ) == -1) goto error;
 #endif
-    signal_init_thread();
     return;
 
  error:
@@ -701,4 +710,12 @@ void WINAPI DbgUserBreakPoint(void)
      kill(getpid(), SIGTRAP);
 }
 
+/**********************************************************************
+ *           NtCurrentTeb   (NTDLL.@)
+ */
+TEB * WINAPI NtCurrentTeb(void)
+{
+    return pthread_getspecific( teb_key );
+}
+
 #endif  /* __powerpc__ */
diff --git a/dlls/ntdll/signal_sparc.c b/dlls/ntdll/signal_sparc.c
index 54165ee..dddc183 100644
--- a/dlls/ntdll/signal_sparc.c
+++ b/dlls/ntdll/signal_sparc.c
@@ -44,6 +44,8 @@
 
 WINE_DEFAULT_DEBUG_CHANNEL(seh);
 
+static pthread_key_t teb_key;
+
 #define HANDLER_DEF(name) void name( int __signal, struct siginfo *__siginfo, ucontext_t *__context )
 #define HANDLER_CONTEXT (__context)
 
@@ -459,10 +461,19 @@ int CDECL __wine_set_signal_handler(unsigned int sig, wine_signal_handler wsh)
 /**********************************************************************
  *		signal_init_thread
  */
-void signal_init_thread(void)
+void signal_init_thread( TEB *teb )
 {
+    static int init_done;
+
+    if (!init_done)
+    {
+        pthread_key_create( &teb_key, NULL );
+        init_done = 1;
+    }
+    pthread_setspecific( teb_key, teb );
 }
 
+
 /**********************************************************************
  *		signal_init_process
  */
@@ -516,4 +527,12 @@ void WINAPI DbgUserBreakPoint(void)
      kill(getpid(), SIGTRAP);
 }
 
+/**********************************************************************
+ *           NtCurrentTeb   (NTDLL.@)
+ */
+TEB * WINAPI NtCurrentTeb(void)
+{
+    return pthread_getspecific( teb_key );
+}
+
 #endif  /* __sparc__ */
diff --git a/dlls/ntdll/signal_x86_64.c b/dlls/ntdll/signal_x86_64.c
index 4a57099..86f2f37 100644
--- a/dlls/ntdll/signal_x86_64.c
+++ b/dlls/ntdll/signal_x86_64.c
@@ -55,6 +55,9 @@ WINE_DEFAULT_DEBUG_CHANNEL(seh);
  */
 #ifdef linux
 
+#include <asm/prctl.h>
+extern int arch_prctl(int func, void *ptr);
+
 typedef struct ucontext SIGCONTEXT;
 
 # define HANDLER_DEF(name) void name( int __signal, struct siginfo *__siginfo, SIGCONTEXT *__context )
@@ -532,8 +535,13 @@ int CDECL __wine_set_signal_handler(unsigned int sig, wine_signal_handler wsh)
 /**********************************************************************
  *		signal_init_thread
  */
-void signal_init_thread(void)
+void signal_init_thread( TEB *teb )
 {
+#ifdef __linux__
+    arch_prctl( ARCH_SET_GS, teb );
+#else
+# error Please define setting %gs for your architecture
+#endif
 }
 
 /**********************************************************************
@@ -554,7 +562,6 @@ void signal_init_process(void)
 #ifdef SIGTRAP
     if (set_handler( SIGTRAP, (void (*)())trap_handler ) == -1) goto error;
 #endif
-    signal_init_thread();
     return;
 
  error:
diff --git a/dlls/ntdll/thread.c b/dlls/ntdll/thread.c
index f2806d9..7c66660 100644
--- a/dlls/ntdll/thread.c
+++ b/dlls/ntdll/thread.c
@@ -296,7 +296,7 @@ HANDLE thread_init(void)
     thread_info.teb_base   = teb;
     thread_info.teb_sel    = thread_data->fs;
     wine_pthread_get_functions( &pthread_functions, sizeof(pthread_functions) );
-    pthread_functions.init_current_teb( &thread_info );
+    signal_init_thread( teb );
     pthread_functions.init_thread( &thread_info );
     virtual_init_threading();
 
@@ -424,8 +424,7 @@ static void start_thread( struct wine_pthread_thread_info *info )
     debug_info.out_pos = debug_info.output;
     thread_data->debug_info = &debug_info;
 
-    pthread_functions.init_current_teb( info );
-    signal_init_thread();
+    signal_init_thread( teb );
     server_init_thread( func );
     pthread_functions.init_thread( info );
     virtual_alloc_thread_stack( info->stack_base, info->stack_size );
@@ -1471,30 +1470,3 @@ NTSTATUS WINAPI NtSetInformationThread( HANDLE handle, THREADINFOCLASS class,
         return STATUS_NOT_IMPLEMENTED;
     }
 }
-
-
-/**********************************************************************
- *           NtCurrentTeb   (NTDLL.@)
- */
-#if defined(__i386__) && defined(__GNUC__)
-
-__ASM_GLOBAL_FUNC( NtCurrentTeb, ".byte 0x64\n\tmovl 0x18,%eax\n\tret" )
-
-#elif defined(__i386__) && defined(_MSC_VER)
-
-/* Nothing needs to be done. MS C "magically" exports the inline version from winnt.h */
-
-#elif defined(__x86_64__) && defined(__GNUC__)
-
-/* not exported on x86_64 */
-
-#else
-
-/**********************************************************************/
-
-TEB * WINAPI NtCurrentTeb(void)
-{
-    return pthread_functions.get_current_teb();
-}
-
-#endif  /* __i386__ */




More information about the wine-cvs mailing list