mapi32/tests: Fix typo.
[wine] / dlls / ntdll / signal_x86_64.c
1 /*
2  * x86-64 signal handling routines
3  *
4  * Copyright 1999, 2005 Alexandre Julliard
5  *
6  * This library is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Lesser General Public
8  * License as published by the Free Software Foundation; either
9  * version 2.1 of the License, or (at your option) any later version.
10  *
11  * This library is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14  * Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with this library; if not, write to the Free Software
18  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
19  */
20
21 #ifdef __x86_64__
22
23 #include "config.h"
24 #include "wine/port.h"
25
26 #include <assert.h>
27 #include <signal.h>
28 #include <stdlib.h>
29 #include <stdarg.h>
30 #include <stdio.h>
31 #ifdef HAVE_UNISTD_H
32 # include <unistd.h>
33 #endif
34
35 #ifdef HAVE_SYS_PARAM_H
36 # include <sys/param.h>
37 #endif
38 #ifdef HAVE_SYS_SIGNAL_H
39 # include <sys/signal.h>
40 #endif
41
42 #define NONAMELESSUNION
43 #include "windef.h"
44 #include "winternl.h"
45 #include "wine/library.h"
46 #include "wine/exception.h"
47 #include "ntdll_misc.h"
48 #include "wine/debug.h"
49
50 WINE_DEFAULT_DEBUG_CHANNEL(seh);
51
52
53 /***********************************************************************
54  * signal context platform-specific definitions
55  */
56 #ifdef linux
57
58 typedef struct ucontext SIGCONTEXT;
59
60 # define HANDLER_DEF(name) void name( int __signal, struct siginfo *__siginfo, SIGCONTEXT *__context )
61 # define HANDLER_CONTEXT (__context)
62
63 #define RAX_sig(context)     ((context)->uc_mcontext.gregs[REG_RAX])
64 #define RBX_sig(context)     ((context)->uc_mcontext.gregs[REG_RBX])
65 #define RCX_sig(context)     ((context)->uc_mcontext.gregs[REG_RCX])
66 #define RDX_sig(context)     ((context)->uc_mcontext.gregs[REG_RDX])
67 #define RSI_sig(context)     ((context)->uc_mcontext.gregs[REG_RSI])
68 #define RDI_sig(context)     ((context)->uc_mcontext.gregs[REG_RDI])
69 #define RBP_sig(context)     ((context)->uc_mcontext.gregs[REG_RBP])
70 #define R8_sig(context)      ((context)->uc_mcontext.gregs[REG_R8])
71 #define R9_sig(context)      ((context)->uc_mcontext.gregs[REG_R9])
72 #define R10_sig(context)     ((context)->uc_mcontext.gregs[REG_R10])
73 #define R11_sig(context)     ((context)->uc_mcontext.gregs[REG_R11])
74 #define R12_sig(context)     ((context)->uc_mcontext.gregs[REG_R12])
75 #define R13_sig(context)     ((context)->uc_mcontext.gregs[REG_R13])
76 #define R14_sig(context)     ((context)->uc_mcontext.gregs[REG_R14])
77 #define R15_sig(context)     ((context)->uc_mcontext.gregs[REG_R15])
78
79 #define CS_sig(context)      (*((WORD *)&(context)->uc_mcontext.gregs[REG_CSGSFS] + 0))
80 #define GS_sig(context)      (*((WORD *)&(context)->uc_mcontext.gregs[REG_CSGSFS] + 1))
81 #define FS_sig(context)      (*((WORD *)&(context)->uc_mcontext.gregs[REG_CSGSFS] + 2))
82
83 #define RSP_sig(context)     ((context)->uc_mcontext.gregs[REG_RSP])
84 #define RIP_sig(context)     ((context)->uc_mcontext.gregs[REG_RIP])
85 #define EFL_sig(context)     ((context)->uc_mcontext.gregs[REG_EFL])
86 #define TRAP_sig(context)    ((context)->uc_mcontext.gregs[REG_TRAPNO])
87 #define ERROR_sig(context)   ((context)->uc_mcontext.gregs[REG_ERR])
88
89 #define FPU_sig(context)     ((XMM_SAVE_AREA32 *)((context)->uc_mcontext.fpregs))
90
91 #define FAULT_CODE     (__siginfo->si_code)
92 #define FAULT_ADDRESS  (__siginfo->si_addr)
93
94 #endif /* linux */
95
96 #if defined(__NetBSD__)
97 # include <sys/ucontext.h>
98 # include <sys/types.h>
99 # include <signal.h>
100
101 typedef ucontext_t SIGCONTEXT;
102
103 #define RAX_sig(context)    ((context)->uc_mcontext.__gregs[_REG_RAX])
104 #define RBX_sig(context)    ((context)->uc_mcontext.__gregs[_REG_RBX])
105 #define RCX_sig(context)    ((context)->uc_mcontext.__gregs[_REG_RCX])
106 #define RDX_sig(context)    ((context)->uc_mcontext.__gregs[_REG_RDX])
107 #define RSI_sig(context)    ((context)->uc_mcontext.__gregs[_REG_RSI])
108 #define RDI_sig(context)    ((context)->uc_mcontext.__gregs[_REG_RDI])
109 #define RBP_sig(context)    ((context)->uc_mcontext.__gregs[_REG_RBP])
110 #define R8_sig(context)     ((context)->uc_mcontext.__gregs[_REG_R8])
111 #define R9_sig(context)     ((context)->uc_mcontext.__gregs[_REG_R9])
112 #define R10_sig(context)    ((context)->uc_mcontext.__gregs[_REG_R10])
113 #define R11_sig(context)    ((context)->uc_mcontext.__gregs[_REG_R11])
114 #define R12_sig(context)    ((context)->uc_mcontext.__gregs[_REG_R12])
115 #define R13_sig(context)    ((context)->uc_mcontext.__gregs[_REG_R13])
116 #define R14_sig(context)    ((context)->uc_mcontext.__gregs[_REG_R14])
117 #define R15_sig(context)    ((context)->uc_mcontext.__gregs[_REG_R15])
118
119 #define CS_sig(context)     ((context)->uc_mcontext.__gregs[_REG_CS])
120 #define DS_sig(context)     ((context)->uc_mcontext.__gregs[_REG_DS])
121 #define ES_sig(context)     ((context)->uc_mcontext.__gregs[_REG_ES])
122 #define FS_sig(context)     ((context)->uc_mcontext.__gregs[_REG_FS])
123 #define GS_sig(context)     ((context)->uc_mcontext.__gregs[_REG_GS])
124 #define SS_sig(context)     ((context)->uc_mcontext.__gregs[_REG_SS])
125
126 #define EFL_sig(context)    ((context)->uc_mcontext.__gregs[_REG_RFL])
127
128 #define RIP_sig(context)    (*((unsigned long*)&(context)->uc_mcontext.__gregs[_REG_RIP]))
129 #define RSP_sig(context)    (*((unsigned long*)&(context)->uc_mcontext.__gregs[_REG_URSP]))
130
131 #define TRAP_sig(context)   ((context)->uc_mcontext.__gregs[_REG_TRAPNO])
132 #define ERROR_sig(context)  ((context)->uc_mcontext.__gregs[_REG_ERR])
133
134 #define FAULT_CODE          (__siginfo->si_code)
135 #define FAULT_ADDRESS       (__siginfo->si_addr)
136
137 #define HANDLER_DEF(name) void name( int __signal, siginfo_t *__siginfo, SIGCONTEXT *__context )
138 #define HANDLER_CONTEXT (__context)
139
140 #define FPU_sig(context)   ((XMM_SAVE_AREA32 *)((context)->uc_mcontext.__fpregs))
141 #endif /* __NetBSD__ */
142
143 enum i386_trap_code
144 {
145     TRAP_x86_UNKNOWN    = -1,  /* Unknown fault (TRAP_sig not defined) */
146     TRAP_x86_DIVIDE     = 0,   /* Division by zero exception */
147     TRAP_x86_TRCTRAP    = 1,   /* Single-step exception */
148     TRAP_x86_NMI        = 2,   /* NMI interrupt */
149     TRAP_x86_BPTFLT     = 3,   /* Breakpoint exception */
150     TRAP_x86_OFLOW      = 4,   /* Overflow exception */
151     TRAP_x86_BOUND      = 5,   /* Bound range exception */
152     TRAP_x86_PRIVINFLT  = 6,   /* Invalid opcode exception */
153     TRAP_x86_DNA        = 7,   /* Device not available exception */
154     TRAP_x86_DOUBLEFLT  = 8,   /* Double fault exception */
155     TRAP_x86_FPOPFLT    = 9,   /* Coprocessor segment overrun */
156     TRAP_x86_TSSFLT     = 10,  /* Invalid TSS exception */
157     TRAP_x86_SEGNPFLT   = 11,  /* Segment not present exception */
158     TRAP_x86_STKFLT     = 12,  /* Stack fault */
159     TRAP_x86_PROTFLT    = 13,  /* General protection fault */
160     TRAP_x86_PAGEFLT    = 14,  /* Page fault */
161     TRAP_x86_ARITHTRAP  = 16,  /* Floating point exception */
162     TRAP_x86_ALIGNFLT   = 17,  /* Alignment check exception */
163     TRAP_x86_MCHK       = 18,  /* Machine check exception */
164     TRAP_x86_CACHEFLT   = 19   /* Cache flush exception */
165 };
166
167 typedef int (*wine_signal_handler)(unsigned int sig);
168
169 static wine_signal_handler handlers[256];
170
171 /***********************************************************************
172  *           dispatch_signal
173  */
174 static inline int dispatch_signal(unsigned int sig)
175 {
176     if (handlers[sig] == NULL) return 0;
177     return handlers[sig](sig);
178 }
179
180 /***********************************************************************
181  *           save_context
182  *
183  * Set the register values from a sigcontext.
184  */
185 static void save_context( CONTEXT *context, const SIGCONTEXT *sigcontext )
186 {
187     context->Rax    = RAX_sig(sigcontext);
188     context->Rcx    = RCX_sig(sigcontext);
189     context->Rdx    = RDX_sig(sigcontext);
190     context->Rbx    = RBX_sig(sigcontext);
191     context->Rsp    = RSP_sig(sigcontext);
192     context->Rbp    = RBP_sig(sigcontext);
193     context->Rsi    = RSI_sig(sigcontext);
194     context->Rdi    = RDI_sig(sigcontext);
195     context->R8     = R8_sig(sigcontext);
196     context->R9     = R9_sig(sigcontext);
197     context->R10    = R10_sig(sigcontext);
198     context->R11    = R11_sig(sigcontext);
199     context->R12    = R12_sig(sigcontext);
200     context->R13    = R13_sig(sigcontext);
201     context->R14    = R14_sig(sigcontext);
202     context->R15    = R15_sig(sigcontext);
203     context->Rip    = RIP_sig(sigcontext);
204     context->SegCs  = CS_sig(sigcontext);
205     context->SegFs  = FS_sig(sigcontext);
206     context->SegGs  = GS_sig(sigcontext);
207     context->EFlags = EFL_sig(sigcontext);
208     context->SegDs  = 0;  /* FIXME */
209     context->SegEs  = 0;  /* FIXME */
210     context->SegSs  = 0;  /* FIXME */
211     context->MxCsr  = 0;  /* FIXME */
212     if (FPU_sig(sigcontext)) context->u.FltSave = *FPU_sig(sigcontext);
213 }
214
215
216 /***********************************************************************
217  *           restore_context
218  *
219  * Build a sigcontext from the register values.
220  */
221 static void restore_context( const CONTEXT *context, SIGCONTEXT *sigcontext )
222 {
223     RAX_sig(sigcontext) = context->Rax;
224     RCX_sig(sigcontext) = context->Rcx;
225     RDX_sig(sigcontext) = context->Rdx;
226     RBX_sig(sigcontext) = context->Rbx;
227     RSP_sig(sigcontext) = context->Rsp;
228     RBP_sig(sigcontext) = context->Rbp;
229     RSI_sig(sigcontext) = context->Rsi;
230     RDI_sig(sigcontext) = context->Rdi;
231     R8_sig(sigcontext)  = context->R8;
232     R9_sig(sigcontext)  = context->R9;
233     R10_sig(sigcontext) = context->R10;
234     R11_sig(sigcontext) = context->R11;
235     R12_sig(sigcontext) = context->R12;
236     R13_sig(sigcontext) = context->R13;
237     R14_sig(sigcontext) = context->R14;
238     R15_sig(sigcontext) = context->R15;
239     RIP_sig(sigcontext) = context->Rip;
240     CS_sig(sigcontext)  = context->SegCs;
241     FS_sig(sigcontext)  = context->SegFs;
242     GS_sig(sigcontext)  = context->SegGs;
243     EFL_sig(sigcontext) = context->EFlags;
244     if (FPU_sig(sigcontext)) *FPU_sig(sigcontext) = context->u.FltSave;
245 }
246
247
248 /***********************************************************************
249  *              RtlCaptureContext (NTDLL.@)
250  */
251 void WINAPI __regs_RtlCaptureContext( CONTEXT *context, CONTEXT *regs )
252 {
253     *context = *regs;
254 }
255 DEFINE_REGS_ENTRYPOINT( RtlCaptureContext, 1 )
256
257
258 /***********************************************************************
259  *           set_cpu_context
260  *
261  * Set the new CPU context.
262  */
263 void set_cpu_context( const CONTEXT *context )
264 {
265     FIXME("not implemented\n");
266 }
267
268
269 /**********************************************************************
270  *              segv_handler
271  *
272  * Handler for SIGSEGV and related errors.
273  */
274 static HANDLER_DEF(segv_handler)
275 {
276     EXCEPTION_RECORD rec;
277     CONTEXT context;
278
279     save_context( &context, HANDLER_CONTEXT );
280
281     rec.ExceptionRecord  = NULL;
282     rec.ExceptionFlags   = EXCEPTION_CONTINUABLE;
283     rec.ExceptionAddress = (LPVOID)context.Rip;
284     rec.NumberParameters = 0;
285
286     switch(TRAP_sig(HANDLER_CONTEXT))
287     {
288     case TRAP_x86_OFLOW:   /* Overflow exception */
289         rec.ExceptionCode = EXCEPTION_INT_OVERFLOW;
290         break;
291     case TRAP_x86_BOUND:   /* Bound range exception */
292         rec.ExceptionCode = EXCEPTION_ARRAY_BOUNDS_EXCEEDED;
293         break;
294     case TRAP_x86_PRIVINFLT:   /* Invalid opcode exception */
295         rec.ExceptionCode = EXCEPTION_ILLEGAL_INSTRUCTION;
296         break;
297     case TRAP_x86_STKFLT:  /* Stack fault */
298         rec.ExceptionCode = EXCEPTION_STACK_OVERFLOW;
299         break;
300     case TRAP_x86_SEGNPFLT:  /* Segment not present exception */
301     case TRAP_x86_PROTFLT:   /* General protection fault */
302     case TRAP_x86_UNKNOWN:   /* Unknown fault code */
303         rec.ExceptionCode = ERROR_sig(HANDLER_CONTEXT) ? EXCEPTION_ACCESS_VIOLATION
304                                                        : EXCEPTION_PRIV_INSTRUCTION;
305         break;
306     case TRAP_x86_PAGEFLT:  /* Page fault */
307         rec.ExceptionCode = EXCEPTION_ACCESS_VIOLATION;
308 #ifdef FAULT_ADDRESS
309         rec.NumberParameters = 2;
310         rec.ExceptionInformation[0] = (ERROR_sig(HANDLER_CONTEXT) & 2) != 0;
311         rec.ExceptionInformation[1] = (ULONG_PTR)FAULT_ADDRESS;
312         if (!(rec.ExceptionCode = virtual_handle_fault( FAULT_ADDRESS, rec.ExceptionInformation[0] )))
313             goto done;
314 #endif
315         break;
316     case TRAP_x86_ALIGNFLT:  /* Alignment check exception */
317         rec.ExceptionCode = EXCEPTION_DATATYPE_MISALIGNMENT;
318         break;
319     default:
320         ERR( "Got unexpected trap %ld\n", TRAP_sig(HANDLER_CONTEXT) );
321         /* fall through */
322     case TRAP_x86_NMI:       /* NMI interrupt */
323     case TRAP_x86_DNA:       /* Device not available exception */
324     case TRAP_x86_DOUBLEFLT: /* Double fault exception */
325     case TRAP_x86_TSSFLT:    /* Invalid TSS exception */
326     case TRAP_x86_MCHK:      /* Machine check exception */
327     case TRAP_x86_CACHEFLT:  /* Cache flush exception */
328         rec.ExceptionCode = EXCEPTION_ILLEGAL_INSTRUCTION;
329         break;
330     }
331
332     __regs_RtlRaiseException( &rec, &context );
333 done:
334     restore_context( &context, HANDLER_CONTEXT );
335 }
336
337 /**********************************************************************
338  *              trap_handler
339  *
340  * Handler for SIGTRAP.
341  */
342 static HANDLER_DEF(trap_handler)
343 {
344     EXCEPTION_RECORD rec;
345     CONTEXT context;
346
347     save_context( &context, HANDLER_CONTEXT );
348     rec.ExceptionFlags   = EXCEPTION_CONTINUABLE;
349     rec.ExceptionRecord  = NULL;
350     rec.ExceptionAddress = (LPVOID)context.Rip;
351     rec.NumberParameters = 0;
352
353     switch(FAULT_CODE)
354     {
355     case TRAP_TRACE:  /* Single-step exception */
356         rec.ExceptionCode = EXCEPTION_SINGLE_STEP;
357         EFL_sig(HANDLER_CONTEXT) &= ~0x100;  /* clear single-step flag */
358         break;
359     case TRAP_BRKPT:   /* Breakpoint exception */
360         rec.ExceptionAddress = (char *)rec.ExceptionAddress - 1;  /* back up over the int3 instruction */
361         /* fall through */
362     default:
363         rec.ExceptionCode = EXCEPTION_BREAKPOINT;
364         break;
365     }
366
367     __regs_RtlRaiseException( &rec, &context );
368     restore_context( &context, HANDLER_CONTEXT );
369 }
370
371 /**********************************************************************
372  *              fpe_handler
373  *
374  * Handler for SIGFPE.
375  */
376 static HANDLER_DEF(fpe_handler)
377 {
378     EXCEPTION_RECORD rec;
379     CONTEXT context;
380
381     save_context( &context, HANDLER_CONTEXT );
382     rec.ExceptionFlags   = EXCEPTION_CONTINUABLE;
383     rec.ExceptionRecord  = NULL;
384     rec.ExceptionAddress = (LPVOID)context.Rip;
385     rec.NumberParameters = 0;
386
387     switch (FAULT_CODE)
388     {
389     case FPE_FLTSUB:
390         rec.ExceptionCode = EXCEPTION_ARRAY_BOUNDS_EXCEEDED;
391         break;
392     case FPE_INTDIV:
393         rec.ExceptionCode = EXCEPTION_INT_DIVIDE_BY_ZERO;
394         break;
395     case FPE_INTOVF:
396         rec.ExceptionCode = EXCEPTION_INT_OVERFLOW;
397         break;
398     case FPE_FLTDIV:
399         rec.ExceptionCode = EXCEPTION_FLT_DIVIDE_BY_ZERO;
400         break;
401     case FPE_FLTOVF:
402         rec.ExceptionCode = EXCEPTION_FLT_OVERFLOW;
403         break;
404     case FPE_FLTUND:
405         rec.ExceptionCode = EXCEPTION_FLT_UNDERFLOW;
406         break;
407     case FPE_FLTRES:
408         rec.ExceptionCode = EXCEPTION_FLT_INEXACT_RESULT;
409         break;
410     case FPE_FLTINV:
411     default:
412         rec.ExceptionCode = EXCEPTION_FLT_INVALID_OPERATION;
413         break;
414     }
415
416     __regs_RtlRaiseException( &rec, &context );
417     restore_context( &context, HANDLER_CONTEXT );
418 }
419
420 /**********************************************************************
421  *              int_handler
422  *
423  * Handler for SIGINT.
424  */
425 static HANDLER_DEF(int_handler)
426 {
427     if (!dispatch_signal(SIGINT))
428     {
429         EXCEPTION_RECORD rec;
430         CONTEXT context;
431
432         save_context( &context, HANDLER_CONTEXT );
433         rec.ExceptionCode    = CONTROL_C_EXIT;
434         rec.ExceptionFlags   = EXCEPTION_CONTINUABLE;
435         rec.ExceptionRecord  = NULL;
436         rec.ExceptionAddress = (LPVOID)context.Rip;
437         rec.NumberParameters = 0;
438         __regs_RtlRaiseException( &rec, &context );
439         restore_context( &context, HANDLER_CONTEXT );
440     }
441 }
442
443
444 /**********************************************************************
445  *              abrt_handler
446  *
447  * Handler for SIGABRT.
448  */
449 static HANDLER_DEF(abrt_handler)
450 {
451     EXCEPTION_RECORD rec;
452     CONTEXT context;
453
454     save_context( &context, HANDLER_CONTEXT );
455     rec.ExceptionCode    = EXCEPTION_WINE_ASSERTION;
456     rec.ExceptionFlags   = EH_NONCONTINUABLE;
457     rec.ExceptionRecord  = NULL;
458     rec.ExceptionAddress = (LPVOID)context.Rip;
459     rec.NumberParameters = 0;
460     __regs_RtlRaiseException( &rec, &context ); /* Should never return.. */
461     restore_context( &context, HANDLER_CONTEXT );
462 }
463
464
465 /**********************************************************************
466  *              quit_handler
467  *
468  * Handler for SIGQUIT.
469  */
470 static HANDLER_DEF(quit_handler)
471 {
472     server_abort_thread(0);
473 }
474
475
476 /**********************************************************************
477  *              usr1_handler
478  *
479  * Handler for SIGUSR1, used to signal a thread that it got suspended.
480  */
481 static HANDLER_DEF(usr1_handler)
482 {
483     CONTEXT context;
484
485     save_context( &context, HANDLER_CONTEXT );
486     wait_suspend( &context );
487     restore_context( &context, HANDLER_CONTEXT );
488 }
489
490
491 /**********************************************************************
492  *              get_signal_stack_total_size
493  *
494  * Retrieve the size to allocate for the signal stack, including the TEB at the bottom.
495  * Must be a power of two.
496  */
497 size_t get_signal_stack_total_size(void)
498 {
499     assert( sizeof(TEB) <= 2*getpagesize() );
500     return 2*getpagesize();  /* this is just for the TEB, we don't need a signal stack */
501 }
502
503
504 /***********************************************************************
505  *           set_handler
506  *
507  * Set a signal handler
508  */
509 static int set_handler( int sig, void (*func)() )
510 {
511     struct sigaction sig_act;
512
513     sig_act.sa_sigaction = func;
514     sig_act.sa_mask = server_block_set;
515     sig_act.sa_flags = SA_RESTART | SA_SIGINFO | SA_ONSTACK;
516     return sigaction( sig, &sig_act, NULL );
517 }
518
519
520 /***********************************************************************
521  *           __wine_set_signal_handler   (NTDLL.@)
522  */
523 int CDECL __wine_set_signal_handler(unsigned int sig, wine_signal_handler wsh)
524 {
525     if (sig > sizeof(handlers) / sizeof(handlers[0])) return -1;
526     if (handlers[sig] != NULL) return -2;
527     handlers[sig] = wsh;
528     return 0;
529 }
530
531
532 /**********************************************************************
533  *              signal_init_thread
534  */
535 void signal_init_thread(void)
536 {
537 }
538
539 /**********************************************************************
540  *              signal_init_process
541  */
542 void signal_init_process(void)
543 {
544     if (set_handler( SIGINT,  (void (*)())int_handler ) == -1) goto error;
545     if (set_handler( SIGFPE,  (void (*)())fpe_handler ) == -1) goto error;
546     if (set_handler( SIGSEGV, (void (*)())segv_handler ) == -1) goto error;
547     if (set_handler( SIGILL,  (void (*)())segv_handler ) == -1) goto error;
548     if (set_handler( SIGABRT, (void (*)())abrt_handler ) == -1) goto error;
549     if (set_handler( SIGQUIT, (void (*)())quit_handler ) == -1) goto error;
550     if (set_handler( SIGUSR1, (void (*)())usr1_handler ) == -1) goto error;
551 #ifdef SIGBUS
552     if (set_handler( SIGBUS,  (void (*)())segv_handler ) == -1) goto error;
553 #endif
554 #ifdef SIGTRAP
555     if (set_handler( SIGTRAP, (void (*)())trap_handler ) == -1) goto error;
556 #endif
557     signal_init_thread();
558     return;
559
560  error:
561     perror("sigaction");
562     exit(1);
563 }
564
565
566 /**********************************************************************
567  *              RtlLookupFunctionEntry   (NTDLL.@)
568  */
569 PRUNTIME_FUNCTION WINAPI RtlLookupFunctionEntry( ULONG64 pc, ULONG64 *base,
570                                                  UNWIND_HISTORY_TABLE *table )
571 {
572     FIXME("stub\n");
573     return NULL;
574 }
575
576
577 /**********************************************************************
578  *              RtlVirtualUnwind   (NTDLL.@)
579  */
580 PVOID WINAPI RtlVirtualUnwind ( ULONG type, ULONG64 base, ULONG64 pc,
581                                 RUNTIME_FUNCTION *function, CONTEXT *context,
582                                 PVOID *data, ULONG64 *frame,
583                                 KNONVOLATILE_CONTEXT_POINTERS *ctx_ptr )
584 {
585     FIXME("stub\n");
586     return NULL;
587 }
588
589
590 /**********************************************************************
591  *              __wine_enter_vm86   (NTDLL.@)
592  */
593 void __wine_enter_vm86( CONTEXT *context )
594 {
595     MESSAGE("vm86 mode not supported on this platform\n");
596 }
597
598 /**********************************************************************
599  *              DbgBreakPoint   (NTDLL.@)
600  */
601 __ASM_GLOBAL_FUNC( DbgBreakPoint, "int $3; ret")
602
603 /**********************************************************************
604  *              DbgUserBreakPoint   (NTDLL.@)
605  */
606 __ASM_GLOBAL_FUNC( DbgUserBreakPoint, "int $3; ret")
607
608 #endif  /* __x86_64__ */