#ifndef AMALGAM_SSA_H #define AMALGAM_SSA_H #include "../std/buffer.h" #include "../std/hash_map.h" #include "../std/defs.h" #include "../defs.h" #include typedef enum { SSA_ASSIGN_INTER, SSA_ASSIGN_STRING, SSA_ASSIGN_REG, SSA_ADD, SSA_SUB, SSA_IMUL, SSA_MUL, SSA_IDIV, SSA_DIV, SSA_EQUALS, SSA_FUNC_START, SSA_FUNC_END, SSA_PUSH, SSA_CALL, SSA_JUMP_ZERO, SSA_JUMP } SsaInstruction; typedef enum { SSA_NUMBER_TYPE_INTEGER, SSA_NUMBER_TYPE_FLOAT } SsaNumberType; typedef struct { union { i64 integer; f64 floating; } value; SsaNumberType type; } SsaNumber; typedef i16 JumpOffset; typedef u16 SsaRegister; typedef u16 SsaIntermediateIndex; typedef u16 SsaStringIndex; typedef u16 SsaFuncIndex; typedef struct { Buffer/*instruction data*/ instructions; HashMap/**/ intermediates_map; Buffer/*SsaNumber*/ intermediates; HashMap/**/ strings_map; Buffer/*BufferView*/ strings; SsaIntermediateIndex intermediate_counter; SsaStringIndex string_counter; SsaRegister reg_counter; SsaFuncIndex func_counter; } Ssa; typedef struct { SsaRegister lhs; u16 rhs; } SsaInsForm1; typedef struct { SsaRegister result; SsaRegister lhs; SsaRegister rhs; } SsaInsForm2; typedef struct { SsaFuncIndex func_index; u16 num_registers; } SsaInsFuncStart; typedef struct { SsaRegister result; FunctionDecl *func_decl; } SsaInsFuncCall; typedef struct { SsaRegister condition_reg; JumpOffset jump_offset; } SsaInsJumpZero; typedef struct { JumpOffset jump_offset; } SsaInsJump; /* None of these functions are thread-safe */ SsaNumber create_ssa_integer(i64 value); SsaNumber create_ssa_float(f64 value); SsaNumber ssa_get_intermediate(Ssa *self, SsaIntermediateIndex index); BufferView ssa_get_string(Ssa *self, SsaStringIndex index); CHECK_RESULT int ssa_init(Ssa *self, ArenaAllocator *allocator); typedef struct { jmp_buf env; Ssa *ssa; amal_compiler *compiler; } SsaCompilerContext; /* longjump to context->env on failure */ void scope_generate_ssa(Scope *self, SsaCompilerContext *context); #endif