mirror of
https://github.com/RPCS3/llvm-mirror.git
synced 2024-11-22 18:54:02 +01:00
CodeGen: add support for emitting ObjC image info
This ensures that we can emit the ObjC Image Info structure on COFF and ELF as well. The frontend already would attempt to emit this information but would get dropped when generating assembly or an object file. llvm-svn: 304736
This commit is contained in:
parent
144e4b1e4c
commit
381d08b36d
@ -41,6 +41,11 @@ public:
|
||||
TargetLoweringObjectFileELF() = default;
|
||||
~TargetLoweringObjectFileELF() override = default;
|
||||
|
||||
/// Emit Obj-C garbage collection and linker options.
|
||||
void emitModuleFlags(MCStreamer &Streamer,
|
||||
ArrayRef<Module::ModuleFlagEntry> ModuleFlags,
|
||||
const TargetMachine &TM) const override;
|
||||
|
||||
void emitPersonalityValue(MCStreamer &Streamer, const DataLayout &TM,
|
||||
const MCSymbol *Sym) const override;
|
||||
|
||||
@ -149,8 +154,7 @@ public:
|
||||
MCSection *getSectionForJumpTable(const Function &F,
|
||||
const TargetMachine &TM) const override;
|
||||
|
||||
/// Emit Obj-C garbage collection and linker options. Only linker option
|
||||
/// emission is implemented for COFF.
|
||||
/// Emit Obj-C garbage collection and linker options.
|
||||
void emitModuleFlags(MCStreamer &Streamer,
|
||||
ArrayRef<Module::ModuleFlagEntry> ModuleFlags,
|
||||
const TargetMachine &TM) const override;
|
||||
|
@ -61,10 +61,53 @@
|
||||
using namespace llvm;
|
||||
using namespace dwarf;
|
||||
|
||||
static void GetObjCImageInfo(ArrayRef<Module::ModuleFlagEntry> ModuleFlags,
|
||||
unsigned &Version, unsigned &Flags,
|
||||
StringRef &Section) {
|
||||
for (const auto &MFE: ModuleFlags) {
|
||||
// Ignore flags with 'Require' behaviour.
|
||||
if (MFE.Behavior == Module::Require)
|
||||
continue;
|
||||
|
||||
StringRef Key = MFE.Key->getString();
|
||||
if (Key == "Objective-C Image Info Version") {
|
||||
Version = mdconst::extract<ConstantInt>(MFE.Val)->getZExtValue();
|
||||
} else if (Key == "Objective-C Garbage Collection" ||
|
||||
Key == "Objective-C GC Only" ||
|
||||
Key == "Objective-C Is Simulated" ||
|
||||
Key == "Objective-C Class Properties" ||
|
||||
Key == "Objective-C Image Swift Version") {
|
||||
Flags |= mdconst::extract<ConstantInt>(MFE.Val)->getZExtValue();
|
||||
} else if (Key == "Objective-C Image Info Section") {
|
||||
Section = cast<MDString>(MFE.Val)->getString();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//===----------------------------------------------------------------------===//
|
||||
// ELF
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
void TargetLoweringObjectFileELF::emitModuleFlags(
|
||||
MCStreamer &Streamer, ArrayRef<Module::ModuleFlagEntry> ModuleFlags,
|
||||
const TargetMachine &TM) const {
|
||||
unsigned Version = 0;
|
||||
unsigned Flags = 0;
|
||||
StringRef Section;
|
||||
|
||||
GetObjCImageInfo(ModuleFlags, Version, Flags, Section);
|
||||
if (Section.empty())
|
||||
return;
|
||||
|
||||
auto &C = getContext();
|
||||
auto *S = C.getELFSection(Section, ELF::SHT_PROGBITS, ELF::SHF_ALLOC);
|
||||
Streamer.SwitchSection(S);
|
||||
Streamer.EmitLabel(C.getOrCreateSymbol(StringRef("OBJC_IMAGE_INFO")));
|
||||
Streamer.EmitIntValue(Version, 4);
|
||||
Streamer.EmitIntValue(Flags, 4);
|
||||
Streamer.AddBlankLine();
|
||||
}
|
||||
|
||||
MCSymbol *TargetLoweringObjectFileELF::getCFIPersonalitySymbol(
|
||||
const GlobalValue *GV, const TargetMachine &TM,
|
||||
MachineModuleInfo *MMI) const {
|
||||
@ -579,32 +622,12 @@ void TargetLoweringObjectFileMachO::Initialize(MCContext &Ctx,
|
||||
void TargetLoweringObjectFileMachO::emitModuleFlags(
|
||||
MCStreamer &Streamer, ArrayRef<Module::ModuleFlagEntry> ModuleFlags,
|
||||
const TargetMachine &TM) const {
|
||||
unsigned VersionVal = 0;
|
||||
unsigned ImageInfoFlags = 0;
|
||||
MDNode *LinkerOptions = nullptr;
|
||||
StringRef SectionVal;
|
||||
|
||||
for (const auto &MFE : ModuleFlags) {
|
||||
// Ignore flags with 'Require' behavior.
|
||||
if (MFE.Behavior == Module::Require)
|
||||
continue;
|
||||
|
||||
StringRef Key = MFE.Key->getString();
|
||||
Metadata *Val = MFE.Val;
|
||||
|
||||
if (Key == "Objective-C Image Info Version") {
|
||||
VersionVal = mdconst::extract<ConstantInt>(Val)->getZExtValue();
|
||||
} else if (Key == "Objective-C Garbage Collection" ||
|
||||
Key == "Objective-C GC Only" ||
|
||||
Key == "Objective-C Is Simulated" ||
|
||||
Key == "Objective-C Class Properties" ||
|
||||
Key == "Objective-C Image Swift Version") {
|
||||
ImageInfoFlags |= mdconst::extract<ConstantInt>(Val)->getZExtValue();
|
||||
} else if (Key == "Objective-C Image Info Section") {
|
||||
SectionVal = cast<MDString>(Val)->getString();
|
||||
} else if (Key == "Linker Options") {
|
||||
LinkerOptions = cast<MDNode>(Val);
|
||||
}
|
||||
if (Key == "Linker Options")
|
||||
LinkerOptions = cast<MDNode>(MFE.Val);
|
||||
}
|
||||
|
||||
// Emit the linker options if present.
|
||||
@ -617,8 +640,14 @@ void TargetLoweringObjectFileMachO::emitModuleFlags(
|
||||
}
|
||||
}
|
||||
|
||||
unsigned VersionVal = 0;
|
||||
unsigned ImageInfoFlags = 0;
|
||||
StringRef SectionVal;
|
||||
GetObjCImageInfo(ModuleFlags, VersionVal, ImageInfoFlags, SectionVal);
|
||||
|
||||
// The section is mandatory. If we don't have it, then we don't have GC info.
|
||||
if (SectionVal.empty()) return;
|
||||
if (SectionVal.empty())
|
||||
return;
|
||||
|
||||
StringRef Segment, Section;
|
||||
unsigned TAA = 0, StubSize = 0;
|
||||
@ -1156,6 +1185,24 @@ void TargetLoweringObjectFileCOFF::emitModuleFlags(
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
unsigned Version = 0;
|
||||
unsigned Flags = 0;
|
||||
StringRef Section;
|
||||
|
||||
GetObjCImageInfo(ModuleFlags, Version, Flags, Section);
|
||||
if (Section.empty())
|
||||
return;
|
||||
|
||||
auto &C = getContext();
|
||||
auto *S = C.getCOFFSection(
|
||||
Section, COFF::IMAGE_SCN_CNT_INITIALIZED_DATA | COFF::IMAGE_SCN_MEM_READ,
|
||||
SectionKind::getReadOnly());
|
||||
Streamer.SwitchSection(S);
|
||||
Streamer.EmitLabel(C.getOrCreateSymbol(StringRef("OBJC_IMAGE_INFO")));
|
||||
Streamer.EmitIntValue(Version, 4);
|
||||
Streamer.EmitIntValue(Flags, 4);
|
||||
Streamer.AddBlankLine();
|
||||
}
|
||||
|
||||
void TargetLoweringObjectFileCOFF::Initialize(MCContext &Ctx,
|
||||
|
14
test/Object/objc-imageinfo-coff.ll
Normal file
14
test/Object/objc-imageinfo-coff.ll
Normal file
@ -0,0 +1,14 @@
|
||||
; RUN: llc -mtriple x86_64-unknown-windows-msvc -filetype asm -o - %s | FileCheck %s
|
||||
|
||||
!llvm.module.flags = !{!0, !1, !2, !3}
|
||||
|
||||
!0 = !{i32 1, !"Objective-C Version", i32 2}
|
||||
!1 = !{i32 1, !"Objective-C Image Info Version", i32 0}
|
||||
!2 = !{i32 1, !"Objective-C Image Info Section", !".objc_imageinfo$B"}
|
||||
!3 = !{i32 1, !"Objective-C Garbage Collection", i32 2}
|
||||
|
||||
; CHECK: .section .objc_imageinfo$B,"dr"
|
||||
; CHECK: OBJC_IMAGE_INFO:
|
||||
; CHECK: .long 0
|
||||
; CHECK: .long 2
|
||||
|
14
test/Object/objc-imageinfo-elf.ll
Normal file
14
test/Object/objc-imageinfo-elf.ll
Normal file
@ -0,0 +1,14 @@
|
||||
; RUN: llc -mtriple x86_64-unknown-linux-gnu -filetype asm -o - %s | FileCheck %s
|
||||
|
||||
!llvm.module.flags = !{!0, !1, !2, !3}
|
||||
|
||||
!0 = !{i32 1, !"Objective-C Version", i32 2}
|
||||
!1 = !{i32 1, !"Objective-C Image Info Version", i32 0}
|
||||
!2 = !{i32 1, !"Objective-C Image Info Section", !"objc_imageinfo"}
|
||||
!3 = !{i32 1, !"Objective-C Garbage Collection", i32 2}
|
||||
|
||||
; CHECK: .section objc_imageinfo
|
||||
; CHECK: OBJC_IMAGE_INFO:
|
||||
; CHECK: .long 0
|
||||
; CHECK: .long 2
|
||||
|
14
test/Object/objc-imageinfo-macho.ll
Normal file
14
test/Object/objc-imageinfo-macho.ll
Normal file
@ -0,0 +1,14 @@
|
||||
; RUN: llc -mtriple x86_64-apple-ios -filetype asm -o - %s | FileCheck %s
|
||||
|
||||
!llvm.module.flags = !{!0, !1, !2, !3}
|
||||
|
||||
!0 = !{i32 1, !"Objective-C Version", i32 2}
|
||||
!1 = !{i32 1, !"Objective-C Image Info Version", i32 0}
|
||||
!2 = !{i32 1, !"Objective-C Image Info Section", !"__DATA,__objc_imageinfo,regular,no_dead_strip"}
|
||||
!3 = !{i32 1, !"Objective-C Garbage Collection", i32 2}
|
||||
|
||||
; CHECK: .section __DATA,__objc_imageinfo,regular,no_dead_strip
|
||||
; CHECK: L_OBJC_IMAGE_INFO:
|
||||
; CHECK: .long 0
|
||||
; CHECK: .long 2
|
||||
|
Loading…
Reference in New Issue
Block a user