blob: e34ace67a372f4e14fa71b9481341607d48737e1 [file] [log] [blame]
Misha Brukmana9f7f6e2003-05-30 20:17:33 +00001//===-- SparcV9CodeEmitter.cpp - --------===//
2//
3//
4//===----------------------------------------------------------------------===//
5
Misha Brukman3de36f52003-05-27 20:07:58 +00006#include "llvm/PassManager.h"
7#include "llvm/CodeGen/MachineCodeEmitter.h"
8#include "llvm/CodeGen/MachineFunctionPass.h"
9#include "llvm/CodeGen/MachineInstr.h"
Misha Brukmana9f7f6e2003-05-30 20:17:33 +000010#include "llvm/Target/TargetMachine.h"
Misha Brukman3de36f52003-05-27 20:07:58 +000011#include "SparcInternals.h"
Misha Brukman0cc640e2003-05-27 21:45:05 +000012#include "SparcV9CodeEmitter.h"
Misha Brukman3de36f52003-05-27 20:07:58 +000013
Misha Brukmana9f7f6e2003-05-30 20:17:33 +000014MachineCodeEmitter * SparcV9CodeEmitter::MCE = 0;
15TargetMachine * SparcV9CodeEmitter::TM = 0;
16
Misha Brukman3de36f52003-05-27 20:07:58 +000017bool UltraSparc::addPassesToEmitMachineCode(PassManager &PM,
18 MachineCodeEmitter &MCE) {
19 //PM.add(new SparcV9CodeEmitter(MCE));
20 //MachineCodeEmitter *M = MachineCodeEmitter::createDebugMachineCodeEmitter();
21 MachineCodeEmitter *M =
Misha Brukman0cc640e2003-05-27 21:45:05 +000022 MachineCodeEmitter::createFilePrinterMachineCodeEmitter(MCE);
Misha Brukmana9f7f6e2003-05-30 20:17:33 +000023 PM.add(new SparcV9CodeEmitter(this, *M));
Misha Brukmandcbe7122003-05-31 06:26:06 +000024 PM.add(createMachineCodeDestructionPass()); // Free stuff no longer needed
Misha Brukman3de36f52003-05-27 20:07:58 +000025 return false;
26}
27
28void SparcV9CodeEmitter::emitConstant(unsigned Val, unsigned Size) {
29 // Output the constant in big endian byte order...
30 unsigned byteVal;
31 for (int i = Size-1; i >= 0; --i) {
32 byteVal = Val >> 8*i;
Misha Brukmana9f7f6e2003-05-30 20:17:33 +000033 MCE->emitByte(byteVal & 255);
34 }
Misha Brukmana9f7f6e2003-05-30 20:17:33 +000035}
36
37unsigned getRealRegNum(unsigned fakeReg, unsigned regClass) {
38 switch (regClass) {
39 case UltraSparcRegInfo::IntRegType: {
40 // Sparc manual, p31
41 static const unsigned IntRegMap[] = {
42 // "o0", "o1", "o2", "o3", "o4", "o5", "o7",
43 8, 9, 10, 11, 12, 13, 15,
44 // "l0", "l1", "l2", "l3", "l4", "l5", "l6", "l7",
45 16, 17, 18, 19, 20, 21, 22, 23,
46 // "i0", "i1", "i2", "i3", "i4", "i5",
47 24, 25, 26, 27, 28, 29,
48 // "i6", "i7",
49 30, 31,
50 // "g0", "g1", "g2", "g3", "g4", "g5", "g6", "g7",
51 0, 1, 2, 3, 4, 5, 6, 7,
52 // "o6"
53 14
54 };
55
56 return IntRegMap[fakeReg];
57 break;
58 }
59 case UltraSparcRegInfo::FPSingleRegType: {
60 return fakeReg;
61 }
62 case UltraSparcRegInfo::FPDoubleRegType: {
63 return fakeReg;
64 }
65 case UltraSparcRegInfo::FloatCCRegType: {
66 return fakeReg;
67
68 }
69 case UltraSparcRegInfo::IntCCRegType: {
70 return fakeReg;
71 }
72 default:
73 assert(0 && "Invalid unified register number in getRegType");
74 return fakeReg;
Misha Brukman3de36f52003-05-27 20:07:58 +000075 }
76}
77
Misha Brukmana9f7f6e2003-05-30 20:17:33 +000078int64_t SparcV9CodeEmitter::getMachineOpValue(MachineInstr &MI,
79 MachineOperand &MO) {
Misha Brukman3de36f52003-05-27 20:07:58 +000080 if (MO.isPhysicalRegister()) {
Misha Brukmana9f7f6e2003-05-30 20:17:33 +000081 // This is necessary because the Sparc doesn't actually lay out registers
82 // in the real fashion -- it skips those that it chooses not to allocate,
83 // i.e. those that are the SP, etc.
84 unsigned fakeReg = MO.getReg(), realReg, regClass, regType;
85 regType = TM->getRegInfo().getRegType(fakeReg);
86 // At least map fakeReg into its class
87 fakeReg = TM->getRegInfo().getClassRegNum(fakeReg, regClass);
88 // Find the real register number for use in an instruction
89 realReg = getRealRegNum(fakeReg, regClass);
90 std::cerr << "Reg[" << fakeReg << "] = " << realReg << "\n";
91 return realReg;
Misha Brukman3de36f52003-05-27 20:07:58 +000092 } else if (MO.isImmediate()) {
93 return MO.getImmedValue();
94 } else if (MO.isPCRelativeDisp()) {
Misha Brukmana9f7f6e2003-05-30 20:17:33 +000095 std::cerr << "Saving reference to BB (PCRelDisp)\n";
96 MCE->saveBBreference((BasicBlock*)MO.getVRegValue(), MI);
97 return 0;
98 } else if (MO.isMachineBasicBlock()) {
99 std::cerr << "Saving reference to BB (MBB)\n";
100 MCE->saveBBreference(MO.getMachineBasicBlock()->getBasicBlock(), MI);
101 return 0;
102 } else if (MO.isFrameIndex()) {
103 std::cerr << "ERROR: Frame index unhandled.\n";
104 return 0;
105 } else if (MO.isConstantPoolIndex()) {
106 std::cerr << "ERROR: Constant Pool index unhandled.\n";
107 return 0;
108 } else if (MO.isGlobalAddress()) {
109 std::cerr << "ERROR: Global addr unhandled.\n";
110 return 0;
111 } else if (MO.isExternalSymbol()) {
112 std::cerr << "ERROR: External symbol unhandled.\n";
Misha Brukman3de36f52003-05-27 20:07:58 +0000113 return 0;
114 } else {
Misha Brukmana9f7f6e2003-05-30 20:17:33 +0000115 std::cerr << "ERROR: Unknown type of MachineOperand: " << MO << "\n";
116 //abort();
Misha Brukman3de36f52003-05-27 20:07:58 +0000117 return 0;
118 }
119}
120
121unsigned SparcV9CodeEmitter::getValueBit(int64_t Val, unsigned bit) {
122 Val >>= bit;
123 return (Val & 1);
124}
125
126
127bool SparcV9CodeEmitter::runOnMachineFunction(MachineFunction &MF) {
Misha Brukmana9f7f6e2003-05-30 20:17:33 +0000128 MCE->startFunction(MF);
129 MCE->emitConstantPool(MF.getConstantPool());
Misha Brukman3de36f52003-05-27 20:07:58 +0000130 for (MachineFunction::iterator I = MF.begin(), E = MF.end(); I != E; ++I)
131 emitBasicBlock(*I);
Misha Brukmana9f7f6e2003-05-30 20:17:33 +0000132 MCE->finishFunction(MF);
Misha Brukman3de36f52003-05-27 20:07:58 +0000133 return false;
134}
135
136void SparcV9CodeEmitter::emitBasicBlock(MachineBasicBlock &MBB) {
Misha Brukman0d603452003-05-27 22:41:44 +0000137 currBB = MBB.getBasicBlock();
Misha Brukmana9f7f6e2003-05-30 20:17:33 +0000138 MCE->startBasicBlock(MBB);
Misha Brukman3de36f52003-05-27 20:07:58 +0000139 for (MachineBasicBlock::iterator I = MBB.begin(), E = MBB.end(); I != E; ++I)
140 emitInstruction(**I);
141}
142
143void SparcV9CodeEmitter::emitInstruction(MachineInstr &MI) {
144 emitConstant(getBinaryCodeForInstr(MI), 4);
145}
146
147#include "SparcV9CodeEmitter.inc"