diff options
Diffstat (limited to 'lib/Target/ARM/AsmPrinter/ARMAsmPrinter.cpp')
-rw-r--r-- | lib/Target/ARM/AsmPrinter/ARMAsmPrinter.cpp | 128 |
1 files changed, 52 insertions, 76 deletions
diff --git a/lib/Target/ARM/AsmPrinter/ARMAsmPrinter.cpp b/lib/Target/ARM/AsmPrinter/ARMAsmPrinter.cpp index fe1c980..400f628a 100644 --- a/lib/Target/ARM/AsmPrinter/ARMAsmPrinter.cpp +++ b/lib/Target/ARM/AsmPrinter/ARMAsmPrinter.cpp @@ -21,6 +21,7 @@ #include "ARMMachineFunctionInfo.h" #include "llvm/Constants.h" #include "llvm/Module.h" +#include "llvm/MDNode.h" #include "llvm/CodeGen/AsmPrinter.h" #include "llvm/CodeGen/DwarfWriter.h" #include "llvm/CodeGen/MachineModuleInfo.h" @@ -96,9 +97,7 @@ namespace { const char *Modifier = 0); void printSOImmOperand(const MachineInstr *MI, int opNum); void printSOImm2PartOperand(const MachineInstr *MI, int opNum); - void printSOOperand(const MachineInstr *MI, int OpNum); void printSORegOperand(const MachineInstr *MI, int opNum); - void printT2SOImmOperand(const MachineInstr *MI, int opNum); void printAddrMode2Operand(const MachineInstr *MI, int OpNo); void printAddrMode2OffsetOperand(const MachineInstr *MI, int OpNo); void printAddrMode3Operand(const MachineInstr *MI, int OpNo); @@ -110,6 +109,7 @@ namespace { void printAddrModePCOperand(const MachineInstr *MI, int OpNo, const char *Modifier = 0); void printBitfieldInvMaskImmOperand (const MachineInstr *MI, int OpNo); + void printThumbAddrModeRROperand(const MachineInstr *MI, int OpNo); void printThumbAddrModeRI5Operand(const MachineInstr *MI, int OpNo, unsigned Scale); @@ -117,6 +117,10 @@ namespace { void printThumbAddrModeS2Operand(const MachineInstr *MI, int OpNo); void printThumbAddrModeS4Operand(const MachineInstr *MI, int OpNo); void printThumbAddrModeSPOperand(const MachineInstr *MI, int OpNo); + + void printT2SOImmOperand(const MachineInstr *MI, int opNum); + void printT2SOOperand(const MachineInstr *MI, int OpNum); + void printPredicateOperand(const MachineInstr *MI, int opNum); void printSBitModifierOperand(const MachineInstr *MI, int opNum); void printPCLabel(const MachineInstr *MI, int opNum); @@ -169,11 +173,6 @@ namespace { O << ")"; } O << "\n"; - - // If the constant pool value is a extern weak symbol, remember to emit - // the weak reference. - if (GV && GV->hasExternalWeakLinkage()) - ExtWeakSymbols.insert(GV); } void getAnalysisUsage(AnalysisUsage &AU) const { @@ -331,8 +330,6 @@ void ARMAsmPrinter::printOperand(const MachineInstr *MI, int opNum, if (isCallOp && Subtarget->isTargetELF() && TM.getRelocationModel() == Reloc::PIC_) O << "(PLT)"; - if (GV->hasExternalWeakLinkage()) - ExtWeakSymbols.insert(GV); break; } case MachineOperand::MO_ExternalSymbol: { @@ -408,32 +405,10 @@ void ARMAsmPrinter::printSOImm2PartOperand(const MachineInstr *MI, int OpNum) { printSOImm(O, ARM_AM::getSOImmVal(V2), VerboseAsm, TAI); } -// Constant shifts so_reg is a 3-operand unit corresponding to register forms of -// the A5.1 "Addressing Mode 1 - Data-processing operands" forms. This -// includes: -// REG 0 - e.g. R5 -// REG IMM, SH_OPC - e.g. R5, LSL #3 -void ARMAsmPrinter::printSOOperand(const MachineInstr *MI, int OpNum) { - const MachineOperand &MO1 = MI->getOperand(OpNum); - const MachineOperand &MO2 = MI->getOperand(OpNum+1); - - unsigned Reg = MO1.getReg(); - assert(TargetRegisterInfo::isPhysicalRegister(Reg)); - O << TM.getRegisterInfo()->getAsmName(Reg); - - // Print the shift opc. - O << ", " - << ARM_AM::getShiftOpcStr(ARM_AM::getSORegShOp(MO2.getImm())) - << " "; - - assert(MO2.isImm() && "Not a valid t2_so_reg value!"); - O << "#" << ARM_AM::getSORegOffset(MO2.getImm()); -} - // so_reg is a 4-operand unit corresponding to register forms of the A5.1 // "Addressing Mode 1 - Data-processing operands" forms. This includes: -// REG 0 0 - e.g. R5 -// REG REG 0,SH_OPC - e.g. R5, ROR R3 +// REG 0 0 - e.g. R5 +// REG REG 0,SH_OPC - e.g. R5, ROR R3 // REG 0 IMM,SH_OPC - e.g. R5, LSL #3 void ARMAsmPrinter::printSORegOperand(const MachineInstr *MI, int Op) { const MachineOperand &MO1 = MI->getOperand(Op); @@ -457,24 +432,6 @@ void ARMAsmPrinter::printSORegOperand(const MachineInstr *MI, int Op) { } } -static void printT2SOImm(raw_ostream &O, int64_t V) { - unsigned Imm = ARM_AM::getT2SOImmValDecode(V); - - // Always print the immediate directly, as the "rotate" form - // is deprecated in some contexts. - O << "#" << Imm; -} - -/// printT2SOImmOperand - T2SOImm is: -/// 1. a 4-bit splat control value and 8 bit immediate value -/// 2. a 5-bit rotate amount and a non-zero 8-bit immediate value -/// represented by a normalizedin 7-bit value (msb is always 1) -void ARMAsmPrinter::printT2SOImmOperand(const MachineInstr *MI, int OpNum) { - const MachineOperand &MO = MI->getOperand(OpNum); - assert(MO.isImm() && "Not a valid so_imm value!"); - printT2SOImm(O, MO.getImm()); -} - void ARMAsmPrinter::printAddrMode2Operand(const MachineInstr *MI, int Op) { const MachineOperand &MO1 = MI->getOperand(Op); const MachineOperand &MO2 = MI->getOperand(Op+1); @@ -643,8 +600,8 @@ void ARMAsmPrinter::printBitfieldInvMaskImmOperand(const MachineInstr *MI, int Op) { const MachineOperand &MO = MI->getOperand(Op); uint32_t v = ~MO.getImm(); - int32_t lsb = ffs (v) - 1; - int32_t width = fls (v) - lsb; + int32_t lsb = CountTrailingZeros_32(v); + int32_t width = (32 - CountLeadingZeros_32 (v)) - lsb; assert(MO.isImm() && "Not a valid bf_inv_mask_imm value!"); O << "#" << lsb << ", #" << width; } @@ -702,6 +659,42 @@ void ARMAsmPrinter::printThumbAddrModeSPOperand(const MachineInstr *MI,int Op) { O << "]"; } +/// printT2SOImmOperand - T2SOImm is: +/// 1. a 4-bit splat control value and 8 bit immediate value +/// 2. a 5-bit rotate amount and a non-zero 8-bit immediate value +/// represented by a normalizedin 7-bit value (msb is always 1) +void ARMAsmPrinter::printT2SOImmOperand(const MachineInstr *MI, int OpNum) { + const MachineOperand &MO = MI->getOperand(OpNum); + assert(MO.isImm() && "Not a valid so_imm value!"); + + unsigned Imm = ARM_AM::getT2SOImmValDecode(MO.getImm()); + // Always print the immediate directly, as the "rotate" form + // is deprecated in some contexts. + O << "#" << Imm; +} + +// Constant shifts t2_so_reg is a 2-operand unit corresponding to the Thumb2 +// register with shift forms. +// REG 0 0 - e.g. R5 +// REG IMM, SH_OPC - e.g. R5, LSL #3 +void ARMAsmPrinter::printT2SOOperand(const MachineInstr *MI, int OpNum) { + const MachineOperand &MO1 = MI->getOperand(OpNum); + const MachineOperand &MO2 = MI->getOperand(OpNum+1); + + unsigned Reg = MO1.getReg(); + assert(TargetRegisterInfo::isPhysicalRegister(Reg)); + O << TM.getRegisterInfo()->getAsmName(Reg); + + // Print the shift opc. + O << ", " + << ARM_AM::getShiftOpcStr(ARM_AM::getSORegShOp(MO2.getImm())) + << " "; + + assert(MO2.isImm() && "Not a valid t2_so_reg value!"); + O << "#" << ARM_AM::getSORegOffset(MO2.getImm()); +} + + void ARMAsmPrinter::printPredicateOperand(const MachineInstr *MI, int opNum) { ARMCC::CondCodes CC = (ARMCC::CondCodes)MI->getOperand(opNum).getImm(); if (CC != ARMCC::AL) @@ -749,10 +742,6 @@ void ARMAsmPrinter::printCPInstOperand(const MachineInstr *MI, int OpNo, EmitMachineConstantPoolValue(MCPE.Val.MachineCPVal); } else { EmitGlobalConstant(MCPE.Val.ConstVal); - // remember to emit the weak reference - if (const GlobalValue *GV = dyn_cast<GlobalValue>(MCPE.Val.ConstVal)) - if (GV->hasExternalWeakLinkage()) - ExtWeakSymbols.insert(GV); } } } @@ -934,6 +923,8 @@ void ARMAsmPrinter::printModuleLevelGV(const GlobalVariable* GVar) { std::string name = Mang->getValueName(GVar); Constant *C = GVar->getInitializer(); + if (isa<MDNode>(C) || isa<MDString>(C)) + return; const Type *Type = C->getType(); unsigned Size = TD->getTypeAllocSize(Type); unsigned Align = TD->getPreferredAlignmentLog(GVar); @@ -1046,12 +1037,6 @@ void ARMAsmPrinter::printModuleLevelGV(const GlobalVariable* GVar) { if (TAI->hasDotTypeDotSizeDirective()) O << "\t.size " << name << ", " << Size << "\n"; - // If the initializer is a extern weak symbol, remember to emit the weak - // reference! - if (const GlobalValue *GV = dyn_cast<GlobalValue>(C)) - if (GV->hasExternalWeakLinkage()) - ExtWeakSymbols.insert(GV); - EmitGlobalConstant(C); O << '\n'; } @@ -1135,18 +1120,12 @@ bool ARMAsmPrinter::doFinalization(Module &M) { } - // Emit initial debug information. - DW->EndModule(); - // Funny Darwin hack: This flag tells the linker that no global symbols // contain code that falls through to other global symbols (e.g. the obvious // implementation of multiple entry points). If this doesn't occur, the // linker can safely perform dead code stripping. Since LLVM never // generates code that does this, it is always safe to set. O << "\t.subsections_via_symbols\n"; - } else { - // Emit final debug information for ELF. - DW->EndModule(); } return AsmPrinter::doFinalization(M); @@ -1158,7 +1137,7 @@ bool ARMAsmPrinter::doFinalization(Module &M) { /// regardless of whether the function is in SSA form. /// FunctionPass *llvm::createARMCodePrinterPass(raw_ostream &o, - ARMTargetMachine &tm, + ARMBaseTargetMachine &tm, CodeGenOpt::Level OptLevel, bool verbose) { return new ARMAsmPrinter(o, tm, tm.getTargetAsmInfo(), OptLevel, verbose); @@ -1167,13 +1146,10 @@ FunctionPass *llvm::createARMCodePrinterPass(raw_ostream &o, namespace { static struct Register { Register() { - ARMTargetMachine::registerAsmPrinter(createARMCodePrinterPass); + ARMBaseTargetMachine::registerAsmPrinter(createARMCodePrinterPass); } } Registrator; } -// Force static initialization when called from -// llvm/InitializeAllAsmPrinters.h -namespace llvm { - void InitializeARMAsmPrinter() { } -} +// Force static initialization. +extern "C" void LLVMInitializeARMAsmPrinter() { } |