MCSymbol *EmitCFICommon();
- std::vector<MCWinFrameInfo *> WinFrameInfos;
- MCWinFrameInfo *CurrentWinFrameInfo;
+ std::vector<WinEH::FrameInfo *> WinFrameInfos;
+ WinEH::FrameInfo *CurrentWinFrameInfo;
void EnsureValidWinFrameInfo();
// SymbolOrdering - Tracks an index to represent the order
virtual void EmitCFIStartProcImpl(MCDwarfFrameInfo &Frame);
virtual void EmitCFIEndProcImpl(MCDwarfFrameInfo &CurFrame);
- MCWinFrameInfo *getCurrentWinFrameInfo() {
+ WinEH::FrameInfo *getCurrentWinFrameInfo() {
return CurrentWinFrameInfo;
}
}
unsigned getNumWinFrameInfos() { return WinFrameInfos.size(); }
- ArrayRef<MCWinFrameInfo *> getWinFrameInfos() const {
+ ArrayRef<WinEH::FrameInfo *> getWinFrameInfos() const {
return WinFrameInfos;
}
};
}
- struct MCWinFrameInfo {
- MCWinFrameInfo()
- : Begin(nullptr), End(nullptr),ExceptionHandler(nullptr),
- Function(nullptr), PrologEnd(nullptr), Symbol(nullptr),
- HandlesUnwind(false), HandlesExceptions(false), LastFrameInst(-1),
- ChainedParent(nullptr), Instructions() {}
- MCSymbol *Begin;
- MCSymbol *End;
- const MCSymbol *ExceptionHandler;
- const MCSymbol *Function;
- MCSymbol *PrologEnd;
- MCSymbol *Symbol;
- bool HandlesUnwind;
- bool HandlesExceptions;
- int LastFrameInst;
- MCWinFrameInfo *ChainedParent;
- std::vector<WinEH::Instruction> Instructions;
- };
-
class MCWin64EHUnwindEmitter {
public:
static StringRef GetSectionSuffix(const MCSymbol *func);
// This emits the unwind info sections (.pdata and .xdata in PE/COFF).
//
static void Emit(MCStreamer &streamer);
- static void EmitUnwindInfo(MCStreamer &streamer, MCWinFrameInfo *info);
+ static void EmitUnwindInfo(MCStreamer &streamer, WinEH::FrameInfo *info);
};
} // end namespace llvm
#ifndef LLVM_MC_MCWINEH_H
#define LLVM_MC_MCWINEH_H
+#include <vector>
+
namespace llvm {
class MCSymbol;
Instruction(unsigned Op, MCSymbol *L, unsigned Reg, unsigned Off)
: Label(L), Offset(Off), Register(Reg), Operation(Op) {}
};
+
+struct FrameInfo {
+ const MCSymbol *Begin;
+ const MCSymbol *End;
+ const MCSymbol *ExceptionHandler;
+ const MCSymbol *Function;
+ const MCSymbol *PrologEnd;
+ const MCSymbol *Symbol;
+
+ bool HandlesUnwind;
+ bool HandlesExceptions;
+
+ int LastFrameInst;
+ const FrameInfo *ChainedParent;
+ std::vector<Instruction> Instructions;
+
+ FrameInfo()
+ : Begin(nullptr), End(nullptr), ExceptionHandler(nullptr),
+ Function(nullptr), PrologEnd(nullptr), Symbol(nullptr),
+ HandlesUnwind(false), HandlesExceptions(false), LastFrameInst(-1),
+ ChainedParent(nullptr), Instructions() {}
+ FrameInfo(const MCSymbol *Function, const MCSymbol *BeginFuncEHLabel)
+ : Begin(BeginFuncEHLabel), End(nullptr), ExceptionHandler(nullptr),
+ Function(Function), PrologEnd(nullptr), Symbol(nullptr),
+ HandlesUnwind(false), HandlesExceptions(false), LastFrameInst(-1),
+ ChainedParent(nullptr), Instructions() {}
+ FrameInfo(const MCSymbol *Function, const MCSymbol *BeginFuncEHLabel,
+ const FrameInfo *ChainedParent)
+ : Begin(BeginFuncEHLabel), End(nullptr), ExceptionHandler(nullptr),
+ Function(Function), PrologEnd(nullptr), Symbol(nullptr),
+ HandlesUnwind(false), HandlesExceptions(false), LastFrameInst(-1),
+ ChainedParent(ChainedParent), Instructions() {}
+};
}
}
// cause the section switch to be visible in the emitted assembly.
// We only do this so the section switch that terminates the handler
// data block is visible.
- MCWinFrameInfo *CurFrame = getCurrentWinFrameInfo();
+ WinEH::FrameInfo *CurFrame = getCurrentWinFrameInfo();
StringRef suffix=MCWin64EHUnwindEmitter::GetSectionSuffix(CurFrame->Function);
const MCSection *xdataSect = getWin64EHTableSection(suffix, getContext());
if (xdataSect)
void MCStreamer::EmitWinCFIStartProc(const MCSymbol *Symbol) {
if (CurrentWinFrameInfo && !CurrentWinFrameInfo->End)
report_fatal_error("Starting a function before ending the previous one!");
- MCWinFrameInfo *Frame = new MCWinFrameInfo;
- Frame->Begin = getContext().CreateTempSymbol();
- Frame->Function = Symbol;
- EmitLabel(Frame->Begin);
- WinFrameInfos.push_back(Frame);
+
+ MCSymbol *StartProc = getContext().CreateTempSymbol();
+ EmitLabel(StartProc);
+
+ WinFrameInfos.push_back(new WinEH::FrameInfo(Symbol, StartProc));
CurrentWinFrameInfo = WinFrameInfos.back();
}
EnsureValidWinFrameInfo();
if (CurrentWinFrameInfo->ChainedParent)
report_fatal_error("Not all chained regions terminated!");
- CurrentWinFrameInfo->End = getContext().CreateTempSymbol();
- EmitLabel(CurrentWinFrameInfo->End);
+
+ MCSymbol *Label = getContext().CreateTempSymbol();
+ EmitLabel(Label);
+ CurrentWinFrameInfo->End = Label;
}
void MCStreamer::EmitWinCFIStartChained() {
EnsureValidWinFrameInfo();
- MCWinFrameInfo *Frame = new MCWinFrameInfo;
- Frame->Begin = getContext().CreateTempSymbol();
- Frame->Function = CurrentWinFrameInfo->Function;
- Frame->ChainedParent = CurrentWinFrameInfo;
- EmitLabel(Frame->Begin);
- WinFrameInfos.push_back(Frame);
+
+ MCSymbol *StartProc = getContext().CreateTempSymbol();
+ EmitLabel(StartProc);
+
+ WinFrameInfos.push_back(new WinEH::FrameInfo(CurrentWinFrameInfo->Function,
+ StartProc, CurrentWinFrameInfo));
CurrentWinFrameInfo = WinFrameInfos.back();
}
EnsureValidWinFrameInfo();
if (!CurrentWinFrameInfo->ChainedParent)
report_fatal_error("End of a chained region outside a chained region!");
- CurrentWinFrameInfo->End = getContext().CreateTempSymbol();
- EmitLabel(CurrentWinFrameInfo->End);
- CurrentWinFrameInfo = CurrentWinFrameInfo->ChainedParent;
+
+ MCSymbol *Label = getContext().CreateTempSymbol();
+ EmitLabel(Label);
+
+ CurrentWinFrameInfo->End = Label;
+ CurrentWinFrameInfo =
+ const_cast<WinEH::FrameInfo *>(CurrentWinFrameInfo->ChainedParent);
}
void MCStreamer::EmitWinEHHandler(const MCSymbol *Sym, bool Unwind,
void MCStreamer::EmitWinCFIEndProlog() {
EnsureValidWinFrameInfo();
- CurrentWinFrameInfo->PrologEnd = getContext().CreateTempSymbol();
- EmitLabel(CurrentWinFrameInfo->PrologEnd);
+
+ MCSymbol *Label = getContext().CreateTempSymbol();
+ EmitLabel(Label);
+
+ CurrentWinFrameInfo->PrologEnd = Label;
}
void MCStreamer::EmitCOFFSectionIndex(MCSymbol const *Symbol) {
Streamer.EmitAbsValue(Diff, 1);
}
-static void EmitUnwindCode(MCStreamer &streamer, MCSymbol *begin,
+static void EmitUnwindCode(MCStreamer &streamer, const MCSymbol *begin,
WinEH::Instruction &inst) {
uint8_t b2;
uint16_t w;
}
static void EmitRuntimeFunction(MCStreamer &streamer,
- const MCWinFrameInfo *info) {
+ const WinEH::FrameInfo *info) {
MCContext &context = streamer.getContext();
streamer.EmitValueToAlignment(4);
context), 4);
}
-static void EmitUnwindInfo(MCStreamer &streamer, MCWinFrameInfo *info) {
+static void EmitUnwindInfo(MCStreamer &streamer, WinEH::FrameInfo *info) {
// If this UNWIND_INFO already has a symbol, it's already been emitted.
- if (info->Symbol) return;
+ if (info->Symbol)
+ return;
MCContext &context = streamer.getContext();
+ MCSymbol *Label = context.CreateTempSymbol();
+
streamer.EmitValueToAlignment(4);
- info->Symbol = context.CreateTempSymbol();
- streamer.EmitLabel(info->Symbol);
+ streamer.EmitLabel(Label);
+ info->Symbol = Label;
// Upper 3 bits are the version number (currently 1).
uint8_t flags = 0x01;
}
void MCWin64EHUnwindEmitter::EmitUnwindInfo(MCStreamer &streamer,
- MCWinFrameInfo *info) {
+ WinEH::FrameInfo *info) {
// Switch sections (the static function above is meant to be called from
// here and from Emit().
MCContext &context = streamer.getContext();