PPCCodeEmitter.cpp revision d2ee218b499fcd364aae7da031819b738f009cd1
121e463b2bf864671a87ebe386cb100ef9349a540Nate Begeman//===-- PPCCodeEmitter.cpp - JIT Code Emitter for PowerPC32 -------*- C++ -*-=// 2b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman// 35dfe3a9c3bd9091f9adecc909665d52bdd4edd8cMisha Brukman// The LLVM Compiler Infrastructure 45dfe3a9c3bd9091f9adecc909665d52bdd4edd8cMisha Brukman// 55dfe3a9c3bd9091f9adecc909665d52bdd4edd8cMisha Brukman// This file was developed by the LLVM research group and is distributed under 65dfe3a9c3bd9091f9adecc909665d52bdd4edd8cMisha Brukman// the University of Illinois Open Source License. See LICENSE.TXT for details. 7b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman// 85dfe3a9c3bd9091f9adecc909665d52bdd4edd8cMisha Brukman//===----------------------------------------------------------------------===// 9b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman// 10d37faba5b485eefe94e36e0f88da899b8fec42e5Misha Brukman// This file defines the PowerPC 32-bit CodeEmitter and associated machinery to 11d37faba5b485eefe94e36e0f88da899b8fec42e5Misha Brukman// JIT-compile bytecode to native PowerPC. 125dfe3a9c3bd9091f9adecc909665d52bdd4edd8cMisha Brukman// 135dfe3a9c3bd9091f9adecc909665d52bdd4edd8cMisha Brukman//===----------------------------------------------------------------------===// 145dfe3a9c3bd9091f9adecc909665d52bdd4edd8cMisha Brukman 1516e71f2f70811c69c56052dd146324fe20e31db5Chris Lattner#include "PPCTargetMachine.h" 1616e71f2f70811c69c56052dd146324fe20e31db5Chris Lattner#include "PPCRelocations.h" 172668959b8879097db368aec7d76c455260abc75bChris Lattner#include "PPC.h" 183070e2ff790e106f5969f503487db5e4b8639ce4Misha Brukman#include "llvm/Module.h" 19de123822e5cc9a7d09b12166439cfd35a6c9ed62Chris Lattner#include "llvm/PassManager.h" 20b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman#include "llvm/CodeGen/MachineCodeEmitter.h" 21b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman#include "llvm/CodeGen/MachineFunctionPass.h" 22d4b4a99587a0856473b9334455f6cebcb4fe2583Misha Brukman#include "llvm/CodeGen/MachineInstrBuilder.h" 23b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman#include "llvm/CodeGen/Passes.h" 24551ccae044b0ff658fe629dd67edd5ffe75d10e8Reid Spencer#include "llvm/Support/Debug.h" 25d2ee218b499fcd364aae7da031819b738f009cd1Evan Cheng#include "llvm/Target/TargetOptions.h" 2686a5484079abc8a20f24066aaf3f5efcccebb673Chris Lattner#include <iostream> 27eea9b134fcd97aa6c11277864fecf2d30640d27fChris Lattnerusing namespace llvm; 285dfe3a9c3bd9091f9adecc909665d52bdd4edd8cMisha Brukman 29b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukmannamespace { 304c7b43b43fdf943c7298718e15ab5d6dfe345be7Chris Lattner class PPCCodeEmitter : public MachineFunctionPass { 31b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman TargetMachine &TM; 32b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman MachineCodeEmitter &MCE; 33b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman 343070e2ff790e106f5969f503487db5e4b8639ce4Misha Brukman // Tracks which instruction references which BasicBlock 35b752a97ca41de789434fa792b6de01f6c04fe13eChris Lattner std::vector<std::pair<MachineBasicBlock*, unsigned*> > BBRefs; 363070e2ff790e106f5969f503487db5e4b8639ce4Misha Brukman // Tracks where each BasicBlock starts 37b752a97ca41de789434fa792b6de01f6c04fe13eChris Lattner std::map<MachineBasicBlock*, long> BBLocations; 383070e2ff790e106f5969f503487db5e4b8639ce4Misha Brukman 393070e2ff790e106f5969f503487db5e4b8639ce4Misha Brukman /// getMachineOpValue - evaluates the MachineOperand of a given MachineInstr 403070e2ff790e106f5969f503487db5e4b8639ce4Misha Brukman /// 41e94c517bb52095f1ad070bb029617d532af405b8Chris Lattner int getMachineOpValue(MachineInstr &MI, MachineOperand &MO); 423070e2ff790e106f5969f503487db5e4b8639ce4Misha Brukman 43b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman public: 444c7b43b43fdf943c7298718e15ab5d6dfe345be7Chris Lattner PPCCodeEmitter(TargetMachine &T, MachineCodeEmitter &M) 45b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman : TM(T), MCE(M) {} 46b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman 47b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman const char *getPassName() const { return "PowerPC Machine Code Emitter"; } 48b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman 49b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman /// runOnMachineFunction - emits the given MachineFunction to memory 50b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman /// 51b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman bool runOnMachineFunction(MachineFunction &MF); 52b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman 53b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman /// emitBasicBlock - emits the given MachineBasicBlock to memory 54b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman /// 55b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman void emitBasicBlock(MachineBasicBlock &MBB); 56b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman 57b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman /// emitWord - write a 32-bit word to memory at the current PC 58b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman /// 59b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman void emitWord(unsigned w) { MCE.emitWord(w); } 60b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman 61d37faba5b485eefe94e36e0f88da899b8fec42e5Misha Brukman /// getValueBit - return the particular bit of Val 62d37faba5b485eefe94e36e0f88da899b8fec42e5Misha Brukman /// 63d37faba5b485eefe94e36e0f88da899b8fec42e5Misha Brukman unsigned getValueBit(int64_t Val, unsigned bit) { return (Val >> bit) & 1; } 64b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman 653070e2ff790e106f5969f503487db5e4b8639ce4Misha Brukman /// getBinaryCodeForInstr - This function, generated by the 663070e2ff790e106f5969f503487db5e4b8639ce4Misha Brukman /// CodeEmitterGenerator using TableGen, produces the binary encoding for 673070e2ff790e106f5969f503487db5e4b8639ce4Misha Brukman /// machine instructions. 68b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman /// 69d37faba5b485eefe94e36e0f88da899b8fec42e5Misha Brukman unsigned getBinaryCodeForInstr(MachineInstr &MI); 70b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman }; 71b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman} 72b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman 735dfe3a9c3bd9091f9adecc909665d52bdd4edd8cMisha Brukman/// addPassesToEmitMachineCode - Add passes to the specified pass manager to get 745dfe3a9c3bd9091f9adecc909665d52bdd4edd8cMisha Brukman/// machine code emitted. This uses a MachineCodeEmitter object to handle 755dfe3a9c3bd9091f9adecc909665d52bdd4edd8cMisha Brukman/// actually outputting the machine code and resolving things like the address 765dfe3a9c3bd9091f9adecc909665d52bdd4edd8cMisha Brukman/// of functions. This method should returns true if machine code emission is 775dfe3a9c3bd9091f9adecc909665d52bdd4edd8cMisha Brukman/// not supported. 785dfe3a9c3bd9091f9adecc909665d52bdd4edd8cMisha Brukman/// 7921e463b2bf864671a87ebe386cb100ef9349a540Nate Begemanbool PPCTargetMachine::addPassesToEmitMachineCode(FunctionPassManager &PM, 8021e463b2bf864671a87ebe386cb100ef9349a540Nate Begeman MachineCodeEmitter &MCE) { 81b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman // Machine code emitter pass for PowerPC 824c7b43b43fdf943c7298718e15ab5d6dfe345be7Chris Lattner PM.add(new PPCCodeEmitter(*this, MCE)); 83d37faba5b485eefe94e36e0f88da899b8fec42e5Misha Brukman // Delete machine code for this function after emitting it 84b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman PM.add(createMachineCodeDeleter()); 85c982cfad875f64284ae0fb2f822b0867657171ebMisha Brukman return false; 86b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman} 87b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman 884c7b43b43fdf943c7298718e15ab5d6dfe345be7Chris Lattnerbool PPCCodeEmitter::runOnMachineFunction(MachineFunction &MF) { 89b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman MCE.startFunction(MF); 90b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman MCE.emitConstantPool(MF.getConstantPool()); 913070e2ff790e106f5969f503487db5e4b8639ce4Misha Brukman for (MachineFunction::iterator BB = MF.begin(), E = MF.end(); BB != E; ++BB) 923070e2ff790e106f5969f503487db5e4b8639ce4Misha Brukman emitBasicBlock(*BB); 93b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman MCE.finishFunction(MF); 943070e2ff790e106f5969f503487db5e4b8639ce4Misha Brukman 953070e2ff790e106f5969f503487db5e4b8639ce4Misha Brukman // Resolve branches to BasicBlocks for the entire function 963070e2ff790e106f5969f503487db5e4b8639ce4Misha Brukman for (unsigned i = 0, e = BBRefs.size(); i != e; ++i) { 97e94c517bb52095f1ad070bb029617d532af405b8Chris Lattner intptr_t Location = BBLocations[BBRefs[i].first]; 988599d385a2f1fbafaaead903ea5be5a9b33a6509Chris Lattner unsigned *Ref = BBRefs[i].second; 99e94c517bb52095f1ad070bb029617d532af405b8Chris Lattner DEBUG(std::cerr << "Fixup @ " << (void*)Ref << " to " << (void*)Location 1008599d385a2f1fbafaaead903ea5be5a9b33a6509Chris Lattner << "\n"); 1018599d385a2f1fbafaaead903ea5be5a9b33a6509Chris Lattner unsigned Instr = *Ref; 1028599d385a2f1fbafaaead903ea5be5a9b33a6509Chris Lattner intptr_t BranchTargetDisp = (Location - (intptr_t)Ref) >> 2; 103b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman 1048599d385a2f1fbafaaead903ea5be5a9b33a6509Chris Lattner switch (Instr >> 26) { 1058599d385a2f1fbafaaead903ea5be5a9b33a6509Chris Lattner default: assert(0 && "Unknown branch user!"); 1068599d385a2f1fbafaaead903ea5be5a9b33a6509Chris Lattner case 18: // This is B or BL 1078599d385a2f1fbafaaead903ea5be5a9b33a6509Chris Lattner *Ref |= (BranchTargetDisp & ((1 << 24)-1)) << 2; 1088599d385a2f1fbafaaead903ea5be5a9b33a6509Chris Lattner break; 1098599d385a2f1fbafaaead903ea5be5a9b33a6509Chris Lattner case 16: // This is BLT,BLE,BEQ,BGE,BGT,BNE, or other bcx instruction 1108599d385a2f1fbafaaead903ea5be5a9b33a6509Chris Lattner *Ref |= (BranchTargetDisp & ((1 << 14)-1)) << 2; 1118599d385a2f1fbafaaead903ea5be5a9b33a6509Chris Lattner break; 1123070e2ff790e106f5969f503487db5e4b8639ce4Misha Brukman } 1133070e2ff790e106f5969f503487db5e4b8639ce4Misha Brukman } 1143070e2ff790e106f5969f503487db5e4b8639ce4Misha Brukman BBRefs.clear(); 1153070e2ff790e106f5969f503487db5e4b8639ce4Misha Brukman BBLocations.clear(); 1163070e2ff790e106f5969f503487db5e4b8639ce4Misha Brukman 117b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman return false; 118b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman} 119b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman 1204c7b43b43fdf943c7298718e15ab5d6dfe345be7Chris Lattnervoid PPCCodeEmitter::emitBasicBlock(MachineBasicBlock &MBB) { 1212497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman assert(!PICEnabled && "CodeEmitter does not support PIC!"); 122b752a97ca41de789434fa792b6de01f6c04fe13eChris Lattner BBLocations[&MBB] = MCE.getCurrentPCValue(); 123a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman for (MachineBasicBlock::iterator I = MBB.begin(), E = MBB.end(); I != E; ++I){ 124a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman MachineInstr &MI = *I; 125a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman unsigned Opcode = MI.getOpcode(); 126e94c517bb52095f1ad070bb029617d532af405b8Chris Lattner switch (MI.getOpcode()) { 127e94c517bb52095f1ad070bb029617d532af405b8Chris Lattner default: 128d4b4a99587a0856473b9334455f6cebcb4fe2583Misha Brukman emitWord(getBinaryCodeForInstr(*I)); 129e94c517bb52095f1ad070bb029617d532af405b8Chris Lattner break; 1302b54400f085391a247dd2c3fffc9f36f7b2dc867Chris Lattner case PPC::IMPLICIT_DEF_GPR: 131919c032fa4511468aadc6f50d6ed9c50890710b3Chris Lattner case PPC::IMPLICIT_DEF_F8: 132919c032fa4511468aadc6f50d6ed9c50890710b3Chris Lattner case PPC::IMPLICIT_DEF_F4: 133e94c517bb52095f1ad070bb029617d532af405b8Chris Lattner break; // pseudo opcode, no side effects 134e94c517bb52095f1ad070bb029617d532af405b8Chris Lattner case PPC::MovePCtoLR: 1352497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman assert(0 && "CodeEmitter does not support MovePCtoLR instruction"); 136e94c517bb52095f1ad070bb029617d532af405b8Chris Lattner break; 137e94c517bb52095f1ad070bb029617d532af405b8Chris Lattner } 138a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman } 139b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman} 140b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman 141a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukmanstatic unsigned enumRegToMachineReg(unsigned enumReg) { 142a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman switch (enumReg) { 143b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman case PPC::R0 : case PPC::F0 : case PPC::CR0: return 0; 144b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman case PPC::R1 : case PPC::F1 : case PPC::CR1: return 1; 1459ba12359e3b4ca5bce5469d86ae38eb1237752eeChris Lattner case PPC::R2 : case PPC::F2 : case PPC::CR2: return 2; 146b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman case PPC::R3 : case PPC::F3 : case PPC::CR3: return 3; 147b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman case PPC::R4 : case PPC::F4 : case PPC::CR4: return 4; 1489ba12359e3b4ca5bce5469d86ae38eb1237752eeChris Lattner case PPC::R5 : case PPC::F5 : case PPC::CR5: return 5; 149b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman case PPC::R6 : case PPC::F6 : case PPC::CR6: return 6; 150b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman case PPC::R7 : case PPC::F7 : case PPC::CR7: return 7; 151a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman case PPC::R8 : case PPC::F8 : return 8; 152b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman case PPC::R9 : case PPC::F9 : return 9; 153b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman case PPC::R10: case PPC::F10: return 10; 154a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman case PPC::R11: case PPC::F11: return 11; 155b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman case PPC::R12: case PPC::F12: return 12; 156b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman case PPC::R13: case PPC::F13: return 13; 157a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman case PPC::R14: case PPC::F14: return 14; 158b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman case PPC::R15: case PPC::F15: return 15; 159b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman case PPC::R16: case PPC::F16: return 16; 160a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman case PPC::R17: case PPC::F17: return 17; 161b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman case PPC::R18: case PPC::F18: return 18; 162b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman case PPC::R19: case PPC::F19: return 19; 163a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman case PPC::R20: case PPC::F20: return 20; 164a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman case PPC::R21: case PPC::F21: return 21; 165b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman case PPC::R22: case PPC::F22: return 22; 166b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman case PPC::R23: case PPC::F23: return 23; 167a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman case PPC::R24: case PPC::F24: return 24; 168b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman case PPC::R25: case PPC::F25: return 25; 169b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman case PPC::R26: case PPC::F26: return 26; 170a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman case PPC::R27: case PPC::F27: return 27; 171b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman case PPC::R28: case PPC::F28: return 28; 172b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman case PPC::R29: case PPC::F29: return 29; 173a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman case PPC::R30: case PPC::F30: return 30; 174a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman case PPC::R31: case PPC::F31: return 31; 175a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman default: 176a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman std::cerr << "Unhandled reg in enumRegToRealReg!\n"; 177a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman abort(); 178a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman } 179a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman} 180a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman 1814c7b43b43fdf943c7298718e15ab5d6dfe345be7Chris Lattnerint PPCCodeEmitter::getMachineOpValue(MachineInstr &MI, MachineOperand &MO) { 182b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman 183e94c517bb52095f1ad070bb029617d532af405b8Chris Lattner int rv = 0; // Return value; defaults to 0 for unhandled cases 184c982cfad875f64284ae0fb2f822b0867657171ebMisha Brukman // or things that get fixed up later by the JIT. 1853070e2ff790e106f5969f503487db5e4b8639ce4Misha Brukman if (MO.isRegister()) { 186a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman rv = enumRegToMachineReg(MO.getReg()); 187f577c6122f8b51c4e4889f1e1c647ae210c501b8Chris Lattner 188adeb43ddf4eac9e75b7c8e79fa832f72922a2926Nate Begeman // Special encoding for MTCRF and MFOCRF, which uses a bit mask for the 189f577c6122f8b51c4e4889f1e1c647ae210c501b8Chris Lattner // register, not the register number directly. 190adeb43ddf4eac9e75b7c8e79fa832f72922a2926Nate Begeman if ((MI.getOpcode() == PPC::MTCRF || MI.getOpcode() == PPC::MFOCRF) && 191f577c6122f8b51c4e4889f1e1c647ae210c501b8Chris Lattner (MO.getReg() >= PPC::CR0 && MO.getReg() <= PPC::CR7)) { 192f577c6122f8b51c4e4889f1e1c647ae210c501b8Chris Lattner rv = 0x80 >> rv; 193f577c6122f8b51c4e4889f1e1c647ae210c501b8Chris Lattner } 194c982cfad875f64284ae0fb2f822b0867657171ebMisha Brukman } else if (MO.isImmediate()) { 195c982cfad875f64284ae0fb2f822b0867657171ebMisha Brukman rv = MO.getImmedValue(); 196477d1de9b2c77455192b6e67dd9496851f4ed8d0Chris Lattner } else if (MO.isGlobalAddress() || MO.isExternalSymbol()) { 197477d1de9b2c77455192b6e67dd9496851f4ed8d0Chris Lattner bool isExternal = MO.isExternalSymbol() || 198477d1de9b2c77455192b6e67dd9496851f4ed8d0Chris Lattner MO.getGlobal()->hasWeakLinkage() || 1995fe0e28650dd49f290fce2b80c0052fbc12d2385Chris Lattner MO.getGlobal()->hasLinkOnceLinkage() || 20037dd6f1b79bd888cb88ced7e5ce5a8ebc7aa44e2Chris Lattner (MO.getGlobal()->isExternal() && 20137dd6f1b79bd888cb88ced7e5ce5a8ebc7aa44e2Chris Lattner !MO.getGlobal()->hasNotBeenReadFromBytecode()); 202d7fa35c6d2acc2fe95346b1b9eaa3c0a30342c85Chris Lattner unsigned Reloc = 0; 203422b0cee7a32636303398d8788f98a59bf15381cNate Begeman if (MI.getOpcode() == PPC::BL) 204e94c517bb52095f1ad070bb029617d532af405b8Chris Lattner Reloc = PPC::reloc_pcrel_bx; 2055efb75daed48edfeb03ba62f3f0afe81b86f5d7fChris Lattner else { 2062497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman switch (MI.getOpcode()) { 2072497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman default: MI.dump(); assert(0 && "Unknown instruction for relocation!"); 2082497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman case PPC::LIS: 209477d1de9b2c77455192b6e67dd9496851f4ed8d0Chris Lattner if (isExternal) 2105efb75daed48edfeb03ba62f3f0afe81b86f5d7fChris Lattner Reloc = PPC::reloc_absolute_ptr_high; // Pointer to stub 21100b16889ab461b7ecef1c91ade101186b7f1fce2Jeff Cohen else 2125efb75daed48edfeb03ba62f3f0afe81b86f5d7fChris Lattner Reloc = PPC::reloc_absolute_high; // Pointer to symbol 2132497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman break; 2142497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman case PPC::LA: 215477d1de9b2c77455192b6e67dd9496851f4ed8d0Chris Lattner assert(!isExternal && "Something in the ISEL changed\n"); 2165efb75daed48edfeb03ba62f3f0afe81b86f5d7fChris Lattner Reloc = PPC::reloc_absolute_low; 2172497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman break; 2182497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman case PPC::LBZ: 2192497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman case PPC::LHA: 2202497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman case PPC::LHZ: 2212497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman case PPC::LWZ: 2222497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman case PPC::LFS: 2232497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman case PPC::LFD: 2242497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman case PPC::STB: 2252497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman case PPC::STH: 2262497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman case PPC::STW: 2272497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman case PPC::STFS: 2282497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman case PPC::STFD: 2292497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman if (isExternal) 2302497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman Reloc = PPC::reloc_absolute_ptr_low; 23100b16889ab461b7ecef1c91ade101186b7f1fce2Jeff Cohen else 2322497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman Reloc = PPC::reloc_absolute_low; 2332497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman break; 2345efb75daed48edfeb03ba62f3f0afe81b86f5d7fChris Lattner } 235e94c517bb52095f1ad070bb029617d532af405b8Chris Lattner } 236477d1de9b2c77455192b6e67dd9496851f4ed8d0Chris Lattner if (MO.isGlobalAddress()) 237477d1de9b2c77455192b6e67dd9496851f4ed8d0Chris Lattner MCE.addRelocation(MachineRelocation(MCE.getCurrentPCOffset(), 2382497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman Reloc, MO.getGlobal(), 0)); 239477d1de9b2c77455192b6e67dd9496851f4ed8d0Chris Lattner else 240477d1de9b2c77455192b6e67dd9496851f4ed8d0Chris Lattner MCE.addRelocation(MachineRelocation(MCE.getCurrentPCOffset(), 2412497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman Reloc, MO.getSymbolName(), 0)); 242c982cfad875f64284ae0fb2f822b0867657171ebMisha Brukman } else if (MO.isMachineBasicBlock()) { 2433070e2ff790e106f5969f503487db5e4b8639ce4Misha Brukman unsigned* CurrPC = (unsigned*)(intptr_t)MCE.getCurrentPCValue(); 244b752a97ca41de789434fa792b6de01f6c04fe13eChris Lattner BBRefs.push_back(std::make_pair(MO.getMachineBasicBlock(), CurrPC)); 245c982cfad875f64284ae0fb2f822b0867657171ebMisha Brukman } else if (MO.isConstantPoolIndex()) { 2463070e2ff790e106f5969f503487db5e4b8639ce4Misha Brukman unsigned index = MO.getConstantPoolIndex(); 247b9f26da5dd6c404e0a6eabcb60fb3c61ac0ee173Chris Lattner unsigned Opcode = MI.getOpcode(); 2482497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman rv = MCE.getConstantPoolEntryAddress(index); 249e54645a6fb9887b3eccf2eade24531165f84b0edChris Lattner if (Opcode == PPC::LIS || Opcode == PPC::ADDIS) { 2502497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman // lis wants hi16(addr) 251b9f26da5dd6c404e0a6eabcb60fb3c61ac0ee173Chris Lattner if ((short)rv < 0) rv += 1 << 16; 252e94c517bb52095f1ad070bb029617d532af405b8Chris Lattner rv >>= 16; 253a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman } else if (Opcode == PPC::LWZ || Opcode == PPC::LA || 254e54645a6fb9887b3eccf2eade24531165f84b0edChris Lattner Opcode == PPC::LI || 255a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman Opcode == PPC::LFS || Opcode == PPC::LFD) { 2562497e6391f8df05926fe17b5cf08dad61c4797d2Nate Begeman // These load opcodes want lo16(addr) 257e94c517bb52095f1ad070bb029617d532af405b8Chris Lattner rv &= 0xffff; 258b9f26da5dd6c404e0a6eabcb60fb3c61ac0ee173Chris Lattner } else { 259b9f26da5dd6c404e0a6eabcb60fb3c61ac0ee173Chris Lattner assert(0 && "Unknown constant pool using instruction!"); 260a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman } 261b9f26da5dd6c404e0a6eabcb60fb3c61ac0ee173Chris Lattner } else { 262b9f26da5dd6c404e0a6eabcb60fb3c61ac0ee173Chris Lattner std::cerr << "ERROR: Unknown type of MachineOperand: " << MO << "\n"; 263b9f26da5dd6c404e0a6eabcb60fb3c61ac0ee173Chris Lattner abort(); 264a4df350ba1193b2f0421d06a135beb21afb80035Misha Brukman } 265b9f26da5dd6c404e0a6eabcb60fb3c61ac0ee173Chris Lattner 266c982cfad875f64284ae0fb2f822b0867657171ebMisha Brukman return rv; 2675dfe3a9c3bd9091f9adecc909665d52bdd4edd8cMisha Brukman} 2685dfe3a9c3bd9091f9adecc909665d52bdd4edd8cMisha Brukman 2694c7b43b43fdf943c7298718e15ab5d6dfe345be7Chris Lattner#include "PPCGenCodeEmitter.inc" 270b05daff7faf694a8d18f00ef00132384c8207cd4Misha Brukman 271