This patch implements runtime Mips specific

setting of ELF header e_flags.

Contributer: Jack Carter
 
llvm-svn: 173884
This commit is contained in:
Jack Carter 2013-01-30 02:16:36 +00:00
parent 7cd7b1f749
commit 9054213d30
7 changed files with 168 additions and 3 deletions

View File

@ -0,0 +1,61 @@
//===-- MipsELFStreamer.cpp - MipsELFStreamer ---------------------------===//
//
// The LLVM Compiler Infrastructure
//
// This file is distributed under the University of Illinois Open Source
// License. See LICENSE.TXT for details.
//
//===-------------------------------------------------------------------===//
#include "MCTargetDesc/MipsELFStreamer.h"
#include "MipsSubtarget.h"
#include "llvm/MC/MCAssembler.h"
#include "llvm/Support/ELF.h"
#include "llvm/Support/ErrorHandling.h"
namespace llvm {
MCELFStreamer* createMipsELFStreamer(MCContext &Context, MCAsmBackend &TAB,
raw_ostream &OS, MCCodeEmitter *Emitter,
bool RelaxAll, bool NoExecStack) {
MipsELFStreamer *S = new MipsELFStreamer(Context, TAB, OS, Emitter,
RelaxAll, NoExecStack);
return S;
}
// For llc. Set a group of ELF header flags
void
MipsELFStreamer::emitELFHeaderFlagsCG(const MipsSubtarget &Subtarget) {
if (hasRawTextSupport())
return;
// Update e_header flags
MCAssembler& MCA = getAssembler();
unsigned EFlags = MCA.getELFHeaderEFlags();
EFlags |= ELF::EF_MIPS_NOREORDER;
// Architecture
if (Subtarget.hasMips64r2())
EFlags |= ELF::EF_MIPS_ARCH_64R2;
else if (Subtarget.hasMips64())
EFlags |= ELF::EF_MIPS_ARCH_64;
else if (Subtarget.hasMips32r2())
EFlags |= ELF::EF_MIPS_ARCH_32R2;
else
EFlags |= ELF::EF_MIPS_ARCH_32;
// Relocation Model
Reloc::Model RM = Subtarget.getRelocationModel();
if (RM == Reloc::PIC_ || RM == Reloc::Default)
EFlags |= ELF::EF_MIPS_PIC;
else if (RM == Reloc::Static)
; // Do nothing for Reloc::Static
else
llvm_unreachable("Unsupported relocation model for e_flags");
MCA.setELFHeaderEFlags(EFlags);
}
}

View File

@ -0,0 +1,37 @@
//=== MipsELFStreamer.h - MipsELFStreamer ------------------------------===//
//
// The LLVM Compiler Infrastructure
//
// This file is distributed under the University of Illinois Open Source
// License. See LICENCE.TXT for details.
//
//===-------------------------------------------------------------------===//
#ifndef MIPSELFSTREAMER_H_
#define MIPSELFSTREAMER_H_
#include "llvm/MC/MCELFStreamer.h"
namespace llvm {
class MipsSubtarget;
class MipsELFStreamer : public MCELFStreamer {
private:
unsigned EFlags;
public:
MipsELFStreamer(MCContext &Context, MCAsmBackend &TAB,
raw_ostream &OS, MCCodeEmitter *Emitter,
bool RelaxAll, bool NoExecStack)
: MCELFStreamer(Context, TAB, OS, Emitter), EFlags(0) {
}
~MipsELFStreamer() {}
void emitELFHeaderFlagsCG(const MipsSubtarget &Subtarget);
// void emitELFHeaderFlagCG(unsigned Val);
};
MCELFStreamer* createMipsELFStreamer(MCContext &Context, MCAsmBackend &TAB,
raw_ostream &OS, MCCodeEmitter *Emitter,
bool RelaxAll, bool NoExecStack);
}
#endif /* MIPSELFSTREAMER_H_ */

View File

@ -11,6 +11,7 @@
//
//===----------------------------------------------------------------------===//
#include "MCTargetDesc/MipsELFStreamer.h"
#include "MipsMCTargetDesc.h"
#include "InstPrinter/MipsInstPrinter.h"
#include "MipsMCAsmInfo.h"
@ -131,7 +132,7 @@ static MCStreamer *createMCStreamer(const Target &T, StringRef TT,
bool NoExecStack) {
Triple TheTriple(TT);
return createELFStreamer(Ctx, MAB, _OS, _Emitter, RelaxAll, NoExecStack);
return createMipsELFStreamer(Ctx, MAB, _OS, _Emitter, RelaxAll, NoExecStack);
}
extern "C" void LLVMInitializeMipsTargetMC() {

View File

@ -15,6 +15,7 @@
#define DEBUG_TYPE "mips-asm-printer"
#include "InstPrinter/MipsInstPrinter.h"
#include "MCTargetDesc/MipsBaseInfo.h"
#include "MCTargetDesc/MipsELFStreamer.h"
#include "Mips.h"
#include "MipsAsmPrinter.h"
#include "MipsInstrInfo.h"
@ -545,9 +546,13 @@ void MipsAsmPrinter::EmitStartOfAsmFile(Module &M) {
void MipsAsmPrinter::EmitEndOfAsmFile(Module &M) {
if (OutStreamer.hasRawTextSupport()) return;
// Emit Mips ELF register info
Subtarget->getMReginfo().emitMipsReginfoSectionCG(
OutStreamer, getObjFileLowering(), *Subtarget);
MipsELFStreamer & MES = static_cast<MipsELFStreamer &>(OutStreamer);
MES.emitELFHeaderFlagsCG(*Subtarget);
}
MachineLocation

View File

@ -26,13 +26,13 @@ void MipsSubtarget::anchor() { }
MipsSubtarget::MipsSubtarget(const std::string &TT, const std::string &CPU,
const std::string &FS, bool little,
Reloc::Model RM) :
Reloc::Model _RM) :
MipsGenSubtargetInfo(TT, CPU, FS),
MipsArchVersion(Mips32), MipsABI(UnknownABI), IsLittle(little),
IsSingleFloat(false), IsFP64bit(false), IsGP64bit(false), HasVFPU(false),
IsLinux(true), HasSEInReg(false), HasCondMov(false), HasSwap(false),
HasBitCount(false), HasFPIdx(false),
InMips16Mode(false), HasDSP(false), HasDSPR2(false), IsAndroid(false)
InMips16Mode(false), HasDSP(false), HasDSPR2(false), IsAndroid(false), RM(_RM)
{
std::string CPUName = CPU;
if (CPUName.empty())

View File

@ -100,6 +100,9 @@ protected:
// The instance to the register info section object
MipsReginfo MRI;
// Relocation Model
Reloc::Model RM;
public:
virtual bool enablePostRAScheduler(CodeGenOpt::Level OptLevel,
AntiDepBreakMode& Mode,
@ -152,6 +155,9 @@ public:
// Grab MipsRegInfo object
const MipsReginfo &getMReginfo() const { return MRI; }
// Grab relocation model
Reloc::Model getRelocationModel() const {return RM;}
};
} // End llvm namespace

View File

@ -0,0 +1,55 @@
; This tests ELF EFLAGS setting with direct object.
; When the assembler is ready a .s file for it will
; be created.
; Non-shared (static) is the absence of pic and or cpic.
; EF_MIPS_NOREORDER (0x00000001) is always on by default currently
; EF_MIPS_PIC (0x00000002)
; EF_MIPS_CPIC (0x00000004) - not tested yet
; EF_MIPS_ABI2 (0x00000020) - n32 not tested yet
; EF_MIPS_ARCH_32 (0x50000000)
; EF_MIPS_ARCH_64 (0x60000000)
; EF_MIPS_ARCH_32R2 (0x70000000)
; EF_MIPS_ARCH_64R2 (0x80000000)
; RUN: llc -filetype=obj -mtriple mipsel-unknown-linux -mcpu=mips32 -relocation-model=static %s -o - | elf-dump --dump-section-data | FileCheck -check-prefix=CHECK-BE32 %s
; RUN: llc -filetype=obj -mtriple mipsel-unknown-linux -mcpu=mips32 %s -o - | elf-dump --dump-section-data | FileCheck -check-prefix=CHECK-BE32_PIC %s
; RUN: llc -filetype=obj -mtriple mipsel-unknown-linux -mcpu=mips32r2 -relocation-model=static %s -o - | elf-dump --dump-section-data | FileCheck -check-prefix=CHECK-BE32R2 %s
; RUN: llc -filetype=obj -mtriple mipsel-unknown-linux -mcpu=mips32r2 %s -o - | elf-dump --dump-section-data | FileCheck -check-prefix=CHECK-BE32R2_PIC %s
; RUN: llc -filetype=obj -mtriple mipsel-unknown-linux -mcpu=mips64 -relocation-model=static %s -o - | elf-dump --dump-section-data | FileCheck -check-prefix=CHECK-BE64 %s
; RUN: llc -filetype=obj -mtriple mipsel-unknown-linux -mcpu=mips64 %s -o - | elf-dump --dump-section-data | FileCheck -check-prefix=CHECK-BE64_PIC %s
; RUN: llc -filetype=obj -mtriple mipsel-unknown-linux -mcpu=mips64r2 -relocation-model=static %s -o - | elf-dump --dump-section-data | FileCheck -check-prefix=CHECK-BE64R2 %s
; RUN: llc -filetype=obj -mtriple mipsel-unknown-linux -mcpu=mips64r2 %s -o - | elf-dump --dump-section-data | FileCheck -check-prefix=CHECK-BE64R2_PIC %s
; 32(R1) bit with NO_REORDER and static
; CHECK-BE32: ('e_flags', 0x50000001)
;
; 32(R1) bit with NO_REORDER and PIC
; CHECK-BE32_PIC: ('e_flags', 0x50000003)
;
; 32R2 bit with NO_REORDER and static
; CHECK-BE32R2: ('e_flags', 0x70000001)
;
; 32R2 bit with NO_REORDER and PIC
; CHECK-BE32R2_PIC: ('e_flags', 0x70000003)
;
; 64(R1) bit with NO_REORDER and static
; CHECK-BE64: ('e_flags', 0x60000001)
;
; 64(R1) bit with NO_REORDER and PIC
; CHECK-BE64_PIC: ('e_flags', 0x60000003)
;
; 64R2 bit with NO_REORDER and static
; CHECK-BE64R2: ('e_flags', 0x80000001)
;
; 64R2 bit with NO_REORDER and PIC
; CHECK-BE64R2_PIC: ('e_flags', 0x80000003)
;
define i32 @main() nounwind {
entry:
ret i32 0
}