JITDwarfEmitter.cpp revision 091fc4b5560e0c87db74855aebecb3f872740c7d
1afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray//===----- JITDwarfEmitter.cpp - Write dwarf tables into memory -----------===// 2afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray// 3afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray// The LLVM Compiler Infrastructure 4afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray// 5afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray// This file is distributed under the University of Illinois Open Source 6afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray// License. See LICENSE.TXT for details. 7afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray// 8afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray//===----------------------------------------------------------------------===// 9afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray// 10afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray// This file defines a JITDwarfEmitter object that is used by the JIT to 11afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray// write dwarf tables to memory. 12afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray// 13afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray//===----------------------------------------------------------------------===// 14afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 15afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray#include "JIT.h" 16afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray#include "JITDwarfEmitter.h" 17afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray#include "llvm/Function.h" 18afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray#include "llvm/ADT/DenseMap.h" 19a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes#include "llvm/CodeGen/JITCodeEmitter.h" 20afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray#include "llvm/CodeGen/MachineFunction.h" 21afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray#include "llvm/CodeGen/MachineLocation.h" 22afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray#include "llvm/CodeGen/MachineModuleInfo.h" 23afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray#include "llvm/ExecutionEngine/JITMemoryManager.h" 24c25e7581b9b8088910da31702d4ca21c4734c6d7Torok Edwin#include "llvm/Support/ErrorHandling.h" 25af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner#include "llvm/MC/MCAsmInfo.h" 261611273351d75b5cbe2a67485bb9831d5916fe26Chris Lattner#include "llvm/MC/MCSymbol.h" 27afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray#include "llvm/Target/TargetData.h" 28afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray#include "llvm/Target/TargetInstrInfo.h" 29afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray#include "llvm/Target/TargetFrameInfo.h" 30afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray#include "llvm/Target/TargetMachine.h" 31afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray#include "llvm/Target/TargetRegisterInfo.h" 32afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffrayusing namespace llvm; 33afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 34003de66227d235a9ca7373d9cb2c0b1b6ae5b81aDaniel DunbarJITDwarfEmitter::JITDwarfEmitter(JIT& theJit) : MMI(0), Jit(theJit) {} 35afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 36afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 37afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffrayunsigned char* JITDwarfEmitter::EmitDwarfTable(MachineFunction& F, 38a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JITCodeEmitter& jce, 39afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray unsigned char* StartFunction, 402763217fbd2f1c54a7a25fd3ae9e997ea6ece0cbReid Kleckner unsigned char* EndFunction, 412763217fbd2f1c54a7a25fd3ae9e997ea6ece0cbReid Kleckner unsigned char* &EHFramePtr) { 42003de66227d235a9ca7373d9cb2c0b1b6ae5b81aDaniel Dunbar assert(MMI && "MachineModuleInfo not registered!"); 43003de66227d235a9ca7373d9cb2c0b1b6ae5b81aDaniel Dunbar 44afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray const TargetMachine& TM = F.getTarget(); 45afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray TD = TM.getTargetData(); 46afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray stackGrowthDirection = TM.getFrameInfo()->getStackGrowthDirection(); 47afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray RI = TM.getRegisterInfo(); 48a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE = &jce; 49afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 50afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray unsigned char* ExceptionTable = EmitExceptionTable(&F, StartFunction, 51afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray EndFunction); 52afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 53afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray unsigned char* Result = 0; 54afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 5546510a73e977273ec67747eb34cbdb43f815e451Dan Gohman const std::vector<const Function *> Personalities = MMI->getPersonalities(); 56afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray EHFramePtr = EmitCommonEHFrame(Personalities[MMI->getPersonalityIndex()]); 57afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 58afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray Result = EmitEHFrame(Personalities[MMI->getPersonalityIndex()], EHFramePtr, 59afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray StartFunction, EndFunction, ExceptionTable); 609d48b555e24842c9a180e22511a39bfe62dfd5bdBill Wendling 61afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray return Result; 62afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray} 63afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 64afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 655913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffrayvoid 665913e6c5dbaff88ac00d5e679382abc72323831aNicolas GeoffrayJITDwarfEmitter::EmitFrameMoves(intptr_t BaseLabelPtr, 675913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffray const std::vector<MachineMove> &Moves) const { 68afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray unsigned PointerSize = TD->getPointerSize(); 69afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray int stackGrowth = stackGrowthDirection == TargetFrameInfo::StackGrowsUp ? 70afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray PointerSize : -PointerSize; 712e9919a5e5fe76f4b1e3290103c4bfd149ebba9cChris Lattner MCSymbol *BaseLabel = 0; 72afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 73afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray for (unsigned i = 0, N = Moves.size(); i < N; ++i) { 74afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray const MachineMove &Move = Moves[i]; 752e9919a5e5fe76f4b1e3290103c4bfd149ebba9cChris Lattner MCSymbol *Label = Move.getLabel(); 76afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 771611273351d75b5cbe2a67485bb9831d5916fe26Chris Lattner // Throw out move if the label is invalid. 78091fc4b5560e0c87db74855aebecb3f872740c7dBill Wendling if (Label && (*JCE->getLabelLocations())[Label] == 0) 791611273351d75b5cbe2a67485bb9831d5916fe26Chris Lattner continue; 80afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 81afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray intptr_t LabelPtr = 0; 822e9919a5e5fe76f4b1e3290103c4bfd149ebba9cChris Lattner if (Label) LabelPtr = JCE->getLabelAddress(Label); 83afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 84afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray const MachineLocation &Dst = Move.getDestination(); 85afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray const MachineLocation &Src = Move.getSource(); 86afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 87afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Advance row if new location. 882e9919a5e5fe76f4b1e3290103c4bfd149ebba9cChris Lattner if (BaseLabelPtr && Label && BaseLabel != Label) { 89a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitByte(dwarf::DW_CFA_advance_loc4); 90a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitInt32(LabelPtr - BaseLabelPtr); 91afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 922e9919a5e5fe76f4b1e3290103c4bfd149ebba9cChris Lattner BaseLabel = Label; 93afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray BaseLabelPtr = LabelPtr; 94afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 95afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 96afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // If advancing cfa. 97489032a2b75f520cf73a53b79dc61792076eb95eDaniel Dunbar if (Dst.isReg() && Dst.getReg() == MachineLocation::VirtualFP) { 98489032a2b75f520cf73a53b79dc61792076eb95eDaniel Dunbar if (!Src.isReg()) { 99489032a2b75f520cf73a53b79dc61792076eb95eDaniel Dunbar if (Src.getReg() == MachineLocation::VirtualFP) { 100a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitByte(dwarf::DW_CFA_def_cfa_offset); 101afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } else { 102a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitByte(dwarf::DW_CFA_def_cfa); 103a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitULEB128Bytes(RI->getDwarfRegNum(Src.getReg(), true)); 104afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 105afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 1069d48b555e24842c9a180e22511a39bfe62dfd5bdBill Wendling JCE->emitULEB128Bytes(-Src.getOffset()); 107afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } else { 1089d48b555e24842c9a180e22511a39bfe62dfd5bdBill Wendling llvm_unreachable("Machine move not supported yet."); 109afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 110489032a2b75f520cf73a53b79dc61792076eb95eDaniel Dunbar } else if (Src.isReg() && 111489032a2b75f520cf73a53b79dc61792076eb95eDaniel Dunbar Src.getReg() == MachineLocation::VirtualFP) { 112489032a2b75f520cf73a53b79dc61792076eb95eDaniel Dunbar if (Dst.isReg()) { 113a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitByte(dwarf::DW_CFA_def_cfa_register); 114a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitULEB128Bytes(RI->getDwarfRegNum(Dst.getReg(), true)); 115afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } else { 1169d48b555e24842c9a180e22511a39bfe62dfd5bdBill Wendling llvm_unreachable("Machine move not supported yet."); 117afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 118afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } else { 119489032a2b75f520cf73a53b79dc61792076eb95eDaniel Dunbar unsigned Reg = RI->getDwarfRegNum(Src.getReg(), true); 120afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray int Offset = Dst.getOffset() / stackGrowth; 121afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 122afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray if (Offset < 0) { 123a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitByte(dwarf::DW_CFA_offset_extended_sf); 124a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitULEB128Bytes(Reg); 125a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitSLEB128Bytes(Offset); 126afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } else if (Reg < 64) { 127a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitByte(dwarf::DW_CFA_offset + Reg); 128a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitULEB128Bytes(Offset); 129afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } else { 130a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitByte(dwarf::DW_CFA_offset_extended); 131a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitULEB128Bytes(Reg); 132a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitULEB128Bytes(Offset); 133afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 134afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 135afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 136afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray} 137afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 138afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray/// SharedTypeIds - How many leading type ids two landing pads have in common. 139afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffraystatic unsigned SharedTypeIds(const LandingPadInfo *L, 140afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray const LandingPadInfo *R) { 141afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray const std::vector<int> &LIds = L->TypeIds, &RIds = R->TypeIds; 142afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray unsigned LSize = LIds.size(), RSize = RIds.size(); 143afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray unsigned MinSize = LSize < RSize ? LSize : RSize; 144afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray unsigned Count = 0; 145afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 146afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray for (; Count != MinSize; ++Count) 147afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray if (LIds[Count] != RIds[Count]) 148afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray return Count; 149afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 150afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray return Count; 151afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray} 152afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 153afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 154afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray/// PadLT - Order landing pads lexicographically by type id. 155afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffraystatic bool PadLT(const LandingPadInfo *L, const LandingPadInfo *R) { 156afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray const std::vector<int> &LIds = L->TypeIds, &RIds = R->TypeIds; 157afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray unsigned LSize = LIds.size(), RSize = RIds.size(); 158afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray unsigned MinSize = LSize < RSize ? LSize : RSize; 159afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 160afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray for (unsigned i = 0; i != MinSize; ++i) 161afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray if (LIds[i] != RIds[i]) 162afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray return LIds[i] < RIds[i]; 163afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 164afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray return LSize < RSize; 165afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray} 166afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 167844731a7f1909f55935e3514c9e713a62d67662eDan Gohmannamespace { 168844731a7f1909f55935e3514c9e713a62d67662eDan Gohman 169afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray/// ActionEntry - Structure describing an entry in the actions table. 170afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffraystruct ActionEntry { 171afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray int ValueForTypeID; // The value to write - may not be equal to the type id. 172afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray int NextAction; 173afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray struct ActionEntry *Previous; 174afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray}; 175afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 176afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray/// PadRange - Structure holding a try-range and the associated landing pad. 177afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffraystruct PadRange { 178afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // The index of the landing pad. 179afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray unsigned PadIndex; 180afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // The index of the begin and end labels in the landing pad's label lists. 181afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray unsigned RangeIndex; 182afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray}; 183afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 1841611273351d75b5cbe2a67485bb9831d5916fe26Chris Lattnertypedef DenseMap<MCSymbol*, PadRange> RangeMapType; 185afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 186afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray/// CallSiteEntry - Structure describing an entry in the call-site table. 187afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffraystruct CallSiteEntry { 1881611273351d75b5cbe2a67485bb9831d5916fe26Chris Lattner MCSymbol *BeginLabel; // zero indicates the start of the function. 1891611273351d75b5cbe2a67485bb9831d5916fe26Chris Lattner MCSymbol *EndLabel; // zero indicates the end of the function. 1901611273351d75b5cbe2a67485bb9831d5916fe26Chris Lattner MCSymbol *PadLabel; // zero indicates that there is no landing pad. 191afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray unsigned Action; 192afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray}; 193afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 194844731a7f1909f55935e3514c9e713a62d67662eDan Gohman} 195844731a7f1909f55935e3514c9e713a62d67662eDan Gohman 196afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffrayunsigned char* JITDwarfEmitter::EmitExceptionTable(MachineFunction* MF, 197afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray unsigned char* StartFunction, 1985913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffray unsigned char* EndFunction) const { 199003de66227d235a9ca7373d9cb2c0b1b6ae5b81aDaniel Dunbar assert(MMI && "MachineModuleInfo not registered!"); 200003de66227d235a9ca7373d9cb2c0b1b6ae5b81aDaniel Dunbar 201afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Map all labels and get rid of any dead landing pads. 20247639fc5be0b8f4873d076a9ed24b9a3c0682b15Bill Wendling MMI->TidyLandingPads(JCE->getLabelLocations()); 203afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 20446510a73e977273ec67747eb34cbdb43f815e451Dan Gohman const std::vector<const GlobalVariable *> &TypeInfos = MMI->getTypeInfos(); 205afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray const std::vector<unsigned> &FilterIds = MMI->getFilterIds(); 206afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray const std::vector<LandingPadInfo> &PadInfos = MMI->getLandingPads(); 207afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray if (PadInfos.empty()) return 0; 208afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 209afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Sort the landing pads in order of their type ids. This is used to fold 210afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // duplicate actions. 211afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray SmallVector<const LandingPadInfo *, 64> LandingPads; 212afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray LandingPads.reserve(PadInfos.size()); 213afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray for (unsigned i = 0, N = PadInfos.size(); i != N; ++i) 214afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray LandingPads.push_back(&PadInfos[i]); 215afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray std::sort(LandingPads.begin(), LandingPads.end(), PadLT); 216afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 217afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Negative type ids index into FilterIds, positive type ids index into 218afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // TypeInfos. The value written for a positive type id is just the type 219afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // id itself. For a negative type id, however, the value written is the 220afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // (negative) byte offset of the corresponding FilterIds entry. The byte 221afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // offset is usually equal to the type id, because the FilterIds entries 222afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // are written using a variable width encoding which outputs one byte per 223afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // entry as long as the value written is not too large, but can differ. 224afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // This kind of complication does not occur for positive type ids because 225afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // type infos are output using a fixed width encoding. 226afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // FilterOffsets[i] holds the byte offset corresponding to FilterIds[i]. 227afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray SmallVector<int, 16> FilterOffsets; 228afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray FilterOffsets.reserve(FilterIds.size()); 229afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray int Offset = -1; 230afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray for(std::vector<unsigned>::const_iterator I = FilterIds.begin(), 231afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray E = FilterIds.end(); I != E; ++I) { 232afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray FilterOffsets.push_back(Offset); 233af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner Offset -= MCAsmInfo::getULEB128Size(*I); 234afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 235afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 236afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Compute the actions table and gather the first action index for each 237afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // landing pad site. 238afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray SmallVector<ActionEntry, 32> Actions; 239afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray SmallVector<unsigned, 64> FirstActions; 240afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray FirstActions.reserve(LandingPads.size()); 241afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 242afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray int FirstAction = 0; 243afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray unsigned SizeActions = 0; 244afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray for (unsigned i = 0, N = LandingPads.size(); i != N; ++i) { 245afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray const LandingPadInfo *LP = LandingPads[i]; 246afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray const std::vector<int> &TypeIds = LP->TypeIds; 247afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray const unsigned NumShared = i ? SharedTypeIds(LP, LandingPads[i-1]) : 0; 248afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray unsigned SizeSiteActions = 0; 249afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 250afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray if (NumShared < TypeIds.size()) { 251afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray unsigned SizeAction = 0; 252afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray ActionEntry *PrevAction = 0; 253afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 254afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray if (NumShared) { 255afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray const unsigned SizePrevIds = LandingPads[i-1]->TypeIds.size(); 256afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray assert(Actions.size()); 257afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray PrevAction = &Actions.back(); 258af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner SizeAction = MCAsmInfo::getSLEB128Size(PrevAction->NextAction) + 259af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner MCAsmInfo::getSLEB128Size(PrevAction->ValueForTypeID); 260afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray for (unsigned j = NumShared; j != SizePrevIds; ++j) { 261af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner SizeAction -= MCAsmInfo::getSLEB128Size(PrevAction->ValueForTypeID); 262afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray SizeAction += -PrevAction->NextAction; 263afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray PrevAction = PrevAction->Previous; 264afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 265afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 266afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 267afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Compute the actions. 268afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray for (unsigned I = NumShared, M = TypeIds.size(); I != M; ++I) { 269afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray int TypeID = TypeIds[I]; 270afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray assert(-1-TypeID < (int)FilterOffsets.size() && "Unknown filter id!"); 271afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray int ValueForTypeID = TypeID < 0 ? FilterOffsets[-1 - TypeID] : TypeID; 272af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner unsigned SizeTypeID = MCAsmInfo::getSLEB128Size(ValueForTypeID); 273afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 274afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray int NextAction = SizeAction ? -(SizeAction + SizeTypeID) : 0; 275af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner SizeAction = SizeTypeID + MCAsmInfo::getSLEB128Size(NextAction); 276afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray SizeSiteActions += SizeAction; 277afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 278afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray ActionEntry Action = {ValueForTypeID, NextAction, PrevAction}; 279afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray Actions.push_back(Action); 280afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 281afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray PrevAction = &Actions.back(); 282afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 283afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 284afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Record the first action of the landing pad site. 285afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray FirstAction = SizeActions + SizeSiteActions - SizeAction + 1; 286afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } // else identical - re-use previous FirstAction 287afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 288afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray FirstActions.push_back(FirstAction); 289afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 290afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Compute this sites contribution to size. 291afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray SizeActions += SizeSiteActions; 292afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 293afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 294afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Compute the call-site table. Entries must be ordered by address. 295afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray SmallVector<CallSiteEntry, 64> CallSites; 296afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 297afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray RangeMapType PadMap; 298afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray for (unsigned i = 0, N = LandingPads.size(); i != N; ++i) { 299afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray const LandingPadInfo *LandingPad = LandingPads[i]; 300afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray for (unsigned j=0, E = LandingPad->BeginLabels.size(); j != E; ++j) { 3011611273351d75b5cbe2a67485bb9831d5916fe26Chris Lattner MCSymbol *BeginLabel = LandingPad->BeginLabels[j]; 302afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray assert(!PadMap.count(BeginLabel) && "Duplicate landing pad labels!"); 303afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray PadRange P = { i, j }; 304afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray PadMap[BeginLabel] = P; 305afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 306afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 307afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 308afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray bool MayThrow = false; 3091611273351d75b5cbe2a67485bb9831d5916fe26Chris Lattner MCSymbol *LastLabel = 0; 310afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray for (MachineFunction::const_iterator I = MF->begin(), E = MF->end(); 311afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray I != E; ++I) { 312afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray for (MachineBasicBlock::const_iterator MI = I->begin(), E = I->end(); 313afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray MI != E; ++MI) { 3144406604047423576e36657c7ede266ca42e79642Dan Gohman if (!MI->isLabel()) { 315afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray MayThrow |= MI->getDesc().isCall(); 316afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray continue; 317afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 318afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 3196b4205aa44094f96115be72dd23aaf47a0257d2fChris Lattner MCSymbol *BeginLabel = MI->getOperand(0).getMCSymbol(); 320afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray assert(BeginLabel && "Invalid label!"); 321afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 322afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray if (BeginLabel == LastLabel) 323afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray MayThrow = false; 324afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 325afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray RangeMapType::iterator L = PadMap.find(BeginLabel); 326afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 327afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray if (L == PadMap.end()) 328afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray continue; 329afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 330afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray PadRange P = L->second; 331afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray const LandingPadInfo *LandingPad = LandingPads[P.PadIndex]; 332afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 333afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray assert(BeginLabel == LandingPad->BeginLabels[P.RangeIndex] && 334afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray "Inconsistent landing pad map!"); 335afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 336afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // If some instruction between the previous try-range and this one may 337afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // throw, create a call-site entry with no landing pad for the region 338afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // between the try-ranges. 339afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray if (MayThrow) { 340afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray CallSiteEntry Site = {LastLabel, BeginLabel, 0, 0}; 341afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray CallSites.push_back(Site); 342afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 343afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 344afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray LastLabel = LandingPad->EndLabels[P.RangeIndex]; 345afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray CallSiteEntry Site = {BeginLabel, LastLabel, 346afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray LandingPad->LandingPadLabel, FirstActions[P.PadIndex]}; 347afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 348afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray assert(Site.BeginLabel && Site.EndLabel && Site.PadLabel && 349afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray "Invalid landing pad!"); 350afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 351afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Try to merge with the previous call-site. 352afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray if (CallSites.size()) { 353719de53742167ca3f0e6b2efafb6eac18bd90452Dan Gohman CallSiteEntry &Prev = CallSites.back(); 354afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray if (Site.PadLabel == Prev.PadLabel && Site.Action == Prev.Action) { 355afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Extend the range of the previous entry. 356afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray Prev.EndLabel = Site.EndLabel; 357afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray continue; 358afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 359afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 360afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 361afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Otherwise, create a new call-site. 362afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray CallSites.push_back(Site); 363afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 364afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 365afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // If some instruction between the previous try-range and the end of the 366afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // function may throw, create a call-site entry with no landing pad for the 367afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // region following the try-range. 368afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray if (MayThrow) { 369afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray CallSiteEntry Site = {LastLabel, 0, 0, 0}; 370afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray CallSites.push_back(Site); 371afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 372afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 373afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Final tallies. 374afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray unsigned SizeSites = CallSites.size() * (sizeof(int32_t) + // Site start. 375afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray sizeof(int32_t) + // Site length. 376afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray sizeof(int32_t)); // Landing pad. 377afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray for (unsigned i = 0, e = CallSites.size(); i < e; ++i) 378af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner SizeSites += MCAsmInfo::getULEB128Size(CallSites[i].Action); 379afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 380afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray unsigned SizeTypes = TypeInfos.size() * TD->getPointerSize(); 381afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 382afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray unsigned TypeOffset = sizeof(int8_t) + // Call site format 383afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Call-site table length 384af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner MCAsmInfo::getULEB128Size(SizeSites) + 385afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray SizeSites + SizeActions + SizeTypes; 386afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 387afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Begin the exception table. 38801248e671100fbd6eac6bc3646096dc75ec885d1Reid Kleckner JCE->emitAlignmentWithFill(4, 0); 38901248e671100fbd6eac6bc3646096dc75ec885d1Reid Kleckner // Asm->EOL("Padding"); 39001248e671100fbd6eac6bc3646096dc75ec885d1Reid Kleckner 391a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes unsigned char* DwarfExceptionTable = (unsigned char*)JCE->getCurrentPCValue(); 392afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 393afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Emit the header. 394a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitByte(dwarf::DW_EH_PE_omit); 395afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Asm->EOL("LPStart format (DW_EH_PE_omit)"); 396a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitByte(dwarf::DW_EH_PE_absptr); 397afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Asm->EOL("TType format (DW_EH_PE_absptr)"); 398a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitULEB128Bytes(TypeOffset); 399afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Asm->EOL("TType base offset"); 400a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitByte(dwarf::DW_EH_PE_udata4); 401afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Asm->EOL("Call site format (DW_EH_PE_udata4)"); 402a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitULEB128Bytes(SizeSites); 403afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Asm->EOL("Call-site table length"); 404afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 405afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Emit the landing pad site information. 406afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray for (unsigned i = 0; i < CallSites.size(); ++i) { 407afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray CallSiteEntry &S = CallSites[i]; 408afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray intptr_t BeginLabelPtr = 0; 409afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray intptr_t EndLabelPtr = 0; 410afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 411afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray if (!S.BeginLabel) { 412afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray BeginLabelPtr = (intptr_t)StartFunction; 413a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitInt32(0); 414afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } else { 415a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes BeginLabelPtr = JCE->getLabelAddress(S.BeginLabel); 416a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitInt32(BeginLabelPtr - (intptr_t)StartFunction); 417afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 418afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 419afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Asm->EOL("Region start"); 420afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 421abeca44d6387930b9ceadc51260f3d58bdc402eaBill Wendling if (!S.EndLabel) 422afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray EndLabelPtr = (intptr_t)EndFunction; 423abeca44d6387930b9ceadc51260f3d58bdc402eaBill Wendling else 424a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes EndLabelPtr = JCE->getLabelAddress(S.EndLabel); 425abeca44d6387930b9ceadc51260f3d58bdc402eaBill Wendling 426abeca44d6387930b9ceadc51260f3d58bdc402eaBill Wendling JCE->emitInt32(EndLabelPtr - BeginLabelPtr); 427afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray //Asm->EOL("Region length"); 428afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 429afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray if (!S.PadLabel) { 430a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitInt32(0); 431afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } else { 432a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes unsigned PadLabelPtr = JCE->getLabelAddress(S.PadLabel); 433a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitInt32(PadLabelPtr - (intptr_t)StartFunction); 434afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 435afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Asm->EOL("Landing pad"); 436afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 437a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitULEB128Bytes(S.Action); 438afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Asm->EOL("Action"); 439afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 440afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 441afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Emit the actions. 442afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray for (unsigned I = 0, N = Actions.size(); I != N; ++I) { 443afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray ActionEntry &Action = Actions[I]; 444afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 445a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitSLEB128Bytes(Action.ValueForTypeID); 446afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray //Asm->EOL("TypeInfo index"); 447a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitSLEB128Bytes(Action.NextAction); 448afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray //Asm->EOL("Next action"); 449afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 450afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 451afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Emit the type ids. 452afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray for (unsigned M = TypeInfos.size(); M; --M) { 45346510a73e977273ec67747eb34cbdb43f815e451Dan Gohman const GlobalVariable *GV = TypeInfos[M - 1]; 454afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 455afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray if (GV) { 4569d48b555e24842c9a180e22511a39bfe62dfd5bdBill Wendling if (TD->getPointerSize() == sizeof(int32_t)) 457a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitInt32((intptr_t)Jit.getOrEmitGlobalVariable(GV)); 4589d48b555e24842c9a180e22511a39bfe62dfd5bdBill Wendling else 459a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitInt64((intptr_t)Jit.getOrEmitGlobalVariable(GV)); 460afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } else { 461afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray if (TD->getPointerSize() == sizeof(int32_t)) 462a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitInt32(0); 463afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray else 464a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitInt64(0); 465afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 466afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Asm->EOL("TypeInfo"); 467afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 468afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 469afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Emit the filter typeids. 470afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray for (unsigned j = 0, M = FilterIds.size(); j < M; ++j) { 471afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray unsigned TypeID = FilterIds[j]; 472a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitULEB128Bytes(TypeID); 473afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray //Asm->EOL("Filter TypeInfo index"); 474afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 47501248e671100fbd6eac6bc3646096dc75ec885d1Reid Kleckner 47601248e671100fbd6eac6bc3646096dc75ec885d1Reid Kleckner JCE->emitAlignmentWithFill(4, 0); 477afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 478afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray return DwarfExceptionTable; 479afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray} 480afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 4815913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffrayunsigned char* 4825913e6c5dbaff88ac00d5e679382abc72323831aNicolas GeoffrayJITDwarfEmitter::EmitCommonEHFrame(const Function* Personality) const { 483afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray unsigned PointerSize = TD->getPointerSize(); 484afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray int stackGrowth = stackGrowthDirection == TargetFrameInfo::StackGrowsUp ? 485afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray PointerSize : -PointerSize; 486afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 487a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes unsigned char* StartCommonPtr = (unsigned char*)JCE->getCurrentPCValue(); 488afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // EH Common Frame header 489a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->allocateSpace(4, 0); 490a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes unsigned char* FrameCommonBeginPtr = (unsigned char*)JCE->getCurrentPCValue(); 491a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitInt32((int)0); 492a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitByte(dwarf::DW_CIE_VERSION); 493a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitString(Personality ? "zPLR" : "zR"); 494a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitULEB128Bytes(1); 495a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitSLEB128Bytes(stackGrowth); 496a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitByte(RI->getDwarfRegNum(RI->getRARegister(), true)); 4979d48b555e24842c9a180e22511a39bfe62dfd5bdBill Wendling 498afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray if (Personality) { 49942cc8f140a4332d949ec40726d6a011cf1e9f0d5Nicolas Geoffray // Augmentation Size: 3 small ULEBs of one byte each, and the personality 50042cc8f140a4332d949ec40726d6a011cf1e9f0d5Nicolas Geoffray // function which size is PointerSize. 501a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitULEB128Bytes(3 + PointerSize); 502afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 50342cc8f140a4332d949ec40726d6a011cf1e9f0d5Nicolas Geoffray // We set the encoding of the personality as direct encoding because we use 50442cc8f140a4332d949ec40726d6a011cf1e9f0d5Nicolas Geoffray // the function pointer. The encoding is not relative because the current 50542cc8f140a4332d949ec40726d6a011cf1e9f0d5Nicolas Geoffray // PC value may be bigger than the personality function pointer. 50642cc8f140a4332d949ec40726d6a011cf1e9f0d5Nicolas Geoffray if (PointerSize == 4) { 507a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitByte(dwarf::DW_EH_PE_sdata4); 508a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitInt32(((intptr_t)Jit.getPointerToGlobal(Personality))); 50942cc8f140a4332d949ec40726d6a011cf1e9f0d5Nicolas Geoffray } else { 510a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitByte(dwarf::DW_EH_PE_sdata8); 511a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitInt64(((intptr_t)Jit.getPointerToGlobal(Personality))); 51242cc8f140a4332d949ec40726d6a011cf1e9f0d5Nicolas Geoffray } 5139d48b555e24842c9a180e22511a39bfe62dfd5bdBill Wendling 51489ee706b6b64aaef7227e2e232b4de9c473632a2Bill Wendling // LSDA encoding: This must match the encoding used in EmitEHFrame () 51589ee706b6b64aaef7227e2e232b4de9c473632a2Bill Wendling if (PointerSize == 4) 51689ee706b6b64aaef7227e2e232b4de9c473632a2Bill Wendling JCE->emitULEB128Bytes(dwarf::DW_EH_PE_pcrel | dwarf::DW_EH_PE_sdata4); 51789ee706b6b64aaef7227e2e232b4de9c473632a2Bill Wendling else 51889ee706b6b64aaef7227e2e232b4de9c473632a2Bill Wendling JCE->emitULEB128Bytes(dwarf::DW_EH_PE_pcrel | dwarf::DW_EH_PE_sdata8); 519a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitULEB128Bytes(dwarf::DW_EH_PE_pcrel | dwarf::DW_EH_PE_sdata4); 520afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } else { 521a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitULEB128Bytes(1); 522a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitULEB128Bytes(dwarf::DW_EH_PE_pcrel | dwarf::DW_EH_PE_sdata4); 523afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 524afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 525afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray std::vector<MachineMove> Moves; 526afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray RI->getInitialFrameState(Moves); 527afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray EmitFrameMoves(0, Moves); 52801248e671100fbd6eac6bc3646096dc75ec885d1Reid Kleckner 52901248e671100fbd6eac6bc3646096dc75ec885d1Reid Kleckner JCE->emitAlignmentWithFill(PointerSize, dwarf::DW_CFA_nop); 53001248e671100fbd6eac6bc3646096dc75ec885d1Reid Kleckner 53101248e671100fbd6eac6bc3646096dc75ec885d1Reid Kleckner JCE->emitInt32At((uintptr_t*)StartCommonPtr, 53201248e671100fbd6eac6bc3646096dc75ec885d1Reid Kleckner (uintptr_t)((unsigned char*)JCE->getCurrentPCValue() - 53301248e671100fbd6eac6bc3646096dc75ec885d1Reid Kleckner FrameCommonBeginPtr)); 534afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 535afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray return StartCommonPtr; 536afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray} 537afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 538afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 5395913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffrayunsigned char* 5405913e6c5dbaff88ac00d5e679382abc72323831aNicolas GeoffrayJITDwarfEmitter::EmitEHFrame(const Function* Personality, 5415913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffray unsigned char* StartCommonPtr, 5425913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffray unsigned char* StartFunction, 5435913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffray unsigned char* EndFunction, 5445913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffray unsigned char* ExceptionTable) const { 545afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray unsigned PointerSize = TD->getPointerSize(); 546afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 547afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // EH frame header. 548a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes unsigned char* StartEHPtr = (unsigned char*)JCE->getCurrentPCValue(); 549a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->allocateSpace(4, 0); 550a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes unsigned char* FrameBeginPtr = (unsigned char*)JCE->getCurrentPCValue(); 551afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // FDE CIE Offset 552a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitInt32(FrameBeginPtr - StartCommonPtr); 553a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitInt32(StartFunction - (unsigned char*)JCE->getCurrentPCValue()); 554a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitInt32(EndFunction - StartFunction); 555afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 556afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // If there is a personality and landing pads then point to the language 557afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // specific data area in the exception table. 5589d48b555e24842c9a180e22511a39bfe62dfd5bdBill Wendling if (Personality) { 5599d48b555e24842c9a180e22511a39bfe62dfd5bdBill Wendling JCE->emitULEB128Bytes(PointerSize == 4 ? 4 : 8); 560afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 5619d48b555e24842c9a180e22511a39bfe62dfd5bdBill Wendling if (PointerSize == 4) { 5629d48b555e24842c9a180e22511a39bfe62dfd5bdBill Wendling if (!MMI->getLandingPads().empty()) 5639d48b555e24842c9a180e22511a39bfe62dfd5bdBill Wendling JCE->emitInt32(ExceptionTable-(unsigned char*)JCE->getCurrentPCValue()); 5649d48b555e24842c9a180e22511a39bfe62dfd5bdBill Wendling else 5659d48b555e24842c9a180e22511a39bfe62dfd5bdBill Wendling JCE->emitInt32((int)0); 566afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } else { 5679d48b555e24842c9a180e22511a39bfe62dfd5bdBill Wendling if (!MMI->getLandingPads().empty()) 5689d48b555e24842c9a180e22511a39bfe62dfd5bdBill Wendling JCE->emitInt64(ExceptionTable-(unsigned char*)JCE->getCurrentPCValue()); 5699d48b555e24842c9a180e22511a39bfe62dfd5bdBill Wendling else 5709d48b555e24842c9a180e22511a39bfe62dfd5bdBill Wendling JCE->emitInt64((int)0); 571afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 572afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } else { 573a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitULEB128Bytes(0); 574afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 575afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 576afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Indicate locations of function specific callee saved registers in 577afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // frame. 578afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray EmitFrameMoves((intptr_t)StartFunction, MMI->getFrameMoves()); 57901248e671100fbd6eac6bc3646096dc75ec885d1Reid Kleckner 58001248e671100fbd6eac6bc3646096dc75ec885d1Reid Kleckner JCE->emitAlignmentWithFill(PointerSize, dwarf::DW_CFA_nop); 58101248e671100fbd6eac6bc3646096dc75ec885d1Reid Kleckner 582afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Indicate the size of the table 58301248e671100fbd6eac6bc3646096dc75ec885d1Reid Kleckner JCE->emitInt32At((uintptr_t*)StartEHPtr, 58401248e671100fbd6eac6bc3646096dc75ec885d1Reid Kleckner (uintptr_t)((unsigned char*)JCE->getCurrentPCValue() - 58501248e671100fbd6eac6bc3646096dc75ec885d1Reid Kleckner StartEHPtr)); 58601248e671100fbd6eac6bc3646096dc75ec885d1Reid Kleckner 587afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray // Double zeroes for the unwind runtime 588afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray if (PointerSize == 8) { 589a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitInt64(0); 590a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitInt64(0); 591afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } else { 592a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitInt32(0); 593a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE->emitInt32(0); 594afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray } 595afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray 596afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray return StartEHPtr; 597afe6c2b001a924cd74bd0aacfed5984d9af004b0Nicolas Geoffray} 598dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 5995913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffrayunsigned JITDwarfEmitter::GetDwarfTableSizeInBytes(MachineFunction& F, 600a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JITCodeEmitter& jce, 601dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray unsigned char* StartFunction, 602dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray unsigned char* EndFunction) { 603dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray const TargetMachine& TM = F.getTarget(); 604dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray TD = TM.getTargetData(); 605dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray stackGrowthDirection = TM.getFrameInfo()->getStackGrowthDirection(); 606dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray RI = TM.getRegisterInfo(); 607a3f99f90338d89354384ca25f53ca4450a1a9d18Bruno Cardoso Lopes JCE = &jce; 608dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray unsigned FinalSize = 0; 609dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 6105913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffray FinalSize += GetExceptionTableSizeInBytes(&F); 611dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 61246510a73e977273ec67747eb34cbdb43f815e451Dan Gohman const std::vector<const Function *> Personalities = MMI->getPersonalities(); 61367c8c4cababc846aab461910a50fd373b35b11aaNicolas Geoffray FinalSize += 61467c8c4cababc846aab461910a50fd373b35b11aaNicolas Geoffray GetCommonEHFrameSizeInBytes(Personalities[MMI->getPersonalityIndex()]); 615dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 61667c8c4cababc846aab461910a50fd373b35b11aaNicolas Geoffray FinalSize += GetEHFrameSizeInBytes(Personalities[MMI->getPersonalityIndex()], 61767c8c4cababc846aab461910a50fd373b35b11aaNicolas Geoffray StartFunction); 6189d48b555e24842c9a180e22511a39bfe62dfd5bdBill Wendling 619dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray return FinalSize; 620dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray} 621dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 6225913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffray/// RoundUpToAlign - Add the specified alignment to FinalSize and returns 6235913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffray/// the new value. 6245913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffraystatic unsigned RoundUpToAlign(unsigned FinalSize, unsigned Alignment) { 625dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray if (Alignment == 0) Alignment = 1; 626580631a73a71ff621c71618b16e9644b30a9d3c9Nicolas Geoffray // Since we do not know where the buffer will be allocated, be pessimistic. 627580631a73a71ff621c71618b16e9644b30a9d3c9Nicolas Geoffray return FinalSize + Alignment; 628dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray} 629dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 6305913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffrayunsigned 6315913e6c5dbaff88ac00d5e679382abc72323831aNicolas GeoffrayJITDwarfEmitter::GetEHFrameSizeInBytes(const Function* Personality, 6325913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffray unsigned char* StartFunction) const { 633dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray unsigned PointerSize = TD->getPointerSize(); 634dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray unsigned FinalSize = 0; 635dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // EH frame header. 636dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray FinalSize += PointerSize; 637dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // FDE CIE Offset 638dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray FinalSize += 3 * PointerSize; 639dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // If there is a personality and landing pads then point to the language 640dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // specific data area in the exception table. 6419d48b555e24842c9a180e22511a39bfe62dfd5bdBill Wendling if (Personality) { 642af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner FinalSize += MCAsmInfo::getULEB128Size(4); 643dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray FinalSize += PointerSize; 644dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } else { 645af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner FinalSize += MCAsmInfo::getULEB128Size(0); 646dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 647dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 648dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Indicate locations of function specific callee saved registers in 649dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // frame. 6505913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffray FinalSize += GetFrameMovesSizeInBytes((intptr_t)StartFunction, 6515913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffray MMI->getFrameMoves()); 652dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 6535913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffray FinalSize = RoundUpToAlign(FinalSize, 4); 654dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 655dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Double zeroes for the unwind runtime 656dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray FinalSize += 2 * PointerSize; 657dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 658dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray return FinalSize; 659dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray} 660dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 6615913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffrayunsigned JITDwarfEmitter::GetCommonEHFrameSizeInBytes(const Function* Personality) 6625913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffray const { 663dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 664dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray unsigned PointerSize = TD->getPointerSize(); 665dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray int stackGrowth = stackGrowthDirection == TargetFrameInfo::StackGrowsUp ? 666dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray PointerSize : -PointerSize; 667dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray unsigned FinalSize = 0; 668dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // EH Common Frame header 669dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray FinalSize += PointerSize; 670dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray FinalSize += 4; 671dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray FinalSize += 1; 6725913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffray FinalSize += Personality ? 5 : 3; // "zPLR" or "zR" 673af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner FinalSize += MCAsmInfo::getULEB128Size(1); 674af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner FinalSize += MCAsmInfo::getSLEB128Size(stackGrowth); 675dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray FinalSize += 1; 676dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 677dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray if (Personality) { 678af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner FinalSize += MCAsmInfo::getULEB128Size(7); 679dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 680dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Encoding 681dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray FinalSize+= 1; 682dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray //Personality 683dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray FinalSize += PointerSize; 684dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 685af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner FinalSize += MCAsmInfo::getULEB128Size(dwarf::DW_EH_PE_pcrel); 686af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner FinalSize += MCAsmInfo::getULEB128Size(dwarf::DW_EH_PE_pcrel); 687dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 688dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } else { 689af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner FinalSize += MCAsmInfo::getULEB128Size(1); 690af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner FinalSize += MCAsmInfo::getULEB128Size(dwarf::DW_EH_PE_pcrel); 691dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 692dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 693dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray std::vector<MachineMove> Moves; 694dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray RI->getInitialFrameState(Moves); 6955913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffray FinalSize += GetFrameMovesSizeInBytes(0, Moves); 6965913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffray FinalSize = RoundUpToAlign(FinalSize, 4); 697dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray return FinalSize; 698dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray} 699dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 700dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffrayunsigned 7015913e6c5dbaff88ac00d5e679382abc72323831aNicolas GeoffrayJITDwarfEmitter::GetFrameMovesSizeInBytes(intptr_t BaseLabelPtr, 7025913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffray const std::vector<MachineMove> &Moves) const { 703dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray unsigned PointerSize = TD->getPointerSize(); 704dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray int stackGrowth = stackGrowthDirection == TargetFrameInfo::StackGrowsUp ? 705dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray PointerSize : -PointerSize; 706dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray bool IsLocal = BaseLabelPtr; 707dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray unsigned FinalSize = 0; 708dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 709dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray for (unsigned i = 0, N = Moves.size(); i < N; ++i) { 710dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray const MachineMove &Move = Moves[i]; 7112e9919a5e5fe76f4b1e3290103c4bfd149ebba9cChris Lattner MCSymbol *Label = Move.getLabel(); 712dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 7131611273351d75b5cbe2a67485bb9831d5916fe26Chris Lattner // Throw out move if the label is invalid. 714091fc4b5560e0c87db74855aebecb3f872740c7dBill Wendling if (Label && (*JCE->getLabelLocations())[Label] == 0) 7151611273351d75b5cbe2a67485bb9831d5916fe26Chris Lattner continue; 716dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 717dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray intptr_t LabelPtr = 0; 7182e9919a5e5fe76f4b1e3290103c4bfd149ebba9cChris Lattner if (Label) LabelPtr = JCE->getLabelAddress(Label); 719dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 720dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray const MachineLocation &Dst = Move.getDestination(); 721dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray const MachineLocation &Src = Move.getSource(); 722dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 723dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Advance row if new location. 7242e9919a5e5fe76f4b1e3290103c4bfd149ebba9cChris Lattner if (BaseLabelPtr && Label && (BaseLabelPtr != LabelPtr || !IsLocal)) { 725dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray FinalSize++; 726dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray FinalSize += PointerSize; 727dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray BaseLabelPtr = LabelPtr; 728dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray IsLocal = true; 729dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 730dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 731dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // If advancing cfa. 732489032a2b75f520cf73a53b79dc61792076eb95eDaniel Dunbar if (Dst.isReg() && Dst.getReg() == MachineLocation::VirtualFP) { 733489032a2b75f520cf73a53b79dc61792076eb95eDaniel Dunbar if (!Src.isReg()) { 734489032a2b75f520cf73a53b79dc61792076eb95eDaniel Dunbar if (Src.getReg() == MachineLocation::VirtualFP) { 735dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray ++FinalSize; 736dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } else { 737dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray ++FinalSize; 738489032a2b75f520cf73a53b79dc61792076eb95eDaniel Dunbar unsigned RegNum = RI->getDwarfRegNum(Src.getReg(), true); 739af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner FinalSize += MCAsmInfo::getULEB128Size(RegNum); 740dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 741dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 742dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray int Offset = -Src.getOffset(); 743dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 744af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner FinalSize += MCAsmInfo::getULEB128Size(Offset); 745dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } else { 746c23197a26f34f559ea9797de51e187087c039c42Torok Edwin llvm_unreachable("Machine move no supported yet."); 747dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 748489032a2b75f520cf73a53b79dc61792076eb95eDaniel Dunbar } else if (Src.isReg() && 749489032a2b75f520cf73a53b79dc61792076eb95eDaniel Dunbar Src.getReg() == MachineLocation::VirtualFP) { 750489032a2b75f520cf73a53b79dc61792076eb95eDaniel Dunbar if (Dst.isReg()) { 7515913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffray ++FinalSize; 752489032a2b75f520cf73a53b79dc61792076eb95eDaniel Dunbar unsigned RegNum = RI->getDwarfRegNum(Dst.getReg(), true); 753af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner FinalSize += MCAsmInfo::getULEB128Size(RegNum); 754dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } else { 755c23197a26f34f559ea9797de51e187087c039c42Torok Edwin llvm_unreachable("Machine move no supported yet."); 756dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 757dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } else { 758489032a2b75f520cf73a53b79dc61792076eb95eDaniel Dunbar unsigned Reg = RI->getDwarfRegNum(Src.getReg(), true); 759dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray int Offset = Dst.getOffset() / stackGrowth; 760dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 761dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray if (Offset < 0) { 762dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray ++FinalSize; 763af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner FinalSize += MCAsmInfo::getULEB128Size(Reg); 764af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner FinalSize += MCAsmInfo::getSLEB128Size(Offset); 765dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } else if (Reg < 64) { 766dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray ++FinalSize; 767af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner FinalSize += MCAsmInfo::getULEB128Size(Offset); 768dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } else { 769dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray ++FinalSize; 770af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner FinalSize += MCAsmInfo::getULEB128Size(Reg); 771af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner FinalSize += MCAsmInfo::getULEB128Size(Offset); 772dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 773dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 774dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 775dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray return FinalSize; 776dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray} 777dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 7785913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffrayunsigned 7795913e6c5dbaff88ac00d5e679382abc72323831aNicolas GeoffrayJITDwarfEmitter::GetExceptionTableSizeInBytes(MachineFunction* MF) const { 780dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray unsigned FinalSize = 0; 781dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 782dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Map all labels and get rid of any dead landing pads. 78347639fc5be0b8f4873d076a9ed24b9a3c0682b15Bill Wendling MMI->TidyLandingPads(JCE->getLabelLocations()); 784dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 78546510a73e977273ec67747eb34cbdb43f815e451Dan Gohman const std::vector<const GlobalVariable *> &TypeInfos = MMI->getTypeInfos(); 786dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray const std::vector<unsigned> &FilterIds = MMI->getFilterIds(); 787dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray const std::vector<LandingPadInfo> &PadInfos = MMI->getLandingPads(); 788dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray if (PadInfos.empty()) return 0; 789dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 790dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Sort the landing pads in order of their type ids. This is used to fold 791dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // duplicate actions. 792dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray SmallVector<const LandingPadInfo *, 64> LandingPads; 793dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray LandingPads.reserve(PadInfos.size()); 794dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray for (unsigned i = 0, N = PadInfos.size(); i != N; ++i) 795dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray LandingPads.push_back(&PadInfos[i]); 796dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray std::sort(LandingPads.begin(), LandingPads.end(), PadLT); 797dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 798dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Negative type ids index into FilterIds, positive type ids index into 799dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // TypeInfos. The value written for a positive type id is just the type 800dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // id itself. For a negative type id, however, the value written is the 801dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // (negative) byte offset of the corresponding FilterIds entry. The byte 802dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // offset is usually equal to the type id, because the FilterIds entries 803dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // are written using a variable width encoding which outputs one byte per 804dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // entry as long as the value written is not too large, but can differ. 805dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // This kind of complication does not occur for positive type ids because 806dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // type infos are output using a fixed width encoding. 807dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // FilterOffsets[i] holds the byte offset corresponding to FilterIds[i]. 808dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray SmallVector<int, 16> FilterOffsets; 809dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray FilterOffsets.reserve(FilterIds.size()); 810dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray int Offset = -1; 811dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray for(std::vector<unsigned>::const_iterator I = FilterIds.begin(), 812dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray E = FilterIds.end(); I != E; ++I) { 813dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray FilterOffsets.push_back(Offset); 814af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner Offset -= MCAsmInfo::getULEB128Size(*I); 815dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 816dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 817dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Compute the actions table and gather the first action index for each 818dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // landing pad site. 819dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray SmallVector<ActionEntry, 32> Actions; 820dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray SmallVector<unsigned, 64> FirstActions; 821dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray FirstActions.reserve(LandingPads.size()); 822dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 823dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray int FirstAction = 0; 824dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray unsigned SizeActions = 0; 825dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray for (unsigned i = 0, N = LandingPads.size(); i != N; ++i) { 826dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray const LandingPadInfo *LP = LandingPads[i]; 827dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray const std::vector<int> &TypeIds = LP->TypeIds; 828dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray const unsigned NumShared = i ? SharedTypeIds(LP, LandingPads[i-1]) : 0; 829dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray unsigned SizeSiteActions = 0; 830dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 831dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray if (NumShared < TypeIds.size()) { 832dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray unsigned SizeAction = 0; 833dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray ActionEntry *PrevAction = 0; 834dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 835dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray if (NumShared) { 836dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray const unsigned SizePrevIds = LandingPads[i-1]->TypeIds.size(); 837dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray assert(Actions.size()); 838dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray PrevAction = &Actions.back(); 839af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner SizeAction = MCAsmInfo::getSLEB128Size(PrevAction->NextAction) + 840af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner MCAsmInfo::getSLEB128Size(PrevAction->ValueForTypeID); 841dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray for (unsigned j = NumShared; j != SizePrevIds; ++j) { 842af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner SizeAction -= MCAsmInfo::getSLEB128Size(PrevAction->ValueForTypeID); 843dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray SizeAction += -PrevAction->NextAction; 844dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray PrevAction = PrevAction->Previous; 845dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 846dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 847dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 848dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Compute the actions. 849dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray for (unsigned I = NumShared, M = TypeIds.size(); I != M; ++I) { 850dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray int TypeID = TypeIds[I]; 851dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray assert(-1-TypeID < (int)FilterOffsets.size() && "Unknown filter id!"); 852dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray int ValueForTypeID = TypeID < 0 ? FilterOffsets[-1 - TypeID] : TypeID; 853af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner unsigned SizeTypeID = MCAsmInfo::getSLEB128Size(ValueForTypeID); 854dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 855dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray int NextAction = SizeAction ? -(SizeAction + SizeTypeID) : 0; 856af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner SizeAction = SizeTypeID + MCAsmInfo::getSLEB128Size(NextAction); 857dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray SizeSiteActions += SizeAction; 858dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 859dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray ActionEntry Action = {ValueForTypeID, NextAction, PrevAction}; 860dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray Actions.push_back(Action); 861dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 862dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray PrevAction = &Actions.back(); 863dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 864dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 865dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Record the first action of the landing pad site. 866dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray FirstAction = SizeActions + SizeSiteActions - SizeAction + 1; 867dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } // else identical - re-use previous FirstAction 868dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 869dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray FirstActions.push_back(FirstAction); 870dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 871dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Compute this sites contribution to size. 872dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray SizeActions += SizeSiteActions; 873dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 874dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 875dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Compute the call-site table. Entries must be ordered by address. 876dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray SmallVector<CallSiteEntry, 64> CallSites; 877dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 878dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray RangeMapType PadMap; 879dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray for (unsigned i = 0, N = LandingPads.size(); i != N; ++i) { 880dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray const LandingPadInfo *LandingPad = LandingPads[i]; 881dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray for (unsigned j=0, E = LandingPad->BeginLabels.size(); j != E; ++j) { 8821611273351d75b5cbe2a67485bb9831d5916fe26Chris Lattner MCSymbol *BeginLabel = LandingPad->BeginLabels[j]; 883dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray assert(!PadMap.count(BeginLabel) && "Duplicate landing pad labels!"); 884dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray PadRange P = { i, j }; 885dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray PadMap[BeginLabel] = P; 886dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 887dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 888dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 889dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray bool MayThrow = false; 8901611273351d75b5cbe2a67485bb9831d5916fe26Chris Lattner MCSymbol *LastLabel = 0; 891dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray for (MachineFunction::const_iterator I = MF->begin(), E = MF->end(); 892dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray I != E; ++I) { 893dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray for (MachineBasicBlock::const_iterator MI = I->begin(), E = I->end(); 894dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray MI != E; ++MI) { 8954406604047423576e36657c7ede266ca42e79642Dan Gohman if (!MI->isLabel()) { 896dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray MayThrow |= MI->getDesc().isCall(); 897dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray continue; 898dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 899dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 9006b4205aa44094f96115be72dd23aaf47a0257d2fChris Lattner MCSymbol *BeginLabel = MI->getOperand(0).getMCSymbol(); 9011611273351d75b5cbe2a67485bb9831d5916fe26Chris Lattner 902dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray if (BeginLabel == LastLabel) 903dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray MayThrow = false; 904dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 905dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray RangeMapType::iterator L = PadMap.find(BeginLabel); 906dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 907dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray if (L == PadMap.end()) 908dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray continue; 909dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 910dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray PadRange P = L->second; 911dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray const LandingPadInfo *LandingPad = LandingPads[P.PadIndex]; 912dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 913dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray assert(BeginLabel == LandingPad->BeginLabels[P.RangeIndex] && 914dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray "Inconsistent landing pad map!"); 915dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 916dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // If some instruction between the previous try-range and this one may 917dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // throw, create a call-site entry with no landing pad for the region 918dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // between the try-ranges. 919dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray if (MayThrow) { 920dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray CallSiteEntry Site = {LastLabel, BeginLabel, 0, 0}; 921dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray CallSites.push_back(Site); 922dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 923dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 924dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray LastLabel = LandingPad->EndLabels[P.RangeIndex]; 925dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray CallSiteEntry Site = {BeginLabel, LastLabel, 926dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray LandingPad->LandingPadLabel, FirstActions[P.PadIndex]}; 927dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 928dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray assert(Site.BeginLabel && Site.EndLabel && Site.PadLabel && 929dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray "Invalid landing pad!"); 930dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 931dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Try to merge with the previous call-site. 932dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray if (CallSites.size()) { 933719de53742167ca3f0e6b2efafb6eac18bd90452Dan Gohman CallSiteEntry &Prev = CallSites.back(); 934dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray if (Site.PadLabel == Prev.PadLabel && Site.Action == Prev.Action) { 935dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Extend the range of the previous entry. 936dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray Prev.EndLabel = Site.EndLabel; 937dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray continue; 938dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 939dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 940dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 941dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Otherwise, create a new call-site. 942dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray CallSites.push_back(Site); 943dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 944dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 945dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // If some instruction between the previous try-range and the end of the 946dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // function may throw, create a call-site entry with no landing pad for the 947dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // region following the try-range. 948dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray if (MayThrow) { 949dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray CallSiteEntry Site = {LastLabel, 0, 0, 0}; 950dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray CallSites.push_back(Site); 951dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 952dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 953dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Final tallies. 954dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray unsigned SizeSites = CallSites.size() * (sizeof(int32_t) + // Site start. 955dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray sizeof(int32_t) + // Site length. 956dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray sizeof(int32_t)); // Landing pad. 957dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray for (unsigned i = 0, e = CallSites.size(); i < e; ++i) 958af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner SizeSites += MCAsmInfo::getULEB128Size(CallSites[i].Action); 959dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 960dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray unsigned SizeTypes = TypeInfos.size() * TD->getPointerSize(); 961dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 962dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray unsigned TypeOffset = sizeof(int8_t) + // Call site format 963dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Call-site table length 964af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner MCAsmInfo::getULEB128Size(SizeSites) + 965dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray SizeSites + SizeActions + SizeTypes; 966dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 967dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray unsigned TotalSize = sizeof(int8_t) + // LPStart format 968dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray sizeof(int8_t) + // TType format 969af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner MCAsmInfo::getULEB128Size(TypeOffset) + // TType base offset 970dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray TypeOffset; 971dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 972dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray unsigned SizeAlign = (4 - TotalSize) & 3; 973dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 974dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Begin the exception table. 9755913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffray FinalSize = RoundUpToAlign(FinalSize, 4); 976dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray for (unsigned i = 0; i != SizeAlign; ++i) { 977dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray ++FinalSize; 978dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 979dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 980dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray unsigned PointerSize = TD->getPointerSize(); 981dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 982dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Emit the header. 983dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray ++FinalSize; 984dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Asm->EOL("LPStart format (DW_EH_PE_omit)"); 985dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray ++FinalSize; 986dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Asm->EOL("TType format (DW_EH_PE_absptr)"); 987dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray ++FinalSize; 988dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Asm->EOL("TType base offset"); 989dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray ++FinalSize; 990dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Asm->EOL("Call site format (DW_EH_PE_udata4)"); 991dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray ++FinalSize; 992dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Asm->EOL("Call-site table length"); 993dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 994dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Emit the landing pad site information. 995dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray for (unsigned i = 0; i < CallSites.size(); ++i) { 996dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray CallSiteEntry &S = CallSites[i]; 997dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 998dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Asm->EOL("Region start"); 999dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray FinalSize += PointerSize; 1000dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 1001dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray //Asm->EOL("Region length"); 1002dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray FinalSize += PointerSize; 1003dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 1004dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Asm->EOL("Landing pad"); 1005dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray FinalSize += PointerSize; 1006dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 1007af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner FinalSize += MCAsmInfo::getULEB128Size(S.Action); 1008dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Asm->EOL("Action"); 1009dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 1010dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 1011dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Emit the actions. 1012dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray for (unsigned I = 0, N = Actions.size(); I != N; ++I) { 1013dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray ActionEntry &Action = Actions[I]; 1014dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 1015dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray //Asm->EOL("TypeInfo index"); 1016af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner FinalSize += MCAsmInfo::getSLEB128Size(Action.ValueForTypeID); 1017dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray //Asm->EOL("Next action"); 1018af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner FinalSize += MCAsmInfo::getSLEB128Size(Action.NextAction); 1019dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 1020dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 1021dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Emit the type ids. 1022dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray for (unsigned M = TypeInfos.size(); M; --M) { 1023dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Asm->EOL("TypeInfo"); 1024dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray FinalSize += PointerSize; 1025dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 1026dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 1027dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray // Emit the filter typeids. 1028dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray for (unsigned j = 0, M = FilterIds.size(); j < M; ++j) { 1029dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray unsigned TypeID = FilterIds[j]; 1030af76e592c7f9deff0e55c13dbb4a34f07f1c7f64Chris Lattner FinalSize += MCAsmInfo::getULEB128Size(TypeID); 1031dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray //Asm->EOL("Filter TypeInfo index"); 1032dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray } 1033dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 10345913e6c5dbaff88ac00d5e679382abc72323831aNicolas Geoffray FinalSize = RoundUpToAlign(FinalSize, 4); 1035dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray 1036dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray return FinalSize; 1037dc17ab2bf0c4d325b87ac8130004ab11f3f7106dNicolas Geoffray} 1038