#include "generator.h" GravityTargetArch gravityNewTargetArch(const char* name) { GravityTargetArch targetArch = malloc(sizeof(struct GravityOpaqueTargetArch)); if (targetArch == NULL) return targetArch; StringBuffer* outputBuff = malloc(sizeof(StringBuffer)); if (outputBuff == NULL) { free(targetArch); return NULL; } initStringBuff(outputBuff); targetArch->outputBuffer = outputBuff; targetArch->name = strdup(name); targetArch->vars = NULL; return targetArch; } void gravityTargetEmitInst(GravityTargetArch arch, GravityInstruction inst) { arch->emitInst(arch, inst); switch (inst.opcode) { case GravityOpcodeIntConst: arch->emitIntConst(arch, inst.operands[0]); break; case GravityOpcodeRet: arch->emitRet(arch, inst.operands[0]); break; case GravityOpcodeAlloc: arch->emitAlloc(arch, inst.operands[0]->type->typeData, inst.result); break; case GravityOpcodeStore: arch->emitStore(arch, inst.operands[0], inst.operands[1]); break; case GravityOpcodeLoad: arch->emitLoad(arch, inst.operands[0], inst.result); break; default: assert(false); } } void gravityTargetEmitBlock(GravityTargetArch arch, GravityBlock block) { arch->emitBlock(arch, block); for (unsigned int i = 0; i < block->instructions.count; i++) { gravityTargetEmitInst(arch, *get(block->instructions, i)); } } void gravityTargetEmitFunction(GravityTargetArch arch, GravityFunction function) { arch->currentFunction = function; arch->emitFunction(arch, function); for (unsigned int i = 0; i < function->blocks.count; i++) { gravityTargetEmitBlock(arch, *get(function->blocks, i)); } } char* gravityTargetEmitModule(GravityTargetArch arch, GravityModule module) { for (unsigned int i = 0; i < module->functions.count; i++) { gravityTargetEmitFunction(arch, *get(module->functions, i)); } return arch->outputBuffer->data; } GravityType gravityResolveInstructionResult(GravityTargetArch arch, GravityInstruction inst) { switch (inst.opcode) { case GravityOpcodeAlloc: { GravityType outType = gravityCreateType(); outType->typeKind = GravityPointerTypeKind; outType->ptrType = inst.operands[0]->type->typeData; return outType; } case GravityOpcodeLoad: { GravityVarSlot* var; HASH_FIND(hh, arch->vars, inst.operands[0], sizeof(void*), var); if (!var) assert(false); return var->type->ptrType; } default: assert(false); } }