14#define DEBUG_TYPE "orc"
19template <
typename ORCABI>
23 constexpr unsigned MaxDisp = ORCABI::StubToPointerMaxDisplacement;
25 ExecutorAddr LastStub = FirstStub + ((NumStubs - 1) * ORCABI::StubSize);
27 ExecutorAddr LastPointer = FirstPointer + ((NumStubs - 1) * ORCABI::StubSize);
29 if (FirstStub < FirstPointer) {
30 if (LastStub >= FirstPointer)
32 return (FirstPointer - FirstStub <= MaxDisp) &&
33 (LastPointer - LastStub <= MaxDisp);
36 if (LastPointer >= FirstStub)
39 return (FirstStub - FirstPointer <= MaxDisp) &&
40 (LastStub - LastPointer <= MaxDisp);
127 const unsigned ReentryFnAddrOffset = 0x110;
128 const unsigned ReentryCtxAddrOffset = 0x118;
130 memcpy(ResolverWorkingMem, ResolverCode,
sizeof(ResolverCode));
131 memcpy(ResolverWorkingMem + ReentryFnAddrOffset, &ReentryFnAddr,
133 memcpy(ResolverWorkingMem + ReentryCtxAddrOffset, &ReentryCtxAddr,
140 unsigned NumTrampolines) {
144 memcpy(TrampolineBlockWorkingMem + OffsetToPtr, &ResolverAddr,
152 reinterpret_cast<uint32_t *
>(TrampolineBlockWorkingMem);
155 Trampolines[3 *
I + 0] = 0xaa1e03f1;
156 Trampolines[3 *
I + 1] = 0x58000010 | (OffsetToPtr << 3);
157 Trampolines[3 *
I + 2] = 0xd63f0200;
162 char *StubsBlockWorkingMem,
ExecutorAddr StubsBlockTargetAddress,
163 ExecutorAddr PointersBlockTargetAddress,
unsigned NumStubs) {
185 "Pointer and stub size must match for algorithm below");
186 assert(stubAndPointerRangesOk<OrcAArch64>(
187 StubsBlockTargetAddress, PointersBlockTargetAddress, NumStubs) &&
188 "PointersBlock is out of range");
190 PointersBlockTargetAddress - StubsBlockTargetAddress;
191 assert((PtrDisplacement % 8 == 0) &&
192 "Displacement to pointer is not a multiple of 8");
194 uint64_t PtrOffsetField = ((PtrDisplacement >> 2) & 0x7ffff) << 5;
196 for (
unsigned I = 0;
I < NumStubs; ++
I)
197 Stub[
I] = 0xd61f020058000010 | PtrOffsetField;
203 unsigned NumTrampolines) {
207 memcpy(TrampolineBlockWorkingMem + OffsetToPtr, &ResolverAddr,
211 reinterpret_cast<uint64_t *
>(TrampolineBlockWorkingMem);
212 uint64_t CallIndirPCRel = 0xf1c40000000015ff;
215 Trampolines[
I] = CallIndirPCRel | ((OffsetToPtr - 6) << 16);
219 char *StubsBlockWorkingMem,
ExecutorAddr StubsBlockTargetAddress,
220 ExecutorAddr PointersBlockTargetAddress,
unsigned NumStubs) {
243 "Pointer and stub size must match for algorithm below");
244 assert(stubAndPointerRangesOk<OrcX86_64_Base>(
245 StubsBlockTargetAddress, PointersBlockTargetAddress, NumStubs) &&
246 "PointersBlock is out of range");
249 (PointersBlockTargetAddress - StubsBlockTargetAddress - 6) << 16;
250 for (
unsigned I = 0;
I < NumStubs; ++
I)
251 Stub[
I] = 0xF1C40000000025ff | PtrOffsetField;
260 dbgs() <<
"Writing resolver code to "
261 <<
formatv(
"{0:x16}", ResolverTargetAddress) <<
"\n";
264 const uint8_t ResolverCode[] = {
282 0x48, 0x81, 0xec, 0x08, 0x02, 0x00, 0x00,
283 0x48, 0x0f, 0xae, 0x04, 0x24,
287 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
289 0x48, 0x8b, 0x75, 0x08,
290 0x48, 0x83, 0xee, 0x06,
294 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
297 0x48, 0x89, 0x45, 0x08,
298 0x48, 0x0f, 0xae, 0x0c, 0x24,
299 0x48, 0x81, 0xc4, 0x08, 0x02, 0x00, 0x00,
318 const unsigned ReentryFnAddrOffset = 0x3a;
319 const unsigned ReentryCtxAddrOffset = 0x28;
321 memcpy(ResolverWorkingMem, ResolverCode,
sizeof(ResolverCode));
322 memcpy(ResolverWorkingMem + ReentryFnAddrOffset, &ReentryFnAddr,
324 memcpy(ResolverWorkingMem + ReentryCtxAddrOffset, &ReentryCtxAddr,
336 const uint8_t ResolverCode[] = {
354 0x48, 0x81, 0xec, 0x08, 0x02, 0x00, 0x00,
355 0x48, 0x0f, 0xae, 0x04, 0x24,
359 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
361 0x48, 0x8B, 0x55, 0x08,
362 0x48, 0x83, 0xea, 0x06,
366 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
369 0x48, 0x83, 0xEC, 0x20,
373 0x48, 0x83, 0xC4, 0x20,
375 0x48, 0x89, 0x45, 0x08,
376 0x48, 0x0f, 0xae, 0x0c, 0x24,
377 0x48, 0x81, 0xc4, 0x08, 0x02, 0x00, 0x00,
396 const unsigned ReentryFnAddrOffset = 0x3a;
397 const unsigned ReentryCtxAddrOffset = 0x28;
399 memcpy(ResolverWorkingMem, ResolverCode,
sizeof(ResolverCode));
400 memcpy(ResolverWorkingMem + ReentryFnAddrOffset, &ReentryFnAddr,
402 memcpy(ResolverWorkingMem + ReentryCtxAddrOffset, &ReentryCtxAddr,
411 assert((ReentryFnAddr.
getValue() >> 32) == 0 &&
"ReentryFnAddr out of range");
413 "ReentryCtxAddr out of range");
415 const uint8_t ResolverCode[] = {
427 0x81, 0xec, 0x18, 0x02, 0x00, 0x00,
428 0x0f, 0xae, 0x44, 0x24, 0x10,
431 0x89, 0x74, 0x24, 0x04,
432 0xc7, 0x04, 0x24, 0x00, 0x00, 0x00,
434 0xb8, 0x00, 0x00, 0x00, 0x00,
437 0x0f, 0xae, 0x4c, 0x24, 0x10,
438 0x81, 0xc4, 0x18, 0x02, 0x00, 0x00,
450 const unsigned ReentryFnAddrOffset = 0x2a;
451 const unsigned ReentryCtxAddrOffset = 0x25;
453 memcpy(ResolverWorkingMem, ResolverCode,
sizeof(ResolverCode));
454 memcpy(ResolverWorkingMem + ReentryFnAddrOffset, &ReentryFnAddr,
456 memcpy(ResolverWorkingMem + ReentryCtxAddrOffset, &ReentryCtxAddr,
463 unsigned NumTrampolines) {
464 assert((ResolverAddr.
getValue() >> 32) == 0 &&
"ResolverAddr out of range");
466 uint64_t CallRelImm = 0xF1C4C400000000e8;
467 uint64_t ResolverRel = ResolverAddr - TrampolineBlockTargetAddress - 5;
471 Trampolines[
I] = CallRelImm | (ResolverRel << 8);
479 "StubsBlockTargetAddress is out of range");
481 "PointersBlockTargetAddress is out of range");
503 assert(stubAndPointerRangesOk<OrcI386>(
504 StubsBlockTargetAddress, PointersBlockTargetAddress, NumStubs) &&
505 "PointersBlock is out of range");
509 for (
unsigned I = 0;
I < NumStubs; ++
I, PtrAddr += 4)
510 Stub[
I] = 0xF1C40000000025ff | (PtrAddr << 16);
592 const unsigned ReentryFnAddrOffset = 0x7c;
593 const unsigned ReentryCtxAddrOffset = 0x6c;
594 const unsigned Offsett = 0xf8;
596 memcpy(ResolverWorkingMem, ResolverCode,
sizeof(ResolverCode));
600 memcpy(ResolverWorkingMem + Offsett, &MoveVxT9,
sizeof(MoveVxT9));
603 0x3c040000 | (((ReentryCtxAddr.
getValue() + 0x8000) >> 16) & 0xFFFF);
604 uint32_t ReentryCtxADDiu = 0x24840000 | (ReentryCtxAddr.
getValue() & 0xFFFF);
605 memcpy(ResolverWorkingMem + ReentryCtxAddrOffset, &ReentryCtxLUi,
606 sizeof(ReentryCtxLUi));
607 memcpy(ResolverWorkingMem + ReentryCtxAddrOffset + 4, &ReentryCtxADDiu,
608 sizeof(ReentryCtxADDiu));
611 0x3c190000 | (((ReentryFnAddr.
getValue() + 0x8000) >> 16) & 0xFFFF);
613 memcpy(ResolverWorkingMem + ReentryFnAddrOffset, &ReentryFnLUi,
614 sizeof(ReentryFnLUi));
615 memcpy(ResolverWorkingMem + ReentryFnAddrOffset + 4, &ReentryFnADDiu,
616 sizeof(ReentryFnADDiu));
622 unsigned NumTrampolines) {
624 assert((ResolverAddr.
getValue() >> 32) == 0 &&
"ResolverAddr out of range");
627 reinterpret_cast<uint32_t *
>(TrampolineBlockWorkingMem);
630 for (
unsigned I = 0;
I < NumTrampolines; ++
I) {
636 Trampolines[5 *
I + 0] = 0x03e0c025;
637 Trampolines[5 *
I + 1] = 0x3c190000 | (RHiAddr & 0xFFFF);
638 Trampolines[5 *
I + 2] = 0x27390000 | (ResolverAddr.
getValue() & 0xFFFF);
639 Trampolines[5 *
I + 3] = 0x0320f809;
640 Trampolines[5 *
I + 4] = 0x00000000;
645 char *StubsBlockWorkingMem,
ExecutorAddr StubsBlockTargetAddress,
646 ExecutorAddr PointersBlockTargetAddress,
unsigned NumStubs) {
648 "InitialPtrVal is out of range");
672 assert(stubAndPointerRangesOk<OrcMips32_Base>(
673 StubsBlockTargetAddress, PointersBlockTargetAddress, NumStubs) &&
674 "PointersBlock is out of range");
680 for (
unsigned I = 0;
I < NumStubs; ++
I) {
681 uint32_t HiAddr = ((PtrAddr + 0x8000) >> 16);
682 Stub[4 *
I + 0] = 0x3c190000 | (HiAddr & 0xFFFF);
683 Stub[4 *
I + 1] = 0x8f390000 | (PtrAddr & 0xFFFF);
684 Stub[4 *
I + 2] = 0x03200008;
685 Stub[4 *
I + 3] = 0x00000000;
776 const unsigned ReentryFnAddrOffset = 0x8c;
777 const unsigned ReentryCtxAddrOffset = 0x6c;
779 memcpy(ResolverWorkingMem, ResolverCode,
sizeof(ResolverCode));
783 (((ReentryCtxAddr.
getValue() + 0x800080008000) >> 48) & 0xFFFF);
785 0x64840000 | (((ReentryCtxAddr.
getValue() + 0x80008000) >> 32) & 0xFFFF);
786 uint32_t ReentryCtxDSLL = 0x00042438;
788 0x64840000 | ((((ReentryCtxAddr.
getValue() + 0x8000) >> 16) & 0xFFFF));
789 uint32_t ReentryCtxDSLL2 = 0x00042438;
791 0x64840000 | (ReentryCtxAddr.
getValue() & 0xFFFF);
793 memcpy(ResolverWorkingMem + ReentryCtxAddrOffset, &ReentryCtxLUi,
794 sizeof(ReentryCtxLUi));
795 memcpy(ResolverWorkingMem + (ReentryCtxAddrOffset + 4), &ReentryCtxDADDiu,
796 sizeof(ReentryCtxDADDiu));
797 memcpy(ResolverWorkingMem + (ReentryCtxAddrOffset + 8), &ReentryCtxDSLL,
798 sizeof(ReentryCtxDSLL));
799 memcpy(ResolverWorkingMem + (ReentryCtxAddrOffset + 12), &ReentryCtxDADDiu2,
800 sizeof(ReentryCtxDADDiu2));
801 memcpy(ResolverWorkingMem + (ReentryCtxAddrOffset + 16), &ReentryCtxDSLL2,
802 sizeof(ReentryCtxDSLL2));
803 memcpy(ResolverWorkingMem + (ReentryCtxAddrOffset + 20), &ReentryCtxDADDiu3,
804 sizeof(ReentryCtxDADDiu3));
808 (((ReentryFnAddr.
getValue() + 0x800080008000) >> 48) & 0xFFFF);
811 0x67390000 | (((ReentryFnAddr.
getValue() + 0x80008000) >> 32) & 0xFFFF);
813 uint32_t ReentryFnDSLL = 0x0019cc38;
816 0x67390000 | (((ReentryFnAddr.
getValue() + 0x8000) >> 16) & 0xFFFF);
818 uint32_t ReentryFnDSLL2 = 0x0019cc38;
820 uint32_t ReentryFnDADDiu3 = 0x67390000 | (ReentryFnAddr.
getValue() & 0xFFFF);
822 memcpy(ResolverWorkingMem + ReentryFnAddrOffset, &ReentryFnLUi,
823 sizeof(ReentryFnLUi));
824 memcpy(ResolverWorkingMem + (ReentryFnAddrOffset + 4), &ReentryFnDADDiu,
825 sizeof(ReentryFnDADDiu));
826 memcpy(ResolverWorkingMem + (ReentryFnAddrOffset + 8), &ReentryFnDSLL,
827 sizeof(ReentryFnDSLL));
828 memcpy(ResolverWorkingMem + (ReentryFnAddrOffset + 12), &ReentryFnDADDiu2,
829 sizeof(ReentryFnDADDiu2));
830 memcpy(ResolverWorkingMem + (ReentryFnAddrOffset + 16), &ReentryFnDSLL2,
831 sizeof(ReentryFnDSLL2));
832 memcpy(ResolverWorkingMem + (ReentryFnAddrOffset + 20), &ReentryFnDADDiu3,
833 sizeof(ReentryFnDADDiu3));
839 unsigned NumTrampolines) {
842 reinterpret_cast<uint32_t *
>(TrampolineBlockWorkingMem);
848 for (
unsigned I = 0;
I < NumTrampolines; ++
I) {
849 Trampolines[10 *
I + 0] = 0x03e0c025;
850 Trampolines[10 *
I + 1] = 0x3c190000 | (HeighestAddr & 0xFFFF);
851 Trampolines[10 *
I + 2] = 0x67390000 | (HeigherAddr & 0xFFFF);
852 Trampolines[10 *
I + 3] = 0x0019cc38;
853 Trampolines[10 *
I + 4] = 0x67390000 | (HiAddr & 0xFFFF);
854 Trampolines[10 *
I + 5] = 0x0019cc38;
855 Trampolines[10 *
I + 6] = 0x67390000 | (ResolverAddr.
getValue() &
857 Trampolines[10 *
I + 7] = 0x0320f809;
858 Trampolines[10 *
I + 8] = 0x00000000;
859 Trampolines[10 *
I + 9] = 0x00000000;
895 assert(stubAndPointerRangesOk<OrcMips64>(
896 StubsBlockTargetAddress, PointersBlockTargetAddress, NumStubs) &&
897 "PointersBlock is out of range");
903 for (
unsigned I = 0;
I < NumStubs; ++
I, PtrAddr += 8) {
904 uint64_t HeighestAddr = ((PtrAddr + 0x800080008000) >> 48);
905 uint64_t HeigherAddr = ((PtrAddr + 0x80008000) >> 32);
906 uint64_t HiAddr = ((PtrAddr + 0x8000) >> 16);
907 Stub[8 *
I + 0] = 0x3c190000 | (HeighestAddr & 0xFFFF);
908 Stub[8 *
I + 1] = 0x67390000 | (HeigherAddr & 0xFFFF);
909 Stub[8 *
I + 2] = 0x0019cc38;
910 Stub[8 *
I + 3] = 0x67390000 | (HiAddr & 0xFFFF);
911 Stub[8 *
I + 4] = 0x0019cc38;
912 Stub[8 *
I + 5] = 0xdf390000 | (PtrAddr & 0xFFFF);
913 Stub[8 *
I + 6] = 0x03200008;
914 Stub[8 *
I + 7] = 0x00000000;
1008 const unsigned ReentryCtxAddrOffset = 0x138;
1009 const unsigned ReentryFnAddrOffset = 0x140;
1011 memcpy(ResolverWorkingMem, ResolverCode,
sizeof(ResolverCode));
1012 memcpy(ResolverWorkingMem + ReentryFnAddrOffset, &ReentryFnAddr,
1014 memcpy(ResolverWorkingMem + ReentryCtxAddrOffset, &ReentryCtxAddr,
1021 unsigned NumTrampolines) {
1025 memcpy(TrampolineBlockWorkingMem + OffsetToPtr, &ResolverAddr,
1029 reinterpret_cast<uint32_t *
>(TrampolineBlockWorkingMem);
1031 uint32_t Hi20 = (OffsetToPtr + 0x800) & 0xFFFFF000;
1032 uint32_t Lo12 = OffsetToPtr - Hi20;
1033 Trampolines[4 *
I + 0] = 0x00000297 | Hi20;
1034 Trampolines[4 *
I + 1] =
1035 0x0002b283 | ((Lo12 & 0xFFF) << 20);
1036 Trampolines[4 *
I + 2] = 0x00028367;
1037 Trampolines[4 *
I + 3] = 0xdeadface;
1042 char *StubsBlockWorkingMem,
ExecutorAddr StubsBlockTargetAddress,
1043 ExecutorAddr PointersBlockTargetAddress,
unsigned NumStubs) {
1068 assert(stubAndPointerRangesOk<OrcRiscv64>(
1069 StubsBlockTargetAddress, PointersBlockTargetAddress, NumStubs) &&
1070 "PointersBlock is out of range");
1074 for (
unsigned I = 0;
I < NumStubs; ++
I) {
1076 PointersBlockTargetAddress - StubsBlockTargetAddress;
1077 uint32_t Hi20 = (PtrDisplacement + 0x800) & 0xFFFFF000;
1078 uint32_t Lo12 = PtrDisplacement - Hi20;
1079 Stub[4 *
I + 0] = 0x00000297 | Hi20;
1080 Stub[4 *
I + 1] = 0x0002b283 | ((Lo12 & 0xFFF) << 20);
1081 Stub[4 *
I + 2] = 0x00028067;
1082 Stub[4 *
I + 3] = 0xfeedbeef;
1084 StubsBlockTargetAddress +=
StubSize;
1094 dbgs() <<
"Writing resolver code to "
1095 <<
formatv(
"{0:x16}", ResolverTargetAddress) <<
"\n";
1151 const unsigned ReentryCtxAddrOffset = 0xb8;
1152 const unsigned ReentryFnAddrOffset = 0xc0;
1154 memcpy(ResolverWorkingMem, ResolverCode,
sizeof(ResolverCode));
1155 memcpy(ResolverWorkingMem + ReentryFnAddrOffset, &ReentryFnAddr,
1157 memcpy(ResolverWorkingMem + ReentryCtxAddrOffset, &ReentryCtxAddr,
1164 unsigned NumTrampolines) {
1167 dbgs() <<
"Writing trampoline code to "
1168 <<
formatv(
"{0:x16}", TrampolineBlockTargetAddress) <<
"\n";
1173 memcpy(TrampolineBlockWorkingMem + OffsetToPtr, &ResolverAddr,
1177 reinterpret_cast<uint32_t *
>(TrampolineBlockWorkingMem);
1179 uint32_t Hi20 = (OffsetToPtr + 0x800) & 0xfffff000;
1180 uint32_t Lo12 = OffsetToPtr - Hi20;
1181 Trampolines[4 *
I + 0] =
1183 (((Hi20 >> 12) & 0xfffff) << 5);
1184 Trampolines[4 *
I + 1] =
1185 0x28c0018c | ((Lo12 & 0xfff) << 10);
1186 Trampolines[4 *
I + 2] = 0x4c00018d;
1187 Trampolines[4 *
I + 3] = 0x0;
1192 char *StubsBlockWorkingMem,
ExecutorAddr StubsBlockTargetAddress,
1193 ExecutorAddr PointersBlockTargetAddress,
unsigned NumStubs) {
1216 dbgs() <<
"Writing stubs code to "
1217 <<
formatv(
"{0:x16}", StubsBlockTargetAddress) <<
"\n";
1219 assert(stubAndPointerRangesOk<OrcLoongArch64>(
1220 StubsBlockTargetAddress, PointersBlockTargetAddress, NumStubs) &&
1221 "PointersBlock is out of range");
1225 for (
unsigned I = 0;
I < NumStubs; ++
I) {
1227 PointersBlockTargetAddress - StubsBlockTargetAddress;
1228 uint32_t Hi20 = (PtrDisplacement + 0x800) & 0xfffff000;
1229 uint32_t Lo12 = PtrDisplacement - Hi20;
1230 Stub[4 *
I + 0] = 0x1c00000c | (((Hi20 >> 12) & 0xfffff)
1233 0x28c0018c | ((Lo12 & 0xfff) << 10);
1234 Stub[4 *
I + 2] = 0x4c000180;
1235 Stub[4 *
I + 3] = 0x0;
1237 StubsBlockTargetAddress +=
StubSize;
static std::optional< bool > isBigEndian(const SmallDenseMap< int64_t, int64_t, 8 > &MemOffset2Idx, int64_t LowestIdx)
Given a map from byte offsets in memory to indices in a load/store, determine if that map corresponds...
static bool stubAndPointerRangesOk(ExecutorAddr StubBlockAddr, ExecutorAddr PointerBlockAddr, unsigned NumStubs)
Provides a library for accessing information about this process and other processes on the operating ...
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
Represents an address in the executor process.
uint64_t getValue() const
static constexpr unsigned PointerSize
static void writeResolverCode(char *ResolverWorkingMem, ExecutorAddr ResolverTargetAddress, ExecutorAddr ReentryFnAddr, ExecutorAddr RentryCtxAddr)
Write the resolver code into the given memory.
static void writeTrampolines(char *TrampolineBlockWorkingMem, ExecutorAddr TrampolineBlockTargetAddress, ExecutorAddr ResolverAddr, unsigned NumTrampolines)
Write the requested number of trampolines into the given memory, which must be big enough to hold 1 p...
static constexpr unsigned TrampolineSize
static constexpr unsigned StubSize
static void writeIndirectStubsBlock(char *StubsBlockWorkingMem, ExecutorAddr StubsBlockTargetAddress, ExecutorAddr PointersBlockTargetAddress, unsigned MinStubs)
Write NumStubs indirect stubs to working memory at StubsBlockWorkingMem.
static void writeResolverCode(char *ResolverWorkingMem, ExecutorAddr ResolverTargetAddress, ExecutorAddr ReentryFnAddr, ExecutorAddr ReentryCtxAddr)
Write the resolver code into the given memory.
static void writeTrampolines(char *TrampolineBlockWorkingMem, ExecutorAddr TrampolineBlockTargetAddress, ExecutorAddr ResolverAddr, unsigned NumTrampolines)
Write the requested number of trampolines into the given memory, which must be big enough to hold 1 p...
static void writeIndirectStubsBlock(char *StubsBlockWorkingMem, ExecutorAddr StubsBlockTargetAddress, ExecutorAddr PointersBlockTargetAddress, unsigned NumStubs)
Write NumStubs indirect stubs to working memory at StubsBlockWorkingMem.
static constexpr unsigned TrampolineSize
static constexpr unsigned StubSize
static constexpr unsigned PointerSize
static constexpr unsigned TrampolineSize
static void writeResolverCode(char *ResolverWorkingMem, ExecutorAddr ResolverTargetAddress, ExecutorAddr ReentryFnAddr, ExecutorAddr ReentryCtxAddr)
Write the resolver code into the given memory.
static void writeIndirectStubsBlock(char *StubsBlockWorkingMem, ExecutorAddr StubsBlockTargetAddress, ExecutorAddr PointersBlockTargetAddress, unsigned NumStubs)
Write NumStubs indirect stubs to working memory at StubsBlockWorkingMem.
static void writeTrampolines(char *TrampolineBlockWorkingMem, ExecutorAddr TrampolineBlockTargetAddress, ExecutorAddr ResolverFnAddr, unsigned NumTrampolines)
Write the requested number of trampolines into the given memory, which must be big enough to hold 1 p...
static void writeResolverCode(char *ResolverBlockWorkingMem, ExecutorAddr ResolverBlockTargetAddress, ExecutorAddr ReentryFnAddr, ExecutorAddr ReentryCtxAddr, bool isBigEndian)
Write the resolver code into the given memory.
static void writeIndirectStubsBlock(char *StubsBlockWorkingMem, ExecutorAddr StubsBlockTargetAddress, ExecutorAddr PointersBlockTargetAddress, unsigned NumStubs)
Write NumStubs indirect stubs to working memory at StubsBlockWorkingMem.
static void writeTrampolines(char *TrampolineBlockWorkingMem, ExecutorAddr TrampolineBlockTargetAddress, ExecutorAddr ResolverAddr, unsigned NumTrampolines)
Write the requested number of trampolines into the given memory, which must be big enough to hold 1 p...
static void writeIndirectStubsBlock(char *StubsBlockWorkingMem, ExecutorAddr StubsBlockTargetAddress, ExecutorAddr PointersBlockTargetAddress, unsigned NumStubs)
Write NumStubs indirect stubs to working memory at StubsBlockWorkingMem.
static void writeTrampolines(char *TrampolineBlockWorkingMem, ExecutorAddr TrampolineBlockTargetAddress, ExecutorAddr ResolverFnAddr, unsigned NumTrampolines)
Write the requested number of trampolines into the given memory, which must be big enough to hold 1 p...
static void writeResolverCode(char *ResolverWorkingMem, ExecutorAddr ResolverTargetAddress, ExecutorAddr ReentryFnAddr, ExecutorAddr ReentryCtxAddr)
Write the resolver code into the given memory.
static constexpr unsigned StubSize
static constexpr unsigned TrampolineSize
static void writeIndirectStubsBlock(char *StubsBlockWorkingMem, ExecutorAddr StubsBlockTargetAddress, ExecutorAddr PointersBlockTargetAddress, unsigned NumStubs)
Write NumStubs indirect stubs to working memory at StubsBlockWorkingMem.
static void writeTrampolines(char *TrampolineBlockWorkingMem, ExecutorAddr TrampolineBlockTargetAddress, ExecutorAddr ResolverFnAddr, unsigned NumTrampolines)
Write the requested number of trampolines into the given memory, which must be big enough to hold 1 p...
static constexpr unsigned PointerSize
static void writeResolverCode(char *ResolverWorkingMem, ExecutorAddr ResolverTargetAddress, ExecutorAddr ReentryFnAddr, ExecutorAddr ReentryCtxAddr)
Write the resolver code into the given memory.
static constexpr unsigned PointerSize
static constexpr unsigned StubSize
static void writeIndirectStubsBlock(char *StubsBlockWorkingMem, ExecutorAddr StubsBlockTargetAddress, ExecutorAddr PointersBlockTargetAddress, unsigned NumStubs)
Write NumStubs indirect stubs to working memory at StubsBlockWorkingMem.
static void writeTrampolines(char *TrampolineBlockWorkingMem, ExecutorAddr TrampolineBlockTargetAddress, ExecutorAddr ResolverAddr, unsigned NumTrampolines)
Write the requested number of trampolines into the given memory, which must be big enough to hold 1 p...
static constexpr unsigned TrampolineSize
static void writeResolverCode(char *ResolverWorkingMem, ExecutorAddr ResolverTargetAddress, ExecutorAddr ReentryFnAddr, ExecutorAddr ReentryCtxAddr)
Write the resolver code into the given memory.
static void writeResolverCode(char *ResolverWorkingMem, ExecutorAddr ResolverTargetAddress, ExecutorAddr ReentryFnAddr, ExecutorAddr ReentryCtxAddr)
Write the resolver code into the given memory.
This is an optimization pass for GlobalISel generic memory operations.
auto formatv(const char *Fmt, Ts &&...Vals) -> formatv_object< decltype(std::make_tuple(support::detail::build_format_adapter(std::forward< Ts >(Vals))...))>
raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
uint64_t alignTo(uint64_t Size, Align A)
Returns a multiple of A needed to store Size bytes.