sighnd.inc 2.7 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394
  1. {
  2. $Id$
  3. This file is part of the Free Pascal run time library.
  4. Copyright (c) 1999-2000 by Michael Van Canneyt,
  5. member of the Free Pascal development team.
  6. Signal handler is arch dependant due to processor to language
  7. exception conversion.
  8. See the file COPYING.FPC, included in this distribution,
  9. for details about the copyright.
  10. This program is distributed in the hope that it will be useful,
  11. but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
  13. **********************************************************************}
  14. const
  15. FPU_All = $7f;
  16. function GetFPUState(const SigContext : TSigContext) : longint;
  17. begin
  18. if assigned(SigContext.fpstate) then
  19. GetfpuState:=SigContext.fpstate^.sw;
  20. {$ifdef SYSTEM_DEBUG}
  21. writeln('xx:',sigcontext.en_tw,' ',sigcontext.en_cw);
  22. {$endif SYSTEM_DEBUG}
  23. {$ifdef SYSTEM_DEBUG}
  24. Writeln(stderr,'FpuState = ',GetFpuState);
  25. {$endif SYSTEM_DEBUG}
  26. end;
  27. procedure SignalToRunerror(sig : longint; SigInfo: PSigInfo; SigContext: PSigContext);cdecl;
  28. var
  29. res,fpustate : word;
  30. begin
  31. res:=0;
  32. case sig of
  33. SIGFPE :
  34. begin
  35. { this is not allways necessary but I don't know yet
  36. how to tell if it is or not PM }
  37. res:=200;
  38. fpustate:=GetFPUState(SigContext^);
  39. if (FpuState and FPU_All) <> 0 then
  40. begin
  41. { first check the more precise options }
  42. if (FpuState and FPU_DivisionByZero)<>0 then
  43. res:=200
  44. else if (FpuState and FPU_Overflow)<>0 then
  45. res:=205
  46. else if (FpuState and FPU_Underflow)<>0 then
  47. res:=206
  48. else if (FpuState and FPU_Denormal)<>0 then
  49. res:=216
  50. else if (FpuState and (FPU_StackOverflow or FPU_StackUnderflow or FPU_Invalid))<>0 Then
  51. res:=207
  52. else
  53. res:=207; {'Coprocessor Error'}
  54. end;
  55. sysResetFPU;
  56. end;
  57. SIGILL,
  58. SIGBUS,
  59. SIGSEGV :
  60. res:=216;
  61. end;
  62. { give runtime error at the position where the signal was raised }
  63. if res<>0 then
  64. HandleErrorAddrFrame(res,pointer(SigContext^.eip),pointer(SigContext^.ebp));
  65. end;
  66. {
  67. $Log$
  68. Revision 1.5 2005-01-30 18:01:15 peter
  69. * signal cleanup for linux
  70. * sigactionhandler instead of tsigaction for bsds
  71. * sigcontext moved to cpu dir
  72. Revision 1.4 2004/08/08 09:36:09 florian
  73. * fixed runerror for invalid operation
  74. Revision 1.3 2004/02/05 01:16:12 florian
  75. + completed x86-64/linux system unit
  76. Revision 1.2 2003/11/01 01:58:11 marco
  77. * more small fixes.
  78. Revision 1.1 2003/11/01 01:27:20 marco
  79. * initial version from 1.0.x branch
  80. }