1 // Licensed to the .NET Foundation under one or more agreements.
2 // The .NET Foundation licenses this file to you under the MIT license.
3 // See the LICENSE file in the project root for more information.
5 /*XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
6 XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
10 XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
11 XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
19 #if defined(_TARGET_ARM_) && defined(_TARGET_UNIX_)
20 int Compiler::mapRegNumToDwarfReg(regNumber reg)
22 int dwarfReg = DWARF_REG_ILLEGAL;
171 noway_assert(!"unexpected REG_NUM");
176 #endif // _TARGET_ARM_ && _TARGET_UNIX_
178 #ifdef _TARGET_ARMARCH_
180 /*XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
181 XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
185 XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
186 XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
189 void Compiler::unwindBegProlog()
191 assert(compGeneratingProlog);
193 #if defined(_TARGET_UNIX_)
194 if (generateCFIUnwindCodes())
196 unwindBegPrologCFI();
199 #endif // _TARGET_UNIX_
201 FuncInfoDsc* func = funCurrentFunc();
203 // There is only one prolog for a function/funclet, and it comes first. So now is
204 // a good time to initialize all the unwind data structures.
206 emitLocation* startLoc;
207 emitLocation* endLoc;
208 unwindGetFuncLocations(func, true, &startLoc, &endLoc);
210 func->uwi.InitUnwindInfo(this, startLoc, endLoc);
211 func->uwi.CaptureLocation();
213 func->uwiCold = NULL; // No cold data yet
216 void Compiler::unwindEndProlog()
218 assert(compGeneratingProlog);
221 void Compiler::unwindBegEpilog()
223 assert(compGeneratingEpilog);
225 #if defined(_TARGET_UNIX_)
226 if (generateCFIUnwindCodes())
230 #endif // _TARGET_UNIX_
232 funCurrentFunc()->uwi.AddEpilog();
235 void Compiler::unwindEndEpilog()
237 assert(compGeneratingEpilog);
240 #if defined(_TARGET_ARM_)
242 void Compiler::unwindPushPopMaskInt(regMaskTP maskInt, bool useOpsize16)
244 // floating point registers cannot be specified in 'maskInt'
245 assert((maskInt & RBM_ALLFLOAT) == 0);
247 UnwindInfo* pu = &funCurrentFunc()->uwi;
251 // The 16-bit opcode only encode R0-R7 and LR
252 assert((maskInt & ~(RBM_R0 | RBM_R1 | RBM_R2 | RBM_R3 | RBM_R4 | RBM_R5 | RBM_R6 | RBM_R7 | RBM_LR)) == 0);
254 bool shortFormat = false;
257 if ((maskInt & (RBM_R0 | RBM_R1 | RBM_R2 | RBM_R3)) == 0)
259 regMaskTP matchMask = maskInt & (RBM_R4 | RBM_R5 | RBM_R6 | RBM_R7);
260 regMaskTP valMask = RBM_R4;
263 if (matchMask == valMask)
278 // D0-D7 : pop {r4-rX,lr} (X=4-7) (opsize 16)
279 pu->AddCode(0xD0 | ((maskInt >> 12) & 0x4) | val);
283 // EC-ED : pop {r0-r7,lr} (opsize 16)
284 pu->AddCode(0xEC | ((maskInt >> 14) & 0x1), (BYTE)maskInt);
290 ~(RBM_R0 | RBM_R1 | RBM_R2 | RBM_R3 | RBM_R4 | RBM_R5 | RBM_R6 | RBM_R7 | RBM_R8 | RBM_R9 | RBM_R10 |
291 RBM_R11 | RBM_R12 | RBM_LR)) == 0);
293 bool shortFormat = false;
296 if (((maskInt & (RBM_R0 | RBM_R1 | RBM_R2 | RBM_R3)) == 0) &&
297 ((maskInt & (RBM_R4 | RBM_R5 | RBM_R6 | RBM_R7 | RBM_R8)) == (RBM_R4 | RBM_R5 | RBM_R6 | RBM_R7 | RBM_R8)))
299 regMaskTP matchMask = maskInt & (RBM_R4 | RBM_R5 | RBM_R6 | RBM_R7 | RBM_R8 | RBM_R9 | RBM_R10 | RBM_R11);
300 regMaskTP valMask = RBM_R4 | RBM_R5 | RBM_R6 | RBM_R7 | RBM_R8;
303 if (matchMask == valMask)
318 // D8-DF : pop {r4-rX,lr} (X=8-11) (opsize 32)
319 pu->AddCode(0xD8 | ((maskInt >> 12) & 0x4) | val);
323 // 80-BF : pop {r0-r12,lr} (opsize 32)
324 pu->AddCode(0x80 | ((maskInt >> 8) & 0x1F) | ((maskInt >> 9) & 0x20), (BYTE)maskInt);
329 void Compiler::unwindPushPopMaskFloat(regMaskTP maskFloat)
331 // Only floating pointer registers can be specified in 'maskFloat'
332 assert((maskFloat & ~RBM_ALLFLOAT) == 0);
334 // If the maskFloat is zero there is no unwind code to emit
336 if (maskFloat == RBM_NONE)
341 UnwindInfo* pu = &funCurrentFunc()->uwi;
344 regMaskTP valMask = (RBM_F16 | RBM_F17);
346 while (maskFloat != valMask)
349 valMask |= (RBM_F16 | RBM_F17);
355 noway_assert(!"Illegal maskFloat");
359 // E0-E7 : vpop {d8-dX} (X=8-15) (opsize 32)
360 assert(0 <= val && val <= 7);
361 pu->AddCode(0xE0 | val);
364 void Compiler::unwindPushMaskInt(regMaskTP maskInt)
366 // Only r0-r12 and lr are supported
368 ~(RBM_R0 | RBM_R1 | RBM_R2 | RBM_R3 | RBM_R4 | RBM_R5 | RBM_R6 | RBM_R7 | RBM_R8 | RBM_R9 | RBM_R10 |
369 RBM_R11 | RBM_R12 | RBM_LR)) == 0);
371 #if defined(_TARGET_UNIX_)
372 if (generateCFIUnwindCodes())
376 #endif // _TARGET_UNIX_
378 bool useOpsize16 = ((maskInt & (RBM_LOW_REGS | RBM_LR)) == maskInt); // Can PUSH use the 16-bit encoding?
379 unwindPushPopMaskInt(maskInt, useOpsize16);
382 void Compiler::unwindPushMaskFloat(regMaskTP maskFloat)
384 // Only floating point registers should be in maskFloat
385 assert((maskFloat & RBM_ALLFLOAT) == maskFloat);
387 #if defined(_TARGET_UNIX_)
388 if (generateCFIUnwindCodes())
392 #endif // _TARGET_UNIX_
394 unwindPushPopMaskFloat(maskFloat);
397 void Compiler::unwindPopMaskInt(regMaskTP maskInt)
399 #if defined(_TARGET_UNIX_)
400 if (generateCFIUnwindCodes())
402 unwindPushPopMaskCFI(maskInt, false);
405 #endif // _TARGET_UNIX_
407 // Only r0-r12 and lr and pc are supported (pc is mapped to lr when encoding)
409 ~(RBM_R0 | RBM_R1 | RBM_R2 | RBM_R3 | RBM_R4 | RBM_R5 | RBM_R6 | RBM_R7 | RBM_R8 | RBM_R9 | RBM_R10 |
410 RBM_R11 | RBM_R12 | RBM_LR | RBM_PC)) == 0);
412 bool useOpsize16 = ((maskInt & (RBM_LOW_REGS | RBM_PC)) == maskInt); // Can POP use the 16-bit encoding?
414 // If we are popping PC, then we'll return from the function. In this case, we assume
415 // the first thing the prolog did was push LR, so give the unwind codes in terms of
416 // the LR that was pushed. Note that the epilog unwind codes are meant to reverse
417 // the effect of the prolog. For "pop {pc}", the prolog had "push {lr}", so we need
418 // an epilog code to model the reverse of that.
419 if (maskInt & RBM_PC)
421 maskInt = (maskInt & ~RBM_PC) | RBM_LR;
423 unwindPushPopMaskInt(maskInt, useOpsize16);
426 void Compiler::unwindPopMaskFloat(regMaskTP maskFloat)
428 #if defined(_TARGET_UNIX_)
429 if (generateCFIUnwindCodes())
431 unwindPushPopMaskCFI(maskFloat, true);
434 #endif // _TARGET_UNIX_
436 // Only floating point registers should be in maskFloat
437 assert((maskFloat & RBM_ALLFLOAT) == maskFloat);
438 unwindPushPopMaskFloat(maskFloat);
441 void Compiler::unwindAllocStack(unsigned size)
443 #if defined(_TARGET_UNIX_)
444 if (generateCFIUnwindCodes())
446 if (compGeneratingEpilog)
448 unwindAllocStackCFI(size);
452 #endif // _TARGET_UNIX_
454 UnwindInfo* pu = &funCurrentFunc()->uwi;
456 assert(size % 4 == 0);
461 // 00-7F : add sp, sp, #X*4 (opsize 16)
462 pu->AddCode((BYTE)size);
464 else if (size <= 0x3FF)
466 // E8-EB : addw sp, sp, #X*4 (opsize 32)
467 pu->AddCode(0xE8 | (BYTE)(size >> 8), (BYTE)size);
469 else if (size <= 0xFFFF)
471 // F7 : add sp, sp, #X*4 (opsize 16)
472 // F9 : add sp, sp, #X*4 (opsize 32)
474 // For large stack size, the most significant bits
475 // are stored first (and next to the opCode (F9)) per the unwind spec.
476 unsigned instrSizeInBytes = pu->GetInstructionSize();
477 BYTE b1 = (instrSizeInBytes == 2) ? 0xF7 : 0xF9;
479 (BYTE)(size >> 8), // msb
484 // F8 : add sp, sp, #X*4 (opsize 16)
485 // FA : add sp, sp, #X*4 (opsize 32)
487 // For large stack size, the most significant bits
488 // are stored first (and next to the opCode (FA)) per the unwind spec.
489 unsigned instrSizeInBytes = pu->GetInstructionSize();
490 BYTE b1 = (instrSizeInBytes == 2) ? 0xF8 : 0xFA;
491 pu->AddCode(b1, (BYTE)(size >> 16), (BYTE)(size >> 8), (BYTE)size);
495 void Compiler::unwindSetFrameReg(regNumber reg, unsigned offset)
497 #if defined(_TARGET_UNIX_)
498 if (generateCFIUnwindCodes())
500 if (compGeneratingEpilog)
502 unwindSetFrameRegCFI(reg, offset);
506 #endif // _TARGET_UNIX_
508 UnwindInfo* pu = &funCurrentFunc()->uwi;
510 // Arm unwind info does not allow offset
512 assert(0 <= reg && reg <= 15);
514 // C0-CF : mov sp, rX (opsize 16)
515 pu->AddCode((BYTE)(0xC0 + reg));
518 void Compiler::unwindSaveReg(regNumber reg, unsigned offset)
523 void Compiler::unwindBranch16()
525 #if defined(_TARGET_UNIX_)
526 if (generateCFIUnwindCodes())
530 #endif // _TARGET_UNIX_
532 UnwindInfo* pu = &funCurrentFunc()->uwi;
534 // TODO-CQ: need to handle changing the exit code from 0xFF to 0xFD. Currently, this will waste an extra 0xFF at the
535 // end, automatically added.
539 void Compiler::unwindNop(unsigned codeSizeInBytes) // codeSizeInBytes is 2 or 4 bytes for Thumb2 instruction
541 #if defined(_TARGET_UNIX_)
542 if (generateCFIUnwindCodes())
546 #endif // _TARGET_UNIX_
548 UnwindInfo* pu = &funCurrentFunc()->uwi;
553 printf("unwindNop: adding NOP for %d byte instruction\n", codeSizeInBytes);
557 INDEBUG(pu->uwiAddingNOP = true);
559 if (codeSizeInBytes == 2)
561 // FB : nop (opsize 16)
566 noway_assert(codeSizeInBytes == 4);
568 // FC : nop (opsize 32)
572 INDEBUG(pu->uwiAddingNOP = false);
575 #endif // defined(_TARGET_ARM_)
577 // The instructions between the last captured "current state" and the current instruction
578 // are in the prolog but have no effect for unwinding. Emit the appropriate NOP unwind codes
580 void Compiler::unwindPadding()
582 #if defined(_TARGET_UNIX_)
583 if (generateCFIUnwindCodes())
587 #endif // _TARGET_UNIX_
589 UnwindInfo* pu = &funCurrentFunc()->uwi;
590 genEmitter->emitUnwindNopPadding(pu->GetCurrentEmitterLocation(), this);
593 // Ask the VM to reserve space for the unwind information for the function and
595 void Compiler::unwindReserve()
597 assert(!compGeneratingProlog);
598 assert(!compGeneratingEpilog);
600 assert(compFuncInfoCount > 0);
601 for (unsigned funcIdx = 0; funcIdx < compFuncInfoCount; funcIdx++)
603 unwindReserveFunc(funGetFunc(funcIdx));
607 void Compiler::unwindReserveFunc(FuncInfoDsc* func)
609 BOOL isFunclet = (func->funKind == FUNC_ROOT) ? FALSE : TRUE;
610 bool funcHasColdSection = false;
612 #if defined(_TARGET_UNIX_)
613 if (generateCFIUnwindCodes())
615 DWORD unwindCodeBytes = 0;
616 if (fgFirstColdBlock != nullptr)
618 eeReserveUnwindInfo(isFunclet, true /*isColdCode*/, unwindCodeBytes);
620 unwindCodeBytes = (DWORD)(func->cfiCodes->size() * sizeof(CFI_CODE));
621 eeReserveUnwindInfo(isFunclet, false /*isColdCode*/, unwindCodeBytes);
625 #endif // _TARGET_UNIX_
627 // If there is cold code, split the unwind data between the hot section and the
628 // cold section. This needs to be done before we split into fragments, as each
629 // of the hot and cold sections can have multiple fragments.
631 if (fgFirstColdBlock != NULL)
633 assert(!isFunclet); // TODO-CQ: support hot/cold splitting with EH
635 emitLocation* startLoc;
636 emitLocation* endLoc;
637 unwindGetFuncLocations(func, false, &startLoc, &endLoc);
639 func->uwiCold = new (this, CMK_UnwindInfo) UnwindInfo();
640 func->uwiCold->InitUnwindInfo(this, startLoc, endLoc);
641 func->uwiCold->HotColdSplitCodes(&func->uwi);
643 funcHasColdSection = true;
646 // First we need to split the function or funclet into fragments that are no larger
647 // than 512K, so the fragment size will fit in the unwind data "Function Length" field.
648 // The ARM Exception Data specification "Function Fragments" section describes this.
651 func->uwi.Reserve(isFunclet, true);
653 // After the hot section, split and reserve the cold section
655 if (funcHasColdSection)
657 assert(func->uwiCold != NULL);
659 func->uwiCold->Split();
660 func->uwiCold->Reserve(isFunclet, false);
664 // unwindEmit: Report all the unwind information to the VM.
666 // pHotCode: Pointer to the beginning of the memory with the function and funclet hot code
667 // pColdCode: Pointer to the beginning of the memory with the function and funclet cold code.
669 void Compiler::unwindEmit(void* pHotCode, void* pColdCode)
671 assert(compFuncInfoCount > 0);
672 for (unsigned funcIdx = 0; funcIdx < compFuncInfoCount; funcIdx++)
674 unwindEmitFunc(funGetFunc(funcIdx), pHotCode, pColdCode);
678 void Compiler::unwindEmitFunc(FuncInfoDsc* func, void* pHotCode, void* pColdCode)
680 // Verify that the JIT enum is in sync with the JIT-EE interface enum
681 static_assert_no_msg(FUNC_ROOT == (FuncKind)CORJIT_FUNC_ROOT);
682 static_assert_no_msg(FUNC_HANDLER == (FuncKind)CORJIT_FUNC_HANDLER);
683 static_assert_no_msg(FUNC_FILTER == (FuncKind)CORJIT_FUNC_FILTER);
685 #if defined(_TARGET_UNIX_)
686 if (generateCFIUnwindCodes())
688 unwindEmitFuncCFI(func, pHotCode, pColdCode);
691 #endif // _TARGET_UNIX_
693 func->uwi.Allocate((CorJitFuncKind)func->funKind, pHotCode, pColdCode, true);
695 if (func->uwiCold != NULL)
697 func->uwiCold->Allocate((CorJitFuncKind)func->funKind, pHotCode, pColdCode, false);
701 #if defined(_TARGET_ARM_)
703 /*XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
704 XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
706 XX Unwind Info Debug helpers XX
708 XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
709 XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
714 // Return the opcode size of an instruction, in bytes, given the first byte of
715 // its corresponding unwind code.
717 unsigned GetOpcodeSizeFromUnwindHeader(BYTE b1)
719 static BYTE s_UnwindOpsize[256] = {
720 // array of opsizes, in bytes (as specified in the ARM unwind specification)
721 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, // 00-0F
722 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, // 10-1F
723 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, // 20-2F
724 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, // 30-3F
725 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, // 40-4F
726 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, // 50-5F
727 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, // 60-6F
728 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, // 70-7F
729 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, // 80-8F
730 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, // 90-9F
731 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, // A0-AF
732 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, // B0-BF
733 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, // C0-CF
734 2, 2, 2, 2, 2, 2, 2, 2, 4, 4, 4, 4, 4, 4, 4, 4, // D0-DF
735 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 2, 2, 2, 4, // E0-EF
736 0, 0, 0, 0, 0, 4, 4, 2, 2, 4, 4, 2, 4, 2, 4, 0 // F0-FF
739 BYTE opsize = s_UnwindOpsize[b1];
740 assert(opsize == 2 ||
741 opsize == 4); // We shouldn't get a code with no opsize (the 0xFF end code is handled specially)
745 // Return the size of the unwind code (from 1 to 4 bytes), given the first byte of the unwind bytes
747 unsigned GetUnwindSizeFromUnwindHeader(BYTE b1)
749 static BYTE s_UnwindSize[256] = {
750 // array of unwind sizes, in bytes (as specified in the ARM unwind specification)
751 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, // 00-0F
752 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, // 10-1F
753 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, // 20-2F
754 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, // 30-3F
755 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, // 40-4F
756 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, // 50-5F
757 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, // 60-6F
758 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, // 70-7F
759 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, // 80-8F
760 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, // 90-9F
761 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, // A0-AF
762 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, // B0-BF
763 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, // C0-CF
764 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, // D0-DF
765 1, 1, 1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 2, 2, // E0-EF
766 1, 1, 1, 1, 1, 2, 2, 3, 4, 3, 4, 1, 1, 1, 1, 1 // F0-FF
769 unsigned size = s_UnwindSize[b1];
770 assert(1 <= size && size <= 4);
776 /*XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
777 XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
779 XX Unwind Info Support Classes XX
781 XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
782 XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
785 ///////////////////////////////////////////////////////////////////////////////
789 ///////////////////////////////////////////////////////////////////////////////
793 // Walk the prolog codes and calculate the size of the prolog or epilog, in bytes.
794 // The 0xFD and 0xFE "end + NOP" codes need to be handled differently between
795 // the prolog and epilog. They count as pure "end" codes in a prolog, but they
796 // count as 16 and 32 bit NOPs (respectively), as well as an "end", in an epilog.
797 unsigned UnwindCodesBase::GetCodeSizeFromUnwindCodes(bool isProlog)
799 BYTE* pCodesStart = GetCodes();
800 BYTE* pCodes = pCodesStart;
807 // 0xFD, 0xFE, 0xFF are "end" codes
809 if (!isProlog && (b1 == 0xFD || b1 == 0xFE))
811 // Count the special "end + NOP" code size in the epilog
812 size += GetOpcodeSizeFromUnwindHeader(b1);
815 break; // We hit an "end" code; we're done
817 size += GetOpcodeSizeFromUnwindHeader(b1);
818 pCodes += GetUnwindSizeFromUnwindHeader(b1);
819 assert(pCodes - pCodesStart < 256); // 255 is the absolute maximum number of code bytes allowed
826 #endif // defined(_TARGET_ARM_)
828 ///////////////////////////////////////////////////////////////////////////////
832 ///////////////////////////////////////////////////////////////////////////////
834 // We're going to use the prolog codes memory to store the final unwind data.
835 // Ensure we have enough memory to store everything. If 'epilogBytes' > 0, then
836 // move the prolog codes so there are 'epilogBytes' bytes after the prolog codes.
837 // Set the header pointer for future use, adding the header bytes (this pointer
838 // is updated when a header byte is added), and remember the index that points
839 // to the beginning of the header.
841 void UnwindPrologCodes::SetFinalSize(int headerBytes, int epilogBytes)
844 // We're done adding codes. Check that we didn't accidentally create a bigger prolog.
845 unsigned codeSize = GetCodeSizeFromUnwindCodes(true);
846 assert(codeSize <= MAX_PROLOG_SIZE_BYTES);
849 int prologBytes = Size();
851 EnsureSize(headerBytes + prologBytes + epilogBytes + 3); // 3 = padding bytes for alignment
853 upcUnwindBlockSlot = upcCodeSlot - headerBytes - epilogBytes; // Index of the first byte of the unwind header
855 assert(upcMemSize == upcUnwindBlockSlot + headerBytes + prologBytes + epilogBytes + 3);
857 upcHeaderSlot = upcUnwindBlockSlot - 1; // upcHeaderSlot is always incremented before storing
858 assert(upcHeaderSlot >= -1);
862 // The prolog codes that are already at the end of the array need to get moved to the middle,
863 // with space for the non-matching epilog codes to follow.
865 memmove_s(&upcMem[upcUnwindBlockSlot + headerBytes], upcMemSize - (upcUnwindBlockSlot + headerBytes),
866 &upcMem[upcCodeSlot], prologBytes);
868 // Note that the three UWC_END padding bytes still exist at the end of the array.
869 CLANG_FORMAT_COMMENT_ANCHOR;
872 // Zero out the epilog codes memory, to ensure we've copied the right bytes. Don't zero the padding bytes.
873 memset(&upcMem[upcUnwindBlockSlot + headerBytes + prologBytes], 0, epilogBytes);
877 upcUnwindBlockSlot + headerBytes + prologBytes; // upcEpilogSlot points to the next epilog location to fill
879 // Update upcCodeSlot to point at the new beginning of the prolog codes
880 upcCodeSlot = upcUnwindBlockSlot + headerBytes;
884 // Add a header word. Header words are added starting at the beginning, in order: first to last.
885 // This is in contrast to the prolog unwind codes, which are added in reverse order.
886 void UnwindPrologCodes::AddHeaderWord(DWORD d)
888 assert(-1 <= upcHeaderSlot);
889 assert(upcHeaderSlot + 4 < upcCodeSlot); // Don't collide with the unwind codes that are already there!
891 // Store it byte-by-byte in little-endian format. We've already ensured there is enough space
892 // in SetFinalSize().
893 upcMem[++upcHeaderSlot] = (BYTE)d;
894 upcMem[++upcHeaderSlot] = (BYTE)(d >> 8);
895 upcMem[++upcHeaderSlot] = (BYTE)(d >> 16);
896 upcMem[++upcHeaderSlot] = (BYTE)(d >> 24);
899 // AppendEpilog: copy the epilog bytes to the next epilog bytes slot
900 void UnwindPrologCodes::AppendEpilog(UnwindEpilogInfo* pEpi)
902 assert(upcEpilogSlot != -1);
904 int epiSize = pEpi->Size();
905 memcpy_s(&upcMem[upcEpilogSlot], upcMemSize - upcEpilogSlot - 3, pEpi->GetCodes(),
906 epiSize); // -3 to avoid writing to the alignment padding
907 assert(pEpi->GetStartIndex() ==
908 upcEpilogSlot - upcCodeSlot); // Make sure we copied it where we expected to copy it.
910 upcEpilogSlot += epiSize;
911 assert(upcEpilogSlot <= upcMemSize - 3);
914 // GetFinalInfo: return a pointer to the final unwind info to hand to the VM, and the size of this info in bytes
915 void UnwindPrologCodes::GetFinalInfo(/* OUT */ BYTE** ppUnwindBlock, /* OUT */ ULONG* pUnwindBlockSize)
917 assert(upcHeaderSlot + 1 == upcCodeSlot); // We better have filled in the header before asking for the final data!
919 *ppUnwindBlock = &upcMem[upcUnwindBlockSlot];
921 // We put 4 'end' codes at the end for padding, so we can ensure we have an
922 // unwind block that is a multiple of 4 bytes in size. Subtract off three 'end'
923 // codes (leave one), and then align the size up to a multiple of 4.
924 *pUnwindBlockSize = AlignUp((UINT)(upcMemSize - upcUnwindBlockSlot - 3), sizeof(DWORD));
927 // Do the argument unwind codes match our unwind codes?
928 // If they don't match, return -1. If they do, return the offset into
929 // our codes at which they match. Note that this means that the
930 // argument codes can match a subset of our codes. The subset needs to be at
931 // the end, for the "end" code to match.
933 // This is similar to UnwindEpilogInfo::Match().
935 #if defined(_TARGET_ARM_)
936 // Note that if we wanted to handle 0xFD and 0xFE codes, by converting
937 // an existing 0xFF code to one of those, we might do that here.
938 #endif // defined(_TARGET_ARM_)
940 int UnwindPrologCodes::Match(UnwindEpilogInfo* pEpi)
942 if (Size() < pEpi->Size())
947 int matchIndex = Size() - pEpi->Size();
949 if (0 == memcmp(GetCodes() + matchIndex, pEpi->GetCodes(), pEpi->Size()))
957 // Copy the prolog codes from another prolog. The only time this is legal is
958 // if we are at the initial state and no prolog codes have been added.
959 // This is used to create the 'phantom' prolog for non-first fragments.
961 void UnwindPrologCodes::CopyFrom(UnwindPrologCodes* pCopyFrom)
963 assert(uwiComp == pCopyFrom->uwiComp);
964 assert(upcMem == upcMemLocal);
965 assert(upcMemSize == UPC_LOCAL_COUNT);
966 assert(upcHeaderSlot == -1);
967 assert(upcEpilogSlot == -1);
970 EnsureSize(pCopyFrom->upcMemSize);
971 assert(upcMemSize == pCopyFrom->upcMemSize);
972 memcpy_s(upcMem, upcMemSize, pCopyFrom->upcMem, pCopyFrom->upcMemSize);
974 // Copy the other data
975 upcCodeSlot = pCopyFrom->upcCodeSlot;
976 upcHeaderSlot = pCopyFrom->upcHeaderSlot;
977 upcEpilogSlot = pCopyFrom->upcEpilogSlot;
978 upcUnwindBlockSlot = pCopyFrom->upcUnwindBlockSlot;
981 void UnwindPrologCodes::EnsureSize(int requiredSize)
983 if (requiredSize > upcMemSize)
985 // Reallocate, and copy everything to a new array.
987 // Choose the next power of two size. This may or may not be the best choice.
988 noway_assert((requiredSize & 0xC0000000) == 0); // too big!
990 for (newSize = upcMemSize << 1; newSize < requiredSize; newSize <<= 1)
995 BYTE* newUnwindCodes = new (uwiComp, CMK_UnwindInfo) BYTE[newSize];
996 memcpy_s(newUnwindCodes + newSize - upcMemSize, upcMemSize, upcMem,
997 upcMemSize); // copy the existing data to the end
999 // Clear the old unwind codes; nobody should be looking at them
1000 memset(upcMem, 0xFF, upcMemSize);
1002 upcMem = newUnwindCodes; // we don't free anything that used to be there since we have a no-release allocator
1003 upcCodeSlot += newSize - upcMemSize;
1004 upcMemSize = newSize;
1009 void UnwindPrologCodes::Dump(int indent)
1011 printf("%*sUnwindPrologCodes @0x%08p, size:%d:\n", indent, "", dspPtr(this), sizeof(*this));
1012 printf("%*s uwiComp: 0x%08p\n", indent, "", dspPtr(uwiComp));
1013 printf("%*s &upcMemLocal[0]: 0x%08p\n", indent, "", dspPtr(&upcMemLocal[0]));
1014 printf("%*s upcMem: 0x%08p\n", indent, "", dspPtr(upcMem));
1015 printf("%*s upcMemSize: %d\n", indent, "", upcMemSize);
1016 printf("%*s upcCodeSlot: %d\n", indent, "", upcCodeSlot);
1017 printf("%*s upcHeaderSlot: %d\n", indent, "", upcHeaderSlot);
1018 printf("%*s upcEpilogSlot: %d\n", indent, "", upcEpilogSlot);
1019 printf("%*s upcUnwindBlockSlot: %d\n", indent, "", upcUnwindBlockSlot);
1023 printf("%*s codes:", indent, "");
1024 for (int i = 0; i < upcMemSize; i++)
1026 printf(" %02x", upcMem[i]);
1027 if (i == upcCodeSlot)
1029 else if (i == upcHeaderSlot)
1031 else if (i == upcEpilogSlot)
1033 else if (i == upcUnwindBlockSlot)
1041 ///////////////////////////////////////////////////////////////////////////////
1043 // UnwindEpilogCodes
1045 ///////////////////////////////////////////////////////////////////////////////
1047 void UnwindEpilogCodes::EnsureSize(int requiredSize)
1049 if (requiredSize > uecMemSize)
1051 // Reallocate, and copy everything to a new array.
1053 // Choose the next power of two size. This may or may not be the best choice.
1054 noway_assert((requiredSize & 0xC0000000) == 0); // too big!
1056 for (newSize = uecMemSize << 1; newSize < requiredSize; newSize <<= 1)
1061 BYTE* newUnwindCodes = new (uwiComp, CMK_UnwindInfo) BYTE[newSize];
1062 memcpy_s(newUnwindCodes, newSize, uecMem, uecMemSize);
1064 // Clear the old unwind codes; nobody should be looking at them
1065 memset(uecMem, 0xFF, uecMemSize);
1067 uecMem = newUnwindCodes; // we don't free anything that used to be there since we have a no-release allocator
1068 // uecCodeSlot stays the same
1069 uecMemSize = newSize;
1074 void UnwindEpilogCodes::Dump(int indent)
1076 printf("%*sUnwindEpilogCodes @0x%08p, size:%d:\n", indent, "", dspPtr(this), sizeof(*this));
1077 printf("%*s uwiComp: 0x%08p\n", indent, "", dspPtr(uwiComp));
1078 printf("%*s &uecMemLocal[0]: 0x%08p\n", indent, "", dspPtr(&uecMemLocal[0]));
1079 printf("%*s uecMem: 0x%08p\n", indent, "", dspPtr(uecMem));
1080 printf("%*s uecMemSize: %d\n", indent, "", uecMemSize);
1081 printf("%*s uecCodeSlot: %d\n", indent, "", uecCodeSlot);
1082 printf("%*s uecFinalized: %s\n", indent, "", dspBool(uecFinalized));
1086 printf("%*s codes:", indent, "");
1087 for (int i = 0; i < uecMemSize; i++)
1089 printf(" %02x", uecMem[i]);
1090 if (i == uecCodeSlot)
1091 printf(" <-C"); // Indicate the current pointer
1098 ///////////////////////////////////////////////////////////////////////////////
1102 ///////////////////////////////////////////////////////////////////////////////
1104 // Do the current unwind codes match those of the argument epilog?
1105 // If they don't match, return -1. If they do, return the offset into
1106 // our codes at which the argument codes match. Note that this means that
1107 // the argument codes can match a subset of our codes. The subset needs to be at
1108 // the end, for the "end" code to match.
1110 // Note that if we wanted to handle 0xFD and 0xFE codes, by converting
1111 // an existing 0xFF code to one of those, we might do that here.
1113 int UnwindEpilogInfo::Match(UnwindEpilogInfo* pEpi)
1117 // We are already matched to someone else, and won't provide codes to the final layout
1121 if (Size() < pEpi->Size())
1126 int matchIndex = Size() - pEpi->Size();
1128 if (0 == memcmp(GetCodes() + matchIndex, pEpi->GetCodes(), pEpi->Size()))
1136 void UnwindEpilogInfo::CaptureEmitLocation()
1138 noway_assert(epiEmitLocation == NULL); // This function is only called once per epilog
1139 epiEmitLocation = new (uwiComp, CMK_UnwindInfo) emitLocation();
1140 epiEmitLocation->CaptureLocation(uwiComp->genEmitter);
1143 void UnwindEpilogInfo::FinalizeOffset()
1145 epiStartOffset = epiEmitLocation->CodeOffset(uwiComp->genEmitter);
1149 void UnwindEpilogInfo::Dump(int indent)
1151 printf("%*sUnwindEpilogInfo @0x%08p, size:%d:\n", indent, "", dspPtr(this), sizeof(*this));
1152 printf("%*s uwiComp: 0x%08p\n", indent, "", dspPtr(uwiComp));
1153 printf("%*s epiNext: 0x%08p\n", indent, "", dspPtr(epiNext));
1154 printf("%*s epiEmitLocation: 0x%08p\n", indent, "", dspPtr(epiEmitLocation));
1155 printf("%*s epiStartOffset: 0x%x\n", indent, "", epiStartOffset);
1156 printf("%*s epiMatches: %s\n", indent, "", dspBool(epiMatches));
1157 printf("%*s epiStartIndex: %d\n", indent, "", epiStartIndex);
1159 epiCodes.Dump(indent + 2);
1163 ///////////////////////////////////////////////////////////////////////////////
1165 // UnwindFragmentInfo
1167 ///////////////////////////////////////////////////////////////////////////////
1169 UnwindFragmentInfo::UnwindFragmentInfo(Compiler* comp, emitLocation* emitLoc, bool hasPhantomProlog)
1172 , ufiEmitLoc(emitLoc)
1173 , ufiHasPhantomProlog(hasPhantomProlog)
1174 , ufiPrologCodes(comp)
1175 , ufiEpilogFirst(comp)
1176 , ufiEpilogList(NULL)
1177 , ufiEpilogLast(NULL)
1178 , ufiCurCodes(&ufiPrologCodes)
1180 , ufiStartOffset(UFI_ILLEGAL_OFFSET)
1185 ufiInitialized = UFI_INITIALIZED_PATTERN;
1189 void UnwindFragmentInfo::FinalizeOffset()
1191 if (ufiEmitLoc == NULL)
1193 // NULL emit location means the beginning of the code. This is to handle the first fragment prolog.
1198 ufiStartOffset = ufiEmitLoc->CodeOffset(uwiComp->genEmitter);
1201 for (UnwindEpilogInfo* pEpi = ufiEpilogList; pEpi != NULL; pEpi = pEpi->epiNext)
1203 pEpi->FinalizeOffset();
1207 void UnwindFragmentInfo::AddEpilog()
1209 assert(ufiInitialized == UFI_INITIALIZED_PATTERN);
1214 assert(ufiEpilogList == NULL);
1215 ufiInProlog = false;
1219 assert(ufiEpilogList != NULL);
1223 // Either allocate a new epilog object, or, for the first one, use the
1224 // preallocated one that is a member of the UnwindFragmentInfo class.
1226 UnwindEpilogInfo* newepi;
1228 if (ufiEpilogList == NULL)
1230 // Use the epilog that's in the class already. Be sure to initialize it!
1231 newepi = ufiEpilogList = &ufiEpilogFirst;
1235 newepi = new (uwiComp, CMK_UnwindInfo) UnwindEpilogInfo(uwiComp);
1238 // Put the new epilog at the end of the epilog list
1240 if (ufiEpilogLast != NULL)
1242 ufiEpilogLast->epiNext = newepi;
1245 ufiEpilogLast = newepi;
1247 // What is the starting code offset of the epilog? Store an emitter location
1248 // so we can ask the emitter later, after codegen.
1250 newepi->CaptureEmitLocation();
1252 // Put subsequent unwind codes in this new epilog
1254 ufiCurCodes = &newepi->epiCodes;
1257 // Copy the prolog codes from the 'pCopyFrom' fragment. These prolog codes will
1258 // become 'phantom' prolog codes in this fragment. Note that this fragment should
1259 // not have any prolog codes currently; it is at the initial state.
1261 void UnwindFragmentInfo::CopyPrologCodes(UnwindFragmentInfo* pCopyFrom)
1263 ufiPrologCodes.CopyFrom(&pCopyFrom->ufiPrologCodes);
1264 #ifdef _TARGET_ARM64_
1265 ufiPrologCodes.AddCode(UWC_END_C);
1269 // Split the epilog codes that currently exist in 'pSplitFrom'. The ones that represent
1270 // epilogs that start at or after the location represented by 'emitLoc' are removed
1271 // from 'pSplitFrom' and moved to this fragment. Note that this fragment should not have
1272 // any epilog codes currently; it is at the initial state.
1274 void UnwindFragmentInfo::SplitEpilogCodes(emitLocation* emitLoc, UnwindFragmentInfo* pSplitFrom)
1276 UnwindEpilogInfo* pEpiPrev;
1277 UnwindEpilogInfo* pEpi;
1279 UNATIVE_OFFSET splitOffset = emitLoc->CodeOffset(uwiComp->genEmitter);
1281 for (pEpiPrev = NULL, pEpi = pSplitFrom->ufiEpilogList; pEpi != NULL; pEpiPrev = pEpi, pEpi = pEpi->epiNext)
1283 pEpi->FinalizeOffset(); // Get the offset of the epilog from the emitter so we can compare it
1284 if (pEpi->GetStartOffset() >= splitOffset)
1286 // This epilog and all following epilogs, which must be in order of increasing offsets,
1287 // get moved to this fragment.
1289 // Splice in the epilogs to this fragment. Set the head of the epilog
1290 // list to this epilog.
1291 ufiEpilogList = pEpi; // In this case, don't use 'ufiEpilogFirst'
1292 ufiEpilogLast = pSplitFrom->ufiEpilogLast;
1294 // Splice out the tail of the list from the 'pSplitFrom' epilog list
1295 pSplitFrom->ufiEpilogLast = pEpiPrev;
1296 if (pSplitFrom->ufiEpilogLast == NULL)
1298 pSplitFrom->ufiEpilogList = NULL;
1302 pSplitFrom->ufiEpilogLast->epiNext = NULL;
1305 // No more codes should be added once we start splitting
1306 pSplitFrom->ufiCurCodes = NULL;
1314 // Is this epilog at the end of an unwind fragment? Ask the emitter.
1315 // Note that we need to know this before all code offsets are finalized,
1316 // so we can determine whether we can omit an epilog scope word for a
1317 // single matching epilog.
1319 bool UnwindFragmentInfo::IsAtFragmentEnd(UnwindEpilogInfo* pEpi)
1321 return uwiComp->genEmitter->emitIsFuncEnd(pEpi->epiEmitLocation, (ufiNext == NULL) ? NULL : ufiNext->ufiEmitLoc);
1324 // Merge the unwind codes as much as possible.
1325 // This function is called before all offsets are final.
1326 // Also, compute the size of the final unwind block. Store this
1327 // and some other data for later, when we actually emit the
1330 void UnwindFragmentInfo::MergeCodes()
1332 assert(ufiInitialized == UFI_INITIALIZED_PATTERN);
1334 unsigned epilogCount = 0;
1335 unsigned epilogCodeBytes = 0; // The total number of unwind code bytes used by epilogs that don't match the
1337 unsigned epilogIndex = ufiPrologCodes.Size(); // The "Epilog Start Index" for the next non-matching epilog codes
1338 UnwindEpilogInfo* pEpi;
1340 for (pEpi = ufiEpilogList; pEpi != NULL; pEpi = pEpi->epiNext)
1344 pEpi->FinalizeCodes();
1346 // Does this epilog match the prolog?
1347 // NOTE: for the purpose of matching, we don't handle the 0xFD and 0xFE end codes that allow slightly unequal
1348 // prolog and epilog codes.
1352 matchIndex = ufiPrologCodes.Match(pEpi);
1353 if (matchIndex != -1)
1356 pEpi->SetStartIndex(matchIndex); // Prolog codes start at zero, so matchIndex is exactly the start index
1360 // The epilog codes don't match the prolog codes. Do they match any of the epilogs
1361 // we've seen so far?
1363 bool matched = false;
1364 for (UnwindEpilogInfo* pEpi2 = ufiEpilogList; pEpi2 != pEpi; pEpi2 = pEpi2->epiNext)
1366 matchIndex = pEpi2->Match(pEpi);
1367 if (matchIndex != -1)
1369 // Use the same epilog index as the one we matched, as it has already been set.
1371 pEpi->SetStartIndex(pEpi2->GetStartIndex() + matchIndex); // We might match somewhere inside pEpi2's
1372 // codes, in which case matchIndex > 0
1380 pEpi->SetStartIndex(epilogIndex); // We'll copy these codes to the next available location
1381 epilogCodeBytes += pEpi->Size();
1382 epilogIndex += pEpi->Size();
1387 DWORD codeBytes = ufiPrologCodes.Size() + epilogCodeBytes;
1388 codeBytes = AlignUp(codeBytes, sizeof(DWORD));
1391 codeBytes / sizeof(DWORD); // This is how many words we need to store all the unwind codes in the unwind block
1393 // Do we need the 2nd header word for "Extended Code Words" or "Extended Epilog Count"?
1395 bool needExtendedCodeWordsEpilogCount =
1396 (codeWords > UW_MAX_CODE_WORDS_COUNT) || (epilogCount > UW_MAX_EPILOG_COUNT);
1398 // How many epilog scope words do we need?
1400 bool setEBit = false; // do we need to set the E bit?
1401 unsigned epilogScopes = epilogCount; // Note that this could be zero if we have no epilogs!
1403 if (epilogCount == 1)
1405 assert(ufiEpilogList != NULL);
1406 assert(ufiEpilogList->epiNext == NULL);
1408 if (ufiEpilogList->Matches() && (ufiEpilogList->GetStartIndex() == 0) && // The match is with the prolog
1409 !needExtendedCodeWordsEpilogCount && IsAtFragmentEnd(ufiEpilogList))
1411 epilogScopes = 0; // Don't need any epilog scope words
1416 DWORD headerBytes = (1 // Always need first header DWORD
1417 + (needExtendedCodeWordsEpilogCount ? 1 : 0) // Do we need the 2nd DWORD for Extended Code
1418 // Words or Extended Epilog Count?
1419 + epilogScopes // One DWORD per epilog scope, for EBit = 0
1421 sizeof(DWORD); // convert it to bytes
1423 DWORD finalSize = headerBytes + codeBytes; // Size of actual unwind codes, aligned up to 4-byte words,
1424 // including end padding if necessary
1426 // Construct the final unwind information.
1428 // We re-use the memory for the prolog unwind codes to construct the full unwind data. If all the epilogs
1429 // match the prolog, this is easy: we just prepend the header. If there are epilog codes that don't match
1430 // the prolog, we still use the prolog codes memory, but it's a little more complicated, since the
1431 // unwind info is ordered as: (a) header, (b) prolog codes, (c) non-matching epilog codes. And, the prolog
1432 // codes array is filled in from end-to-beginning. So, we compute the size of memory we need, ensure we
1433 // have that much memory, and then copy the prolog codes to the right place, appending the non-matching
1434 // epilog codes and prepending the header.
1436 ufiPrologCodes.SetFinalSize(headerBytes, epilogCodeBytes);
1438 if (epilogCodeBytes != 0)
1440 // We need to copy the epilog code bytes to their final memory location
1442 for (pEpi = ufiEpilogList; pEpi != NULL; pEpi = pEpi->epiNext)
1444 if (!pEpi->Matches())
1446 ufiPrologCodes.AppendEpilog(pEpi);
1451 // Save some data for later
1453 ufiSize = finalSize;
1454 ufiSetEBit = setEBit;
1455 ufiNeedExtendedCodeWordsEpilogCount = needExtendedCodeWordsEpilogCount;
1456 ufiCodeWords = codeWords;
1457 ufiEpilogScopes = epilogScopes;
1460 // Finalize: Prepare the unwind information for the VM. Compute and prepend the unwind header.
1462 void UnwindFragmentInfo::Finalize(UNATIVE_OFFSET functionLength)
1464 assert(ufiInitialized == UFI_INITIALIZED_PATTERN);
1467 if (0 && uwiComp->verbose)
1469 printf("*************** Before fragment #%d finalize\n", ufiNum);
1474 // Compute the header
1476 #if defined(_TARGET_ARM_)
1477 noway_assert((functionLength & 1) == 0);
1478 DWORD headerFunctionLength = functionLength / 2;
1479 #elif defined(_TARGET_ARM64_)
1480 noway_assert((functionLength & 3) == 0);
1481 DWORD headerFunctionLength = functionLength / 4;
1482 #endif // _TARGET_ARM64_
1484 DWORD headerVers = 0; // Version of the unwind info is zero. No other version number is currently defined.
1485 DWORD headerXBit = 0; // We never generate "exception data", but the VM might add some.
1487 #if defined(_TARGET_ARM_)
1488 DWORD headerFBit = ufiHasPhantomProlog ? 1 : 0; // Is this data a fragment in the sense of the unwind data
1489 // specification? That is, do the prolog codes represent a real
1491 #endif // defined(_TARGET_ARM_)
1492 DWORD headerEpilogCount; // This depends on how we set headerEBit.
1493 DWORD headerCodeWords;
1494 DWORD headerExtendedEpilogCount = 0; // This depends on how we set headerEBit.
1495 DWORD headerExtendedCodeWords = 0;
1500 headerEpilogCount = ufiEpilogList->GetStartIndex(); // probably zero -- the start of the prolog codes!
1501 headerCodeWords = ufiCodeWords;
1507 if (ufiNeedExtendedCodeWordsEpilogCount)
1509 headerEpilogCount = 0;
1510 headerCodeWords = 0;
1511 headerExtendedEpilogCount = ufiEpilogScopes;
1512 headerExtendedCodeWords = ufiCodeWords;
1516 headerEpilogCount = ufiEpilogScopes;
1517 headerCodeWords = ufiCodeWords;
1521 // Start writing the header
1523 noway_assert(headerFunctionLength <=
1524 0x3FFFFU); // We create fragments to prevent this from firing, so if it hits, we have an internal error
1526 if ((headerEpilogCount > UW_MAX_EPILOG_COUNT) || (headerCodeWords > UW_MAX_CODE_WORDS_COUNT))
1528 IMPL_LIMITATION("unwind data too large");
1531 #if defined(_TARGET_ARM_)
1532 DWORD header = headerFunctionLength | (headerVers << 18) | (headerXBit << 20) | (headerEBit << 21) |
1533 (headerFBit << 22) | (headerEpilogCount << 23) | (headerCodeWords << 28);
1534 #elif defined(_TARGET_ARM64_)
1535 DWORD header = headerFunctionLength | (headerVers << 18) | (headerXBit << 20) | (headerEBit << 21) |
1536 (headerEpilogCount << 22) | (headerCodeWords << 27);
1537 #endif // defined(_TARGET_ARM64_)
1539 ufiPrologCodes.AddHeaderWord(header);
1541 // Construct the second header word, if needed
1543 if (ufiNeedExtendedCodeWordsEpilogCount)
1545 noway_assert(headerEBit == 0);
1546 noway_assert(headerEpilogCount == 0);
1547 noway_assert(headerCodeWords == 0);
1548 noway_assert((headerExtendedEpilogCount > UW_MAX_EPILOG_COUNT) ||
1549 (headerExtendedCodeWords > UW_MAX_CODE_WORDS_COUNT));
1551 if ((headerExtendedEpilogCount > UW_MAX_EXTENDED_EPILOG_COUNT) ||
1552 (headerExtendedCodeWords > UW_MAX_EXTENDED_CODE_WORDS_COUNT))
1554 IMPL_LIMITATION("unwind data too large");
1557 DWORD header2 = headerExtendedEpilogCount | (headerExtendedCodeWords << 16);
1559 ufiPrologCodes.AddHeaderWord(header2);
1562 // Construct the epilog scope words, if needed
1566 for (UnwindEpilogInfo* pEpi = ufiEpilogList; pEpi != NULL; pEpi = pEpi->epiNext)
1568 #if defined(_TARGET_ARM_)
1569 DWORD headerCondition = 0xE; // The epilog is unconditional. We don't have epilogs under the IT instruction.
1570 #endif // defined(_TARGET_ARM_)
1572 // The epilog must strictly follow the prolog. The prolog is in the first fragment of
1573 // the hot section. If this epilog is at the start of a fragment, it can't be the
1574 // first fragment in the hot section. We actually don't know if we're processing
1575 // the hot or cold section (or a funclet), so we can't distinguish these cases. Thus,
1576 // we just assert that the epilog starts within the fragment.
1577 assert(pEpi->GetStartOffset() >= GetStartOffset());
1579 // We report the offset of an epilog as the offset from the beginning of the function/funclet fragment,
1580 // NOT the offset from the beginning of the main function.
1581 DWORD headerEpilogStartOffset = pEpi->GetStartOffset() - GetStartOffset();
1583 #if defined(_TARGET_ARM_)
1584 noway_assert((headerEpilogStartOffset & 1) == 0);
1585 headerEpilogStartOffset /= 2; // The unwind data stores the actual offset divided by 2 (since the low bit of
1586 // the actual offset is always zero)
1587 #elif defined(_TARGET_ARM64_)
1588 noway_assert((headerEpilogStartOffset & 3) == 0);
1589 headerEpilogStartOffset /= 4; // The unwind data stores the actual offset divided by 4 (since the low 2 bits
1590 // of the actual offset is always zero)
1591 #endif // defined(_TARGET_ARM64_)
1593 DWORD headerEpilogStartIndex = pEpi->GetStartIndex();
1595 if ((headerEpilogStartOffset > UW_MAX_EPILOG_START_OFFSET) ||
1596 (headerEpilogStartIndex > UW_MAX_EPILOG_START_INDEX))
1598 IMPL_LIMITATION("unwind data too large");
1601 #if defined(_TARGET_ARM_)
1602 DWORD epilogScopeWord = headerEpilogStartOffset | (headerCondition << 20) | (headerEpilogStartIndex << 24);
1603 #elif defined(_TARGET_ARM64_)
1604 DWORD epilogScopeWord = headerEpilogStartOffset | (headerEpilogStartIndex << 22);
1605 #endif // defined(_TARGET_ARM64_)
1607 ufiPrologCodes.AddHeaderWord(epilogScopeWord);
1611 // The unwind code words are already here, following the header, so we're done!
1614 void UnwindFragmentInfo::Reserve(BOOL isFunclet, bool isHotCode)
1616 assert(isHotCode || !isFunclet); // TODO-CQ: support hot/cold splitting in functions with EH
1620 BOOL isColdCode = isHotCode ? FALSE : TRUE;
1622 ULONG unwindSize = Size();
1625 if (uwiComp->verbose)
1628 printf("reserveUnwindInfo: fragment #%d:\n", ufiNum);
1632 uwiComp->eeReserveUnwindInfo(isFunclet, isColdCode, unwindSize);
1635 // Allocate the unwind info for a fragment with the VM.
1637 // funKind: funclet kind
1638 // pHotCode: hot section code buffer
1639 // pColdCode: cold section code buffer
1640 // funcEndOffset: offset of the end of this function/funclet. Used if this fragment is the last one for a
1641 // function/funclet.
1642 // isHotCode: are we allocating the unwind info for the hot code section?
1644 void UnwindFragmentInfo::Allocate(
1645 CorJitFuncKind funKind, void* pHotCode, void* pColdCode, UNATIVE_OFFSET funcEndOffset, bool isHotCode)
1647 UNATIVE_OFFSET startOffset;
1648 UNATIVE_OFFSET endOffset;
1649 UNATIVE_OFFSET codeSize;
1651 // We don't support hot/cold splitting with EH, so if there is cold code, this
1652 // better not be a funclet!
1653 // TODO-CQ: support funclets in cold code
1655 noway_assert(isHotCode || funKind == CORJIT_FUNC_ROOT);
1657 // Compute the final size, and start and end offsets of the fragment
1659 startOffset = GetStartOffset();
1661 if (ufiNext == NULL)
1663 // This is the last fragment, so the fragment extends to the end of the function/fragment.
1664 assert(funcEndOffset != 0);
1665 endOffset = funcEndOffset;
1669 // The fragment length is all the code between the beginning of this fragment
1670 // and the beginning of the next fragment. Note that all fragments have had their
1671 // offsets computed before any fragment is allocated.
1672 endOffset = ufiNext->GetStartOffset();
1675 assert(endOffset > startOffset);
1676 codeSize = endOffset - startOffset;
1678 // Finalize the fragment unwind block to hand to the VM
1682 // Get the final unwind information and hand it to the VM
1684 ULONG unwindBlockSize;
1687 GetFinalInfo(&pUnwindBlock, &unwindBlockSize);
1690 if (uwiComp->opts.dspUnwind)
1692 DumpUnwindInfo(uwiComp, isHotCode, startOffset, endOffset, pUnwindBlock, unwindBlockSize);
1696 // Adjust for cold or hot code:
1697 // 1. The VM doesn't want the cold code pointer unless this is cold code.
1698 // 2. The startOffset and endOffset need to be from the base of the hot section for hot code
1699 // and from the base of the cold section for cold code
1703 assert(endOffset <= uwiComp->info.compTotalHotCodeSize);
1708 assert(startOffset >= uwiComp->info.compTotalHotCodeSize);
1709 startOffset -= uwiComp->info.compTotalHotCodeSize;
1710 endOffset -= uwiComp->info.compTotalHotCodeSize;
1714 if (uwiComp->verbose)
1717 printf("unwindEmit: fragment #%d:\n", ufiNum);
1721 uwiComp->eeAllocUnwindInfo((BYTE*)pHotCode, (BYTE*)pColdCode, startOffset, endOffset, unwindBlockSize, pUnwindBlock,
1726 void UnwindFragmentInfo::Dump(int indent)
1729 UnwindEpilogInfo* pEpi;
1732 for (pEpi = ufiEpilogList; pEpi != NULL; pEpi = pEpi->epiNext)
1737 printf("%*sUnwindFragmentInfo #%d, @0x%08p, size:%d:\n", indent, "", ufiNum, dspPtr(this), sizeof(*this));
1738 printf("%*s uwiComp: 0x%08p\n", indent, "", dspPtr(uwiComp));
1739 printf("%*s ufiNext: 0x%08p\n", indent, "", dspPtr(ufiNext));
1740 printf("%*s ufiEmitLoc: 0x%08p\n", indent, "", dspPtr(ufiEmitLoc));
1741 printf("%*s ufiHasPhantomProlog: %s\n", indent, "", dspBool(ufiHasPhantomProlog));
1742 printf("%*s %d epilog%s\n", indent, "", count, (count != 1) ? "s" : "");
1743 printf("%*s ufiEpilogList: 0x%08p\n", indent, "", dspPtr(ufiEpilogList));
1744 printf("%*s ufiEpilogLast: 0x%08p\n", indent, "", dspPtr(ufiEpilogLast));
1745 printf("%*s ufiCurCodes: 0x%08p\n", indent, "", dspPtr(ufiCurCodes));
1746 printf("%*s ufiSize: %u\n", indent, "", ufiSize);
1747 printf("%*s ufiSetEBit: %s\n", indent, "", dspBool(ufiSetEBit));
1748 printf("%*s ufiNeedExtendedCodeWordsEpilogCount: %s\n", indent, "", dspBool(ufiNeedExtendedCodeWordsEpilogCount));
1749 printf("%*s ufiCodeWords: %u\n", indent, "", ufiCodeWords);
1750 printf("%*s ufiEpilogScopes: %u\n", indent, "", ufiEpilogScopes);
1751 printf("%*s ufiStartOffset: 0x%x\n", indent, "", ufiStartOffset);
1752 printf("%*s ufiInProlog: %s\n", indent, "", dspBool(ufiInProlog));
1753 printf("%*s ufiInitialized: 0x%08x\n", indent, "", ufiInitialized);
1755 ufiPrologCodes.Dump(indent + 2);
1757 for (pEpi = ufiEpilogList; pEpi != NULL; pEpi = pEpi->epiNext)
1759 pEpi->Dump(indent + 2);
1764 ///////////////////////////////////////////////////////////////////////////////
1768 ///////////////////////////////////////////////////////////////////////////////
1770 void UnwindInfo::InitUnwindInfo(Compiler* comp, emitLocation* startLoc, emitLocation* endLoc)
1774 // The first fragment is a member of UnwindInfo, so it doesn't need to be allocated.
1775 // However, its constructor needs to be explicitly called, since the constructor for
1776 // UnwindInfo is not called.
1778 uwiFragmentFirst.UnwindFragmentInfo::UnwindFragmentInfo(comp, startLoc, false);
1780 uwiFragmentLast = &uwiFragmentFirst;
1784 // Allocate an emitter location object. It is initialized to something
1785 // invalid: it has a null 'ig' that needs to get set before it can be used.
1786 // Note that when we create an UnwindInfo for the cold section, this never
1787 // gets initialized with anything useful, since we never add unwind codes
1788 // to the cold section; we simply distribute the existing (previously added) codes.
1789 uwiCurLoc = new (uwiComp, CMK_UnwindInfo) emitLocation();
1792 uwiInitialized = UWI_INITIALIZED_PATTERN;
1793 uwiAddingNOP = false;
1797 // Split the unwind codes in 'puwi' into those that are in the hot section (leave them in 'puwi')
1798 // and those that are in the cold section (move them to 'this'). There is exactly one fragment
1799 // in each UnwindInfo; the fragments haven't been split for size, yet.
1801 void UnwindInfo::HotColdSplitCodes(UnwindInfo* puwi)
1803 // Ensure that there is exactly a single fragment in both the hot and the cold sections
1804 assert(&uwiFragmentFirst == uwiFragmentLast);
1805 assert(&puwi->uwiFragmentFirst == puwi->uwiFragmentLast);
1806 assert(uwiFragmentLast->ufiNext == NULL);
1807 assert(puwi->uwiFragmentLast->ufiNext == NULL);
1809 // The real prolog is in the hot section, so this, cold, section has a phantom prolog
1810 uwiFragmentLast->ufiHasPhantomProlog = true;
1811 uwiFragmentLast->CopyPrologCodes(puwi->uwiFragmentLast);
1813 // Now split the epilog codes
1814 uwiFragmentLast->SplitEpilogCodes(uwiFragmentLast->ufiEmitLoc, puwi->uwiFragmentLast);
1817 // Split the function or funclet into fragments that are no larger than 512K,
1818 // so the fragment size will fit in the unwind data "Function Length" field.
1819 // The ARM Exception Data specification "Function Fragments" section describes this.
1820 // We split the function so that it is no larger than 512K bytes, or the value of
1821 // the COMPlus_JitSplitFunctionSize value, if defined (and smaller). We must determine
1822 // how to split the function/funclet before we issue the instructions, so we can
1823 // reserve the unwind space with the VM. The instructions issued may shrink (but not
1824 // expand!) during issuing (although this is extremely rare in any case, and may not
1825 // actually occur on ARM), so we don't finalize actual sizes or offsets.
1827 // ARM64 has very similar limitations, except functions can be up to 1MB. TODO-ARM64-Bug?: make sure this works!
1829 // We don't split any prolog or epilog. Ideally, we might not split an instruction,
1830 // although that doesn't matter because the unwind at any point would still be
1833 void UnwindInfo::Split()
1835 UNATIVE_OFFSET maxFragmentSize; // The maximum size of a code fragment in bytes
1837 maxFragmentSize = UW_MAX_FRAGMENT_SIZE_BYTES;
1840 // Consider COMPlus_JitSplitFunctionSize
1841 unsigned splitFunctionSize = (unsigned)JitConfig.JitSplitFunctionSize();
1843 if (splitFunctionSize != 0)
1844 if (splitFunctionSize < maxFragmentSize)
1845 maxFragmentSize = splitFunctionSize;
1848 // Now, there should be exactly one fragment.
1850 assert(uwiFragmentLast != NULL);
1851 assert(uwiFragmentLast == &uwiFragmentFirst);
1852 assert(uwiFragmentLast->ufiNext == NULL);
1854 // Find the code size of this function/funclet.
1856 UNATIVE_OFFSET startOffset;
1857 UNATIVE_OFFSET endOffset;
1858 UNATIVE_OFFSET codeSize;
1860 if (uwiFragmentLast->ufiEmitLoc == NULL)
1862 // NULL emit location means the beginning of the code. This is to handle the first fragment prolog.
1867 startOffset = uwiFragmentLast->ufiEmitLoc->CodeOffset(uwiComp->genEmitter);
1870 if (uwiEndLoc == NULL)
1872 // Note that compTotalHotCodeSize and compTotalColdCodeSize are computed before issuing instructions
1873 // from the emitter instruction group offsets, and will be accurate unless the issued code shrinks.
1874 // compNativeCodeSize is precise, but is only set after instructions are issued, which is too late
1875 // for us, since we need to decide how many fragments we need before the code memory is allocated
1876 // (which is before instruction issuing).
1877 UNATIVE_OFFSET estimatedTotalCodeSize =
1878 uwiComp->info.compTotalHotCodeSize + uwiComp->info.compTotalColdCodeSize;
1879 assert(estimatedTotalCodeSize != 0);
1880 endOffset = estimatedTotalCodeSize;
1884 endOffset = uwiEndLoc->CodeOffset(uwiComp->genEmitter);
1887 assert(endOffset > startOffset); // there better be at least 1 byte of code
1888 codeSize = endOffset - startOffset;
1890 // Now that we know the code size for this section (main function hot or cold, or funclet),
1891 // figure out how many fragments we're going to need.
1893 UNATIVE_OFFSET numberOfFragments = (codeSize + maxFragmentSize - 1) / maxFragmentSize; // round up
1894 assert(numberOfFragments > 0);
1896 if (numberOfFragments == 1)
1898 // No need to split; we're done
1902 // Now, we're going to commit to splitting the function into "numberOfFragments" fragments,
1903 // for the purpose of unwind information. We need to do the actual splits so we can figure out
1904 // the size of each piece of unwind data for the call to reserveUnwindInfo(). We won't know
1905 // the actual offsets of the splits since we haven't issued the instructions yet, so store
1906 // an emitter location instead of an offset, and "finalize" the offset in the unwindEmit() phase,
1907 // like we do for the function length and epilog offsets.
1908 CLANG_FORMAT_COMMENT_ANCHOR;
1911 if (uwiComp->verbose)
1913 printf("Split unwind info into %d fragments (function/funclet size: %d, maximum fragment size: %d)\n",
1914 numberOfFragments, codeSize, maxFragmentSize);
1918 // Call the emitter to do the split, and call us back for every split point it chooses.
1919 uwiComp->genEmitter->emitSplit(uwiFragmentLast->ufiEmitLoc, uwiEndLoc, maxFragmentSize, (void*)this,
1923 // Did the emitter split the function/funclet into as many fragments as we asked for?
1924 // It might be fewer if the COMPlus_JitSplitFunctionSize was used, but it better not
1925 // be fewer if we're splitting into 512K blocks!
1927 unsigned fragCount = 0;
1928 for (UnwindFragmentInfo* pFrag = &uwiFragmentFirst; pFrag != NULL; pFrag = pFrag->ufiNext)
1932 if (fragCount < numberOfFragments)
1934 if (uwiComp->verbose)
1936 printf("WARNING: asked the emitter for %d fragments, but only got %d\n", numberOfFragments, fragCount);
1939 // If this fires, then we split into fewer fragments than we asked for, and we are using
1940 // the default, unwind-data-defined 512K maximum fragment size. We won't be able to fit
1941 // this fragment into the unwind data! If you set COMPlus_JitSplitFunctionSize to something
1942 // small, we might not be able to split into as many fragments as asked for, because we
1943 // can't split prologs or epilogs.
1944 assert(maxFragmentSize != UW_MAX_FRAGMENT_SIZE_BYTES);
1949 /*static*/ void UnwindInfo::EmitSplitCallback(void* context, emitLocation* emitLoc)
1951 UnwindInfo* puwi = (UnwindInfo*)context;
1952 puwi->AddFragment(emitLoc);
1955 // Reserve space for the unwind info for all fragments
1957 void UnwindInfo::Reserve(BOOL isFunclet, bool isHotCode)
1959 assert(uwiInitialized == UWI_INITIALIZED_PATTERN);
1960 assert(isHotCode || !isFunclet);
1962 for (UnwindFragmentInfo* pFrag = &uwiFragmentFirst; pFrag != NULL; pFrag = pFrag->ufiNext)
1964 pFrag->Reserve(isFunclet, isHotCode);
1968 // Allocate and populate VM unwind info for all fragments
1970 void UnwindInfo::Allocate(CorJitFuncKind funKind, void* pHotCode, void* pColdCode, bool isHotCode)
1972 assert(uwiInitialized == UWI_INITIALIZED_PATTERN);
1974 UnwindFragmentInfo* pFrag;
1976 // First, finalize all the offsets (the location of the beginning of fragments, and epilogs),
1977 // so a fragment can use the finalized offset of the subsequent fragment to determine its code size.
1979 UNATIVE_OFFSET endOffset;
1981 if (uwiEndLoc == NULL)
1983 assert(uwiComp->info.compNativeCodeSize != 0);
1984 endOffset = uwiComp->info.compNativeCodeSize;
1988 endOffset = uwiEndLoc->CodeOffset(uwiComp->genEmitter);
1991 for (pFrag = &uwiFragmentFirst; pFrag != NULL; pFrag = pFrag->ufiNext)
1993 pFrag->FinalizeOffset();
1996 for (pFrag = &uwiFragmentFirst; pFrag != NULL; pFrag = pFrag->ufiNext)
1998 pFrag->Allocate(funKind, pHotCode, pColdCode, endOffset, isHotCode);
2002 void UnwindInfo::AddEpilog()
2004 assert(uwiInitialized == UWI_INITIALIZED_PATTERN);
2005 assert(uwiFragmentLast != NULL);
2006 uwiFragmentLast->AddEpilog();
2010 #if defined(_TARGET_ARM_)
2012 unsigned UnwindInfo::GetInstructionSize()
2014 assert(uwiInitialized == UWI_INITIALIZED_PATTERN);
2015 return uwiComp->genEmitter->emitGetInstructionSize(uwiCurLoc);
2018 #endif // defined(_TARGET_ARM_)
2020 void UnwindInfo::CaptureLocation()
2022 assert(uwiInitialized == UWI_INITIALIZED_PATTERN);
2023 assert(uwiCurLoc != NULL);
2024 uwiCurLoc->CaptureLocation(uwiComp->genEmitter);
2027 void UnwindInfo::AddFragment(emitLocation* emitLoc)
2029 assert(uwiInitialized == UWI_INITIALIZED_PATTERN);
2030 assert(uwiFragmentLast != NULL);
2032 UnwindFragmentInfo* newFrag = new (uwiComp, CMK_UnwindInfo) UnwindFragmentInfo(uwiComp, emitLoc, true);
2035 newFrag->ufiNum = uwiFragmentLast->ufiNum + 1;
2038 newFrag->CopyPrologCodes(&uwiFragmentFirst);
2039 newFrag->SplitEpilogCodes(emitLoc, uwiFragmentLast);
2041 // Link the new fragment in at the end of the fragment list
2042 uwiFragmentLast->ufiNext = newFrag;
2043 uwiFragmentLast = newFrag;
2048 #if defined(_TARGET_ARM_)
2050 // Given the first byte of the unwind code, check that its opsize matches
2051 // the last instruction added in the emitter.
2052 void UnwindInfo::CheckOpsize(BYTE b1)
2054 // Adding NOP padding goes through the same path, but doesn't update the location to indicate
2055 // the correct location of the instruction for which we are adding a NOP, so just skip the
2056 // assert. Should be ok, because the emitter is telling us the size of the instruction for
2057 // which we are adding the NOP.
2061 unsigned opsizeInBytes = GetOpcodeSizeFromUnwindHeader(b1);
2062 unsigned instrSizeInBytes = GetInstructionSize();
2063 assert(opsizeInBytes == instrSizeInBytes);
2066 #endif // defined(_TARGET_ARM_)
2068 void UnwindInfo::Dump(bool isHotCode, int indent)
2071 UnwindFragmentInfo* pFrag;
2074 for (pFrag = &uwiFragmentFirst; pFrag != NULL; pFrag = pFrag->ufiNext)
2079 printf("%*sUnwindInfo %s@0x%08p, size:%d:\n", indent, "", isHotCode ? "" : "COLD ", dspPtr(this), sizeof(*this));
2080 printf("%*s uwiComp: 0x%08p\n", indent, "", dspPtr(uwiComp));
2081 printf("%*s %d fragment%s\n", indent, "", count, (count != 1) ? "s" : "");
2082 printf("%*s uwiFragmentLast: 0x%08p\n", indent, "", dspPtr(uwiFragmentLast));
2083 printf("%*s uwiEndLoc: 0x%08p\n", indent, "", dspPtr(uwiEndLoc));
2084 printf("%*s uwiInitialized: 0x%08x\n", indent, "", uwiInitialized);
2086 for (pFrag = &uwiFragmentFirst; pFrag != NULL; pFrag = pFrag->ufiNext)
2088 pFrag->Dump(indent + 2);
2094 #if defined(_TARGET_ARM_)
2096 /*XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
2097 XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
2101 XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
2102 XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
2107 // start is 0-based index from LSB, length is number of bits
2108 DWORD ExtractBits(DWORD dw, DWORD start, DWORD length)
2110 return (dw >> start) & ((1 << length) - 1);
2113 // Dump an integer register set. 'x' is an array of bits where bit 0 = r0, bit 1 = r1, etc.
2114 // The highest register considered is r12.
2115 // If 'lr' is non-zero, the "lr" register is emitted last.
2116 // Returns the number of characters printed.
2117 DWORD DumpIntRegSet(DWORD x, DWORD lr)
2119 assert(x != 0 || lr != 0); // we must have one
2120 assert((x & 0xE000) == 0); // don't handle r13 (sp), r14 (lr), r15 (pc) in 'x'
2127 for (DWORD bitNum = 0; bitNum < 12; bitNum++)
2136 printf("r%u", bitNum);
2137 printed += (bitNum < 10) ? 2 : 3;
2158 // Dump a register set range from register 'start' to register 'end'.
2159 // rtype should be "r" or "d" to indicate register type.
2160 // If 'lr' is non-zero, the "lr" register is emitted last. (Note that
2161 // 'lr' should be zero for rtype == "d".)
2162 // Returns the number of characters printed.
2163 DWORD DumpRegSetRange(const char* const rtype, DWORD start, DWORD end, DWORD lr)
2165 assert(start <= end);
2167 DWORD rtypeLen = strlen(rtype);
2172 for (DWORD reg = start; reg <= end; reg++)
2179 printf("%s%u", rtype, reg);
2180 printed += rtypeLen + ((reg < 10) ? 1 : 2);
2185 assert(!first); // If 'lr' is set, it can't be first, since we require a non-empty range
2196 // Returns the number of characters printed.
2197 DWORD DumpOpsize(DWORD padding, DWORD opsize)
2199 if (padding > 100) // underflow?
2201 DWORD printed = padding;
2202 for (; padding > 0; padding--)
2204 printf("; opsize %d\n", opsize);
2205 return printed + 11; // assumes opsize is always 2 digits
2208 // Dump the unwind data.
2210 // isHotCode: true if this unwind data is for the hot section
2211 // startOffset: byte offset of the code start that this unwind data represents
2212 // endOffset: byte offset of the code end that this unwind data represents
2213 // pHeader: pointer to the unwind data blob
2214 // unwindBlockSize: size in bytes of the unwind data blob
2216 void DumpUnwindInfo(Compiler* comp,
2218 UNATIVE_OFFSET startOffset,
2219 UNATIVE_OFFSET endOffset,
2220 const BYTE* const pHeader,
2221 ULONG unwindBlockSize)
2223 printf("Unwind Info%s:\n", isHotCode ? "" : " COLD");
2225 // pHeader is not guaranteed to be aligned. We put four 0xFF end codes at the end
2226 // to provide padding, and round down to get a multiple of 4 bytes in size.
2227 DWORD UNALIGNED* pdw = (DWORD UNALIGNED*)pHeader;
2232 DWORD codeWords = ExtractBits(dw, 28, 4);
2233 DWORD epilogCount = ExtractBits(dw, 23, 5);
2234 DWORD FBit = ExtractBits(dw, 22, 1);
2235 DWORD EBit = ExtractBits(dw, 21, 1);
2236 DWORD XBit = ExtractBits(dw, 20, 1);
2237 DWORD Vers = ExtractBits(dw, 18, 2);
2238 DWORD functionLength = ExtractBits(dw, 0, 18);
2240 printf(" >> Start offset : 0x%06x (not in unwind data)\n", comp->dspOffset(startOffset));
2241 printf(" >> End offset : 0x%06x (not in unwind data)\n", comp->dspOffset(endOffset));
2242 printf(" Code Words : %u\n", codeWords);
2243 printf(" Epilog Count : %u\n", epilogCount);
2244 printf(" F bit : %u\n", FBit);
2245 printf(" E bit : %u\n", EBit);
2246 printf(" X bit : %u\n", XBit);
2247 printf(" Vers : %u\n", Vers);
2248 printf(" Function Length : %u (0x%05x) Actual length = %u (0x%06x)\n", functionLength, functionLength,
2249 functionLength * 2, functionLength * 2);
2251 assert(functionLength * 2 == endOffset - startOffset);
2253 if (codeWords == 0 && epilogCount == 0)
2255 // We have an extension word specifying a larger number of Code Words or Epilog Counts
2256 // than can be specified in the header word.
2260 codeWords = ExtractBits(dw, 16, 8);
2261 epilogCount = ExtractBits(dw, 0, 16);
2262 assert((dw & 0xF0000000) == 0); // reserved field should be zero
2264 printf(" ---- Extension word ----\n");
2265 printf(" Extended Code Words : %u\n", codeWords);
2266 printf(" Extended Epilog Count : %u\n", epilogCount);
2269 bool epilogStartAt[256] = {}; // One byte per possible epilog start index; initialized to false
2273 // We have an array of epilog scopes
2275 printf(" ---- Epilog scopes ----\n");
2276 if (epilogCount == 0)
2278 printf(" No epilogs\n");
2282 for (DWORD scope = 0; scope < epilogCount; scope++)
2286 DWORD epilogStartOffset = ExtractBits(dw, 0, 18);
2287 DWORD res = ExtractBits(dw, 18, 2);
2288 DWORD condition = ExtractBits(dw, 20, 4);
2289 DWORD epilogStartIndex = ExtractBits(dw, 24, 8);
2291 // Note that epilogStartOffset for a funclet is the offset from the beginning
2292 // of the current funclet, not the offset from the beginning of the main function.
2293 // To help find it when looking through JitDump output, also show the offset from
2294 // the beginning of the main function.
2295 DWORD epilogStartOffsetFromMainFunctionBegin = epilogStartOffset * 2 + startOffset;
2299 printf(" ---- Scope %d\n", scope);
2300 printf(" Epilog Start Offset : %u (0x%05x) Actual offset = %u (0x%06x) Offset from main "
2301 "function begin = %u (0x%06x)\n",
2302 comp->dspOffset(epilogStartOffset), comp->dspOffset(epilogStartOffset),
2303 comp->dspOffset(epilogStartOffset * 2), comp->dspOffset(epilogStartOffset * 2),
2304 comp->dspOffset(epilogStartOffsetFromMainFunctionBegin),
2305 comp->dspOffset(epilogStartOffsetFromMainFunctionBegin));
2306 printf(" Condition : %u (0x%x)%s\n", condition, condition,
2307 (condition == 0xE) ? " (always)" : "");
2308 printf(" Epilog Start Index : %u (0x%02x)\n", epilogStartIndex, epilogStartIndex);
2310 epilogStartAt[epilogStartIndex] = true; // an epilog starts at this offset in the unwind codes
2316 printf(" --- One epilog, unwind codes at %u\n", epilogCount);
2317 assert(epilogCount < _countof(epilogStartAt));
2318 epilogStartAt[epilogCount] = true; // the one and only epilog starts its unwind codes at this offset
2323 printf(" ---- Note: 'F' bit is set. Prolog codes are for a 'phantom' prolog.\n");
2326 // Dump the unwind codes
2328 printf(" ---- Unwind codes ----\n");
2330 DWORD countOfUnwindCodes = codeWords * 4;
2331 PBYTE pUnwindCode = (PBYTE)pdw;
2332 BYTE b1, b2, b3, b4;
2337 for (DWORD i = 0; i < countOfUnwindCodes; i++)
2339 // Does this byte start an epilog sequence? If so, note that fact.
2340 if (epilogStartAt[i])
2342 printf(" ---- Epilog start at index %u ----\n", i);
2345 b1 = *pUnwindCode++;
2347 if ((b1 & 0x80) == 0)
2349 // 00-7F : add sp, sp, #X*4 (opsize 16)
2351 printf(" %02X add sp, sp, #%-8d", b1, x * 4);
2352 DumpOpsize(opCol - 37, 16);
2354 else if ((b1 & 0xC0) == 0x80)
2356 // 80-BF : pop {r0-r12,lr} (X = bitmask) (opsize 32)
2357 assert(i + 1 < countOfUnwindCodes);
2358 b2 = *pUnwindCode++;
2361 DWORD LBit = ExtractBits(b1, 5, 1);
2362 x = ((DWORD)(b1 & 0x1F) << 8) | (DWORD)b2;
2364 printf(" %02X %02X pop ", b1, b2);
2366 printed += DumpIntRegSet(x, LBit);
2367 DumpOpsize(opCol - printed, 32);
2369 else if ((b1 & 0xF0) == 0xC0)
2371 // C0-CF : mov sp, rX (X=0-15) (opsize 16)
2373 printf(" %02X mov sp, r%u", b1, x);
2374 printed = 25 + ((x > 10) ? 2 : 1);
2375 DumpOpsize(opCol - printed, 16);
2377 else if ((b1 & 0xF8) == 0xD0)
2379 // D0-D7 : pop {r4-rX,lr} (X=4-7) (opsize 16)
2381 DWORD LBit = b1 & 0x4;
2382 printf(" %02X pop ", b1);
2384 printed += DumpRegSetRange("r", 4, x + 4, LBit);
2385 DumpOpsize(opCol - printed, 16);
2387 else if ((b1 & 0xF8) == 0xD8)
2389 // D8-DF : pop {r4-rX,lr} (X=8-11) (opsize 32)
2391 DWORD LBit = b1 & 0x4;
2392 printf(" %02X pop ", b1);
2394 printed += DumpRegSetRange("r", 4, x + 8, LBit);
2395 DumpOpsize(opCol - printed, 32);
2397 else if ((b1 & 0xF8) == 0xE0)
2399 // E0-E7 : vpop {d8-dX} (X=8-15) (opsize 32)
2401 printf(" %02X vpop ", b1);
2403 printed += DumpRegSetRange("d", 8, x + 8, 0);
2404 DumpOpsize(opCol - printed, 32);
2406 else if ((b1 & 0xFC) == 0xE8)
2408 // E8-EB : addw sp, sp, #X*4 (opsize 32)
2409 assert(i + 1 < countOfUnwindCodes);
2410 b2 = *pUnwindCode++;
2413 x = ((DWORD)(b1 & 0x3) << 8) | (DWORD)b2;
2415 printf(" %02X %02X addw sp, sp, #%-8u", b1, b2, x * 4);
2416 DumpOpsize(opCol - 38, 32);
2418 else if ((b1 & 0xFE) == 0xEC)
2420 // EC-ED : pop {r0-r7,lr} (X = bitmask) (opsize 16)
2421 assert(i + 1 < countOfUnwindCodes);
2422 b2 = *pUnwindCode++;
2425 DWORD LBit = ExtractBits(b1, 0, 1);
2428 printf(" %02X %02X pop ", b1, b2);
2430 printed += DumpIntRegSet(x, LBit);
2431 DumpOpsize(opCol - printed, 16);
2433 else if (b1 == 0xEE)
2435 assert(i + 1 < countOfUnwindCodes);
2436 b2 = *pUnwindCode++;
2439 if ((b2 & 0xF0) == 0)
2441 // EE/0x (opsize 16)
2443 printf(" %02X %02X Microsoft-specific (x = %02X)", b1, b2, x);
2448 // EE/xy (opsize 16)
2449 x = ExtractBits(b2, 4, 4);
2450 y = ExtractBits(b2, 0, 4);
2451 printf(" %02X %02X Available (x = %02X, y = %02X)", b1, b2, x, y);
2455 else if (b1 == 0xEF)
2457 assert(i + 1 < countOfUnwindCodes);
2458 b2 = *pUnwindCode++;
2461 if ((b2 & 0xF0) == 0)
2463 // EF/0x : ldr lr, [sp], #X*4 (opsize 32)
2465 printf(" %02X %02X ldr lr, [sp], #%-8u", b1, b2, x * 4);
2466 DumpOpsize(opCol - 39, 32);
2470 // EF/xy (opsize 32)
2471 x = ExtractBits(b2, 4, 4);
2472 y = ExtractBits(b2, 0, 4);
2473 printf(" %02X %02X Available (x = %02X, y = %02X)", b1, b2, x, y);
2477 else if ((b1 & 0xF7) == 0xF0)
2481 printf(" %02X Available (x = %02X)\n", b1, x);
2483 else if (b1 == 0xF5)
2485 // F5 : vpop {dS-dE} (opsize 32)
2487 assert(i + 1 < countOfUnwindCodes);
2488 b2 = *pUnwindCode++;
2491 DWORD s = ExtractBits(b2, 4, 4);
2492 DWORD e = ExtractBits(b2, 0, 4);
2494 printf(" %02X %02X vpop ", b1, b2);
2496 printed += DumpRegSetRange("d", s, e, 0);
2497 DumpOpsize(opCol - printed, 32);
2499 else if (b1 == 0xF6)
2501 // F6 : vpop {d(S+16)-d(E+16)} (opsize 32)
2503 assert(i + 1 < countOfUnwindCodes);
2504 b2 = *pUnwindCode++;
2507 DWORD s = ExtractBits(b2, 4, 4);
2508 DWORD e = ExtractBits(b2, 0, 4);
2510 printf(" %02X %02X vpop ", b1, b2);
2512 printed += DumpRegSetRange("d", s + 16, e + 16, 0);
2513 DumpOpsize(opCol - printed, 32);
2515 else if (b1 == 0xF7 || b1 == 0xF9)
2517 // F7, F9 : add sp, sp, #X*4
2518 // 0xF7 has opsize 16, 0xF9 has opsize 32
2520 assert(i + 2 < countOfUnwindCodes);
2521 b2 = *pUnwindCode++;
2522 b3 = *pUnwindCode++;
2525 x = ((DWORD)b2 << 8) | (DWORD)b3;
2527 opsize = (b1 == 0xF7) ? 16 : 32;
2529 printf(" %02X %02X %02X add sp, sp, #%-8u", b1, b2, b3, x * 4, opsize);
2530 DumpOpsize(opCol - 37, opsize);
2532 else if (b1 == 0xF8 || b1 == 0xFA)
2534 // F8, FA : add sp, sp, #X*4
2535 // 0xF8 has opsize 16, 0xFA has opsize 32
2537 assert(i + 3 < countOfUnwindCodes);
2538 b2 = *pUnwindCode++;
2539 b3 = *pUnwindCode++;
2540 b4 = *pUnwindCode++;
2543 x = ((DWORD)b2 << 16) | ((DWORD)b3 << 8) | (DWORD)b4;
2545 opsize = (b1 == 0xF8) ? 16 : 32;
2547 printf(" %02X %02X %02X %02X add sp, sp, #%-8u", b1, b2, b3, b4, x * 4, opsize);
2548 DumpOpsize(opCol - 37, opsize);
2550 else if (b1 == 0xFB || b1 == 0xFC)
2553 // 0xFB has opsize 16, 0xFC has opsize 32
2555 opsize = (b1 == 0xFB) ? 16 : 32;
2557 printf(" %02X nop", b1, opsize);
2558 DumpOpsize(opCol - 19, opsize);
2560 else if (b1 == 0xFD || b1 == 0xFE)
2562 // FD, FE : end + nop
2563 // 0xFD has opsize 16, 0xFE has opsize 32
2565 opsize = (b1 == 0xFD) ? 16 : 32;
2567 printf(" %02X end + nop", b1, opsize);
2568 DumpOpsize(opCol - 25, opsize);
2570 else if (b1 == 0xFF)
2574 printf(" %02X end\n", b1);
2578 assert(!"Internal error decoding unwind codes");
2583 assert((PBYTE)pdw == pUnwindCode);
2584 assert((PBYTE)pdw == pHeader + unwindBlockSize);
2586 assert(XBit == 0); // We don't handle the case where exception data is present, such as the Exception Handler RVA
2593 #endif // defined(_TARGET_ARM_)
2595 #endif // _TARGET_ARMARCH_