Program::~Program() { for (ArrayList::Iterator it = allFuncs.iterator(); !it.end(); it.next()) delete reinterpret_cast<Function *>(it.get()); for (ArrayList::Iterator it = allRValues.iterator(); !it.end(); it.next()) releaseValue(reinterpret_cast<Value *>(it.get())); }
void CodeEmitter::prepareEmission(Program *prog) { for (ArrayList::Iterator fi = prog->allFuncs.iterator(); !fi.end(); fi.next()) { Function *func = reinterpret_cast<Function *>(fi.get()); func->binPos = prog->binSize; prepareEmission(func); // adjust sizes & positions for schedulding info: if (prog->getTarget()->hasSWSched) { uint32_t adjPos = func->binPos; BasicBlock *bb = NULL; for (int i = 0; i < func->bbCount; ++i) { bb = func->bbArray[i]; int32_t adjSize = bb->binSize; if (adjPos % 64) { adjSize -= 64 - adjPos % 64; if (adjSize < 0) adjSize = 0; } adjSize = bb->binSize + sizeToBundlesNVE4(adjSize) * 8; bb->binPos = adjPos; bb->binSize = adjSize; adjPos += adjSize; } if (bb) func->binSize = adjPos - func->binPos; } prog->binSize += func->binSize; } }
bool Program::emitBinary(struct nv50_ir_prog_info *info) { CodeEmitter *emit = target->getCodeEmitter(progType); emit->prepareEmission(this); if (dbgFlags & NV50_IR_DEBUG_BASIC) this->print(); if (!binSize) { code = NULL; return false; } code = reinterpret_cast<uint32_t *>(MALLOC(binSize)); if (!code) return false; emit->setCodeLocation(code, binSize); for (ArrayList::Iterator fi = allFuncs.iterator(); !fi.end(); fi.next()) { Function *fn = reinterpret_cast<Function *>(fi.get()); assert(emit->getCodeSize() == fn->binPos); for (int b = 0; b < fn->bbCount; ++b) for (Instruction *i = fn->bbArray[b]->getEntry(); i; i = i->next) emit->emitInstruction(i); } info->bin.relocData = emit->getRelocInfo(); delete emit; return true; }
Function::~Function() { prog->del(this, id); if (domTree) delete domTree; if (bbArray) delete[] bbArray; for (ArrayList::Iterator it = allInsns.iterator(); !it.end(); it.next()) delete_Instruction(prog, reinterpret_cast<Instruction *>(it.get())); for (ArrayList::Iterator it = allLValues.iterator(); !it.end(); it.next()) delete_Value(prog, reinterpret_cast<LValue *>(it.get())); for (ArrayList::Iterator BBs = allBBlocks.iterator(); !BBs.end(); BBs.next()) delete reinterpret_cast<BasicBlock *>(BBs.get()); }
bool Program::convertToSSA() { for (ArrayList::Iterator fi = allFuncs.iterator(); !fi.end(); fi.next()) { Function *fn = reinterpret_cast<Function *>(fi.get()); if (!fn->convertToSSA()) return false; } return true; }
void CodeEmitter::prepareEmission(Program *prog) { for (ArrayList::Iterator fi = prog->allFuncs.iterator(); !fi.end(); fi.next()) { Function *func = reinterpret_cast<Function *>(fi.get()); func->binPos = prog->binSize; prepareEmission(func); prog->binSize += func->binSize; } }
bool Program::emitBinary(struct nv50_ir_prog_info *info) { CodeEmitter *emit = target->getCodeEmitter(progType); emit->prepareEmission(this); if (dbgFlags & NV50_IR_DEBUG_BASIC) this->print(); if (!binSize) { code = NULL; return false; } code = reinterpret_cast<uint32_t *>(MALLOC(binSize)); if (!code) return false; emit->setCodeLocation(code, binSize); info->bin.instructions = 0; for (ArrayList::Iterator fi = allFuncs.iterator(); !fi.end(); fi.next()) { Function *fn = reinterpret_cast<Function *>(fi.get()); assert(emit->getCodeSize() == fn->binPos); for (int b = 0; b < fn->bbCount; ++b) { for (Instruction *i = fn->bbArray[b]->getEntry(); i; i = i->next) { emit->emitInstruction(i); info->bin.instructions++; if (i->sType == TYPE_F64 || i->dType == TYPE_F64) info->io.fp64 = true; } } } info->bin.relocData = emit->getRelocInfo(); info->bin.interpData = emit->getInterpInfo(); emitSymbolTable(info); // the nvc0 driver will print the binary iself together with the header if ((dbgFlags & NV50_IR_DEBUG_BASIC) && getTarget()->getChipset() < 0xc0) emit->printBinary(); delete emit; return true; }
void Program::emitSymbolTable(struct nv50_ir_prog_info *info) { unsigned int n = 0, nMax = allFuncs.getSize(); info->bin.syms = (struct nv50_ir_prog_symbol *)MALLOC(nMax * sizeof(*info->bin.syms)); for (ArrayList::Iterator fi = allFuncs.iterator(); !fi.end(); fi.next(), ++n) { Function *f = (Function *)fi.get(); assert(n < nMax); info->bin.syms[n].label = f->getLabel(); info->bin.syms[n].offset = f->binPos; } info->bin.numSyms = n; }