Win64EH.h 4.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171
  1. //===-- llvm/Support/Win64EH.h ---Win64 EH Constants-------------*- C++ -*-===//
  2. //
  3. // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
  4. // See https://llvm.org/LICENSE.txt for license information.
  5. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
  6. //
  7. //===----------------------------------------------------------------------===//
  8. //
  9. // This file contains constants and structures used for implementing
  10. // exception handling on Win64 platforms. For more information, see
  11. // http://msdn.microsoft.com/en-us/library/1eyas8tf.aspx
  12. //
  13. //===----------------------------------------------------------------------===//
  14. #ifndef LLVM_SUPPORT_WIN64EH_H
  15. #define LLVM_SUPPORT_WIN64EH_H
  16. #include "llvm/Support/DataTypes.h"
  17. #include "llvm/Support/Endian.h"
  18. namespace llvm {
  19. namespace Win64EH {
  20. /// UnwindOpcodes - Enumeration whose values specify a single operation in
  21. /// the prolog of a function.
  22. enum UnwindOpcodes {
  23. UOP_PushNonVol = 0,
  24. UOP_AllocLarge,
  25. UOP_AllocSmall,
  26. UOP_SetFPReg,
  27. UOP_SaveNonVol,
  28. UOP_SaveNonVolBig,
  29. UOP_Epilog,
  30. UOP_SpareCode,
  31. UOP_SaveXMM128,
  32. UOP_SaveXMM128Big,
  33. UOP_PushMachFrame,
  34. // The following set of unwind opcodes is for ARM64. They are documented at
  35. // https://docs.microsoft.com/en-us/cpp/build/arm64-exception-handling
  36. UOP_AllocMedium,
  37. UOP_SaveR19R20X,
  38. UOP_SaveFPLRX,
  39. UOP_SaveFPLR,
  40. UOP_SaveReg,
  41. UOP_SaveRegX,
  42. UOP_SaveRegP,
  43. UOP_SaveRegPX,
  44. UOP_SaveLRPair,
  45. UOP_SaveFReg,
  46. UOP_SaveFRegX,
  47. UOP_SaveFRegP,
  48. UOP_SaveFRegPX,
  49. UOP_SetFP,
  50. UOP_AddFP,
  51. UOP_Nop,
  52. UOP_End,
  53. UOP_SaveNext,
  54. UOP_TrapFrame,
  55. UOP_Context,
  56. UOP_ClearUnwoundToCall
  57. };
  58. /// UnwindCode - This union describes a single operation in a function prolog,
  59. /// or part thereof.
  60. union UnwindCode {
  61. struct {
  62. uint8_t CodeOffset;
  63. uint8_t UnwindOpAndOpInfo;
  64. } u;
  65. support::ulittle16_t FrameOffset;
  66. uint8_t getUnwindOp() const {
  67. return u.UnwindOpAndOpInfo & 0x0F;
  68. }
  69. uint8_t getOpInfo() const {
  70. return (u.UnwindOpAndOpInfo >> 4) & 0x0F;
  71. }
  72. };
  73. enum {
  74. /// UNW_ExceptionHandler - Specifies that this function has an exception
  75. /// handler.
  76. UNW_ExceptionHandler = 0x01,
  77. /// UNW_TerminateHandler - Specifies that this function has a termination
  78. /// handler.
  79. UNW_TerminateHandler = 0x02,
  80. /// UNW_ChainInfo - Specifies that this UnwindInfo structure is chained to
  81. /// another one.
  82. UNW_ChainInfo = 0x04
  83. };
  84. /// RuntimeFunction - An entry in the table of functions with unwind info.
  85. struct RuntimeFunction {
  86. support::ulittle32_t StartAddress;
  87. support::ulittle32_t EndAddress;
  88. support::ulittle32_t UnwindInfoOffset;
  89. };
  90. /// UnwindInfo - An entry in the exception table.
  91. struct UnwindInfo {
  92. uint8_t VersionAndFlags;
  93. uint8_t PrologSize;
  94. uint8_t NumCodes;
  95. uint8_t FrameRegisterAndOffset;
  96. UnwindCode UnwindCodes[1];
  97. uint8_t getVersion() const {
  98. return VersionAndFlags & 0x07;
  99. }
  100. uint8_t getFlags() const {
  101. return (VersionAndFlags >> 3) & 0x1f;
  102. }
  103. uint8_t getFrameRegister() const {
  104. return FrameRegisterAndOffset & 0x0f;
  105. }
  106. uint8_t getFrameOffset() const {
  107. return (FrameRegisterAndOffset >> 4) & 0x0f;
  108. }
  109. // The data after unwindCodes depends on flags.
  110. // If UNW_ExceptionHandler or UNW_TerminateHandler is set then follows
  111. // the address of the language-specific exception handler.
  112. // If UNW_ChainInfo is set then follows a RuntimeFunction which defines
  113. // the chained unwind info.
  114. // For more information please see MSDN at:
  115. // http://msdn.microsoft.com/en-us/library/ddssxxy8.aspx
  116. /// Return pointer to language specific data part of UnwindInfo.
  117. void *getLanguageSpecificData() {
  118. return reinterpret_cast<void *>(&UnwindCodes[(NumCodes+1) & ~1]);
  119. }
  120. /// Return pointer to language specific data part of UnwindInfo.
  121. const void *getLanguageSpecificData() const {
  122. return reinterpret_cast<const void *>(&UnwindCodes[(NumCodes + 1) & ~1]);
  123. }
  124. /// Return image-relative offset of language-specific exception handler.
  125. uint32_t getLanguageSpecificHandlerOffset() const {
  126. return *reinterpret_cast<const support::ulittle32_t *>(
  127. getLanguageSpecificData());
  128. }
  129. /// Set image-relative offset of language-specific exception handler.
  130. void setLanguageSpecificHandlerOffset(uint32_t offset) {
  131. *reinterpret_cast<support::ulittle32_t *>(getLanguageSpecificData()) =
  132. offset;
  133. }
  134. /// Return pointer to exception-specific data.
  135. void *getExceptionData() {
  136. return reinterpret_cast<void *>(reinterpret_cast<uint32_t *>(
  137. getLanguageSpecificData())+1);
  138. }
  139. /// Return pointer to chained unwind info.
  140. RuntimeFunction *getChainedFunctionEntry() {
  141. return reinterpret_cast<RuntimeFunction *>(getLanguageSpecificData());
  142. }
  143. /// Return pointer to chained unwind info.
  144. const RuntimeFunction *getChainedFunctionEntry() const {
  145. return reinterpret_cast<const RuntimeFunction *>(getLanguageSpecificData());
  146. }
  147. };
  148. } // End of namespace Win64EH
  149. } // End of namespace llvm
  150. #endif