78 const std::vector<unsigned> &FilterIds =
Asm->MF->getFilterIds();
80 FilterOffsets.
reserve(FilterIds.size());
83 for (
unsigned FilterId : FilterIds) {
91 unsigned SizeActions = 0;
95 const std::vector<int> &TypeIds = LPI->TypeIds;
96 unsigned NumShared = PrevLPI ?
sharedTypeIDs(LPI, PrevLPI) : 0;
97 unsigned SizeSiteActions = 0;
99 if (NumShared < TypeIds.size()) {
101 unsigned SizeActionEntry = 0;
105 unsigned SizePrevIds = PrevLPI->
TypeIds.size();
107 PrevAction = Actions.
size() - 1;
108 SizeActionEntry =
getSLEB128Size(Actions[PrevAction].NextAction) +
111 for (
unsigned j = NumShared; j != SizePrevIds; ++j) {
112 assert(PrevAction != (
unsigned)-1 &&
"PrevAction is invalid!");
113 SizeActionEntry -=
getSLEB128Size(Actions[PrevAction].ValueForTypeID);
114 SizeActionEntry += -Actions[PrevAction].NextAction;
115 PrevAction = Actions[PrevAction].Previous;
120 for (
unsigned J = NumShared, M = TypeIds.size(); J != M; ++J) {
121 int TypeID = TypeIds[J];
122 assert(-1 - TypeID < (
int)FilterOffsets.
size() &&
"Unknown filter id!");
127 int NextAction = SizeActionEntry ? -(SizeActionEntry + SizeTypeID) : 0;
129 SizeSiteActions += SizeActionEntry;
131 ActionEntry Action = { ValueForTypeID, NextAction, PrevAction };
133 PrevAction = Actions.
size() - 1;
137 FirstAction = SizeActions + SizeSiteActions - SizeActionEntry + 1;
148 SizeActions += SizeSiteActions;
381 const std::vector<const GlobalValue *> &TypeInfos = MF->
getTypeInfos();
382 const std::vector<unsigned> &FilterIds = MF->
getFilterIds();
383 const std::vector<LandingPadInfo> &PadInfos = MF->
getLandingPads();
388 LandingPads.
reserve(PadInfos.size());
394 if (LPI.LandingPadLabel && !LPI.LandingPadLabel->isDefined())
401 return L->TypeIds < R->TypeIds;
420 bool HasLEB128Directives =
Asm->MAI->hasLEB128Directives();
421 unsigned CallSiteEncoding =
423 Asm->getObjFileLowering().getCallSiteEncoding();
424 bool HaveTTData = !TypeInfos.empty() || !FilterIds.empty();
427 MCSection *LSDASection =
Asm->getObjFileLowering().getSectionForLSDA(
429 unsigned TTypeEncoding;
463 TTypeEncoding =
Asm->getObjFileLowering().getTTypeEncoding();
470 Asm->OutStreamer->switchSection(LSDASection);
475 Asm->OutContext.getOrCreateSymbol(
Twine(
"GCC_except_table")+
477 Asm->OutStreamer->emitLabel(GCCETSym);
479 CallSiteRanges.
size() > 1 ?
"action_table_base" :
"cst_end");
483 TTBaseLabel =
Asm->createTempSymbol(
"ttbase");
485 const bool VerboseAsm =
Asm->OutStreamer->isVerboseAsm();
491 auto EmitTypeTableRefAndCallSiteTableEndRef = [&]() {
492 Asm->emitEncodingByte(TTypeEncoding,
"@TType");
498 MCSymbol *TTBaseRefLabel =
Asm->createTempSymbol(
"ttbaseref");
499 Asm->emitLabelDifferenceAsULEB128(TTBaseLabel, TTBaseRefLabel);
500 Asm->OutStreamer->emitLabel(TTBaseRefLabel);
507 MCSymbol *CstBeginLabel =
Asm->createTempSymbol(
"cst_begin");
508 Asm->emitEncodingByte(CallSiteEncoding,
"Call site");
509 Asm->emitLabelDifferenceAsULEB128(CstEndLabel, CstBeginLabel);
510 Asm->OutStreamer->emitLabel(CstBeginLabel);
519 auto EmitTypeTableOffsetAndCallSiteTableOffset = [&]() {
521 "Targets supporting .uleb128 do not need to take this path.");
522 if (CallSiteRanges.
size() > 1)
524 "-fbasic-block-sections is not yet supported on "
525 "platforms that do not have general LEB128 directive support.");
538 Asm->emitEncodingByte(TTypeEncoding,
"@TType");
540 const unsigned ByteSizeOfCallSiteOffset =
550 const unsigned TypeInfoSize =
553 const uint64_t LSDASizeBeforeAlign =
555 + ByteSizeOfCallSiteOffset
559 const uint64_t LSDASizeWithoutAlign = LSDASizeBeforeAlign + TypeInfoSize;
560 const unsigned ByteSizeOfLSDAWithoutAlign =
562 const uint64_t DisplacementBeforeAlign =
564 + ByteSizeOfLSDAWithoutAlign + LSDASizeBeforeAlign;
567 const unsigned NeedAlignVal = (4 - DisplacementBeforeAlign % 4) % 4;
568 uint64_t LSDASizeWithAlign = LSDASizeWithoutAlign + NeedAlignVal;
569 const unsigned ByteSizeOfLSDAWithAlign =
575 if (ByteSizeOfLSDAWithAlign > ByteSizeOfLSDAWithoutAlign)
576 LSDASizeWithAlign -= 1;
578 Asm->OutStreamer->emitULEB128IntValue(LSDASizeWithAlign,
579 ByteSizeOfLSDAWithAlign);
582 Asm->emitEncodingByte(CallSiteEncoding,
"Call site");
583 Asm->OutStreamer->emitULEB128IntValue(CallSiteTableSize);
587 if (IsSJLJ || IsWasm) {
588 Asm->OutStreamer->emitLabel(
Asm->getMBBExceptionSym(
Asm->MF->front()));
592 EmitTypeTableRefAndCallSiteTableEndRef();
596 I = CallSites.
begin(), E = CallSites.
end();
I != E; ++
I, ++idx) {
601 Asm->OutStreamer->AddComment(
">> Call Site " +
Twine(idx) +
" <<");
602 Asm->OutStreamer->AddComment(
" On exception at call site "+
Twine(idx));
604 Asm->emitULEB128(idx);
611 Asm->OutStreamer->AddComment(
" Action: cleanup");
613 Asm->OutStreamer->AddComment(
" Action: " +
618 Asm->OutStreamer->emitLabel(CstEndLabel);
640 assert(CallSiteRanges.
size() != 0 &&
"No call-site ranges!");
646 if (CSRange.IsLPRange) {
647 assert(LandingPadRange ==
nullptr &&
648 "All landing pads must be in a single callsite range.");
649 LandingPadRange = &CSRange;
668 if (CSRange.CallSiteBeginIdx != 0) {
673 Asm->OutStreamer->emitLabel(CSRange.ExceptionLabel);
679 if (CallSiteRanges.size() == 1 || LandingPadRange ==
nullptr) {
681 }
else if (!
Asm->isPositionIndependent()) {
687 Asm->MAI->getCodePointerSize());
692 MCSymbol *Dot = Context.createTempSymbol();
693 Asm->OutStreamer->emitLabel(Dot);
694 Asm->OutStreamer->emitValue(
699 Asm->MAI->getCodePointerSize());
702 if (HasLEB128Directives)
703 EmitTypeTableRefAndCallSiteTableEndRef();
705 EmitTypeTableOffsetAndCallSiteTableOffset();
707 for (
size_t CallSiteIdx = CSRange.CallSiteBeginIdx;
708 CallSiteIdx != CSRange.CallSiteEndIdx; ++CallSiteIdx) {
711 MCSymbol *EHFuncBeginSym = CSRange.FragmentBeginLabel;
712 MCSymbol *EHFuncEndSym = CSRange.FragmentEndLabel;
716 BeginLabel = EHFuncBeginSym;
719 EndLabel = EHFuncEndSym;
723 Asm->OutStreamer->AddComment(
">> Call Site " +
Twine(++Entry) +
725 Asm->emitCallSiteOffset(BeginLabel, EHFuncBeginSym, CallSiteEncoding);
727 Asm->OutStreamer->AddComment(
Twine(
" Call between ") +
728 BeginLabel->
getName() +
" and " +
730 Asm->emitCallSiteOffset(EndLabel, BeginLabel, CallSiteEncoding);
736 Asm->OutStreamer->AddComment(
" has no landing pad");
737 Asm->emitCallSiteValue(0, CallSiteEncoding);
740 Asm->OutStreamer->AddComment(
Twine(
" jumps to ") +
752 Asm->OutStreamer->AddComment(
" On action: cleanup");
754 Asm->OutStreamer->AddComment(
" On action: " +
760 Asm->OutStreamer->emitLabel(CstEndLabel);
768 Asm->OutStreamer->AddComment(
">> Action Record " +
Twine(++Entry) +
" <<");
776 if (Action.ValueForTypeID > 0)
777 Asm->OutStreamer->AddComment(
" Catch TypeInfo " +
778 Twine(Action.ValueForTypeID));
779 else if (Action.ValueForTypeID < 0)
780 Asm->OutStreamer->AddComment(
" Filter TypeInfo " +
781 Twine(Action.ValueForTypeID));
783 Asm->OutStreamer->AddComment(
" Cleanup");
785 Asm->emitSLEB128(Action.ValueForTypeID);
789 if (Action.Previous ==
unsigned(-1)) {
790 Asm->OutStreamer->AddComment(
" No further actions");
792 Asm->OutStreamer->AddComment(
" Continue to action " +
793 Twine(Action.Previous + 1));
796 Asm->emitSLEB128(Action.NextAction);