symtabInit

decompiled_code:
__int64 symtabInit()
{
const char **v0; // rax
const char **v1; // rax
const char **v2; // rax
const char **v3; // rax
const char **v4; // rax
const char **v5; // rax
const char **v6; // rax
const char **v7; // rax
const char **v8; // rax
const char **v9; // rax
const char **v10; // rax
const char **v11; // rax
__int64 result; // rax

typeinit();
v0 = (const char **)typeIdCreate(int_type, (__int64)"integer");
addIdToTable_noAddrMove(v0, (const char ***)scope);
v1 = (const char **)typeIdCreate(int_type, (__int64)"INTEGER");
addIdToTable_noAddrMove(v1, (const char ***)scope);
v2 = (const char **)typeIdCreate(char_type, (__int64)"char");
addIdToTable_noAddrMove(v2, (const char ***)scope);
v3 = (const char **)typeIdCreate(char_type, (__int64)"CHAR");
addIdToTable_noAddrMove(v3, (const char ***)scope);
v4 = (const char **)typeIdCreate(bool_type, (__int64)"boolean");
addIdToTable_noAddrMove(v4, (const char ***)scope);
v5 = (const char **)typeIdCreate(bool_type, (__int64)"BOOLEAN");
addIdToTable_noAddrMove(v5, (const char ***)scope);
v6 = (const char **)typeIdCreate(str_type, (__int64)"string");
addIdToTable_noAddrMove(v6, (const char ***)scope);
v7 = (const char **)typeIdCreate(str_type, (__int64)"STRING");
addIdToTable_noAddrMove(v7, (const char ***)scope);
true_expr = newBoolExpr(1LL);
false_expr = newBoolExpr(0LL);
v8 = (const char **)mkBoolId((__int64)"true", true_expr);
addIdToTable_noAddrMove(v8, (const char ***)scope);
v9 = (const char **)mkBoolId((__int64)"TRUE", true_expr);
addIdToTable_noAddrMove(v9, (const char ***)scope);
v10 = (const char **)mkBoolId((__int64)"false", false_expr);
addIdToTable_noAddrMove(v10, (const char ***)scope);
v11 = (const char **)mkBoolId((__int64)"FALSE", false_expr);
addIdToTable_noAddrMove(v11, (const char ***)scope);
result = newNumExpr(1LL);
one_expr = result;
return result;
}

canonical_decompiled_code:
__int64 func6()
{
const char **v0; // rax
const char **v1; // rax
const char **v2; // rax
const char **v3; // rax
const char **v4; // rax
const char **v5; // rax
const char **v6; // rax
const char **v7; // rax
const char **v8; // rax
const char **v9; // rax
const char **v10; // rax
const char **v11; // rax
__int64 result; // rax

func0();
v0 = (const char **)typeIdCreate(int_type, (__int64)"integer");
func5(v0, (const char ***)scope);
v1 = (const char **)typeIdCreate(int_type, (__int64)"INTEGER");
func5(v1, (const char ***)scope);
v2 = (const char **)typeIdCreate(char_type, (__int64)"char");
func5(v2, (const char ***)scope);
v3 = (const char **)typeIdCreate(char_type, (__int64)"CHAR");
func5(v3, (const char ***)scope);
v4 = (const char **)typeIdCreate(bool_type, (__int64)"boolean");
func5(v4, (const char ***)scope);
v5 = (const char **)typeIdCreate(bool_type, (__int64)"BOOLEAN");
func5(v5, (const char ***)scope);
v6 = (const char **)typeIdCreate(str_type, (__int64)"string");
func5(v6, (const char ***)scope);
v7 = (const char **)typeIdCreate(str_type, (__int64)"STRING");
func5(v7, (const char ***)scope);
true_expr = newBoolExpr(1LL);
false_expr = newBoolExpr(0LL);
v8 = (const char **)mkBoolId((__int64)"true", true_expr);
func5(v8, (const char ***)scope);
v9 = (const char **)mkBoolId((__int64)"TRUE", true_expr);
func5(v9, (const char ***)scope);
v10 = (const char **)mkBoolId((__int64)"false", false_expr);
func5(v10, (const char ***)scope);
v11 = (const char **)mkBoolId((__int64)"FALSE", false_expr);
func5(v11, (const char ***)scope);
result = newNumExpr(1LL);
one_expr = result;
return result;
}

original_code:
void symtabInit(void) {
    typeinit();
    ID** s = scope;
    addIdToTable_noAddrMove(typeIdCreate(int_type, "integer"), s);
    addIdToTable_noAddrMove(typeIdCreate(int_type, "INTEGER"), s);
    addIdToTable_noAddrMove(typeIdCreate(char_type, "char"), s);
    addIdToTable_noAddrMove(typeIdCreate(char_type, "CHAR"), s);
    addIdToTable_noAddrMove(typeIdCreate(bool_type, "boolean"), s);
    addIdToTable_noAddrMove(typeIdCreate(bool_type, "BOOLEAN"), s);
    addIdToTable_noAddrMove(typeIdCreate(str_type, "string"), s);
    addIdToTable_noAddrMove(typeIdCreate(str_type, "STRING"), s);
    true_expr = newBoolExpr(1);
    false_expr = newBoolExpr(0);
    ID* boolid = mkBoolId("true", true_expr);
    addIdToTable_noAddrMove(boolid, s);
    boolid = mkBoolId("TRUE", true_expr);
    addIdToTable_noAddrMove(boolid, s);
    boolid = mkBoolId("false", false_expr);
    addIdToTable_noAddrMove(boolid, s);
    boolid = mkBoolId("FALSE", false_expr);
    addIdToTable_noAddrMove(boolid, s);
    one_expr = newNumExpr(1);
}

canonical_original_code:
void symtabInit() {
    typeinit();
    struct id_info **s = scope;
    addIdToTable_noAddrMove(typeIdCreate(int_type, "integer"), s);
    addIdToTable_noAddrMove(typeIdCreate(int_type, "INTEGER"), s);
    addIdToTable_noAddrMove(typeIdCreate(char_type, "char"), s);
    addIdToTable_noAddrMove(typeIdCreate(char_type, "CHAR"), s);
    addIdToTable_noAddrMove(typeIdCreate(bool_type, "boolean"), s);
    addIdToTable_noAddrMove(typeIdCreate(bool_type, "BOOLEAN"), s);
    addIdToTable_noAddrMove(typeIdCreate(str_type, "string"), s);
    addIdToTable_noAddrMove(typeIdCreate(str_type, "STRING"), s);
    true_expr = newBoolExpr(1);
    false_expr = newBoolExpr(0);
    struct id_info *boolid = mkBoolId("true", true_expr);
    addIdToTable_noAddrMove(boolid, s);
    boolid = mkBoolId("TRUE", true_expr);
    addIdToTable_noAddrMove(boolid, s);
    boolid = mkBoolId("false", false_expr);
    addIdToTable_noAddrMove(boolid, s);
    boolid = mkBoolId("FALSE", false_expr);
    addIdToTable_noAddrMove(boolid, s);
    one_expr = newNumExpr(1);
}

user_defined_types: enum identifier_kind { Constant_id=0, Type=1, Variable=2, FParameter=3, Field=4, Procedure=5, Function=6 }

user_defined_types: enum type_kind { Integer=0, Char=1, Boolean=2, String=3, Array=4, Record=5, UndefinedType=6 }

user_defined_types: enum expr_kind_enum { constant_expr=0, operation_bin=1, operation_un=2, registerVal=3, globalVar=4, localVar=5, functionCall=6, typecast=7 }

user_defined_types: enum operator_enum { op_and=0, op_or=1, op_not=2, op_negate=3, op_add=4, op_sub=5, op_mult=6, op_div=7, op_mod=8, op_equal=9, op_nequal=10, op_gt=11, op_lt=12, op_gte=13, op_lte=14 }

user_defined_types: enum stmt_type_enum { assign_stmt=0, if_stmt=1, while_stmt=2, repeat_stmt=3, for_stmt=4, stop_stmt=5, return_stmt=6, read_stmt=7, write_stmt=8, proc_stmt=9, null_stmt=10 }

user_defined_types: struct slist_struct { struct slist_struct *next; void *data; }

user_defined_types: enum BranchType_enum { bt_equal0=0, bt_nequal0=1 }


addVarToCurTable

repo: willghatch/cpslc

decompiled_code:
void __fastcall addVarToCurTable(__int64 a1)
{
int v1; // eax
int v2; // edx
int v3; // edx

v1 = currscope;
v2 = scopeAddr[currscope];
*(_DWORD *)(a1 + 8) = v2;
if ( *(_DWORD *)(a1 + 84) )
v3 = v2 + 4;
else
v3 = **(_DWORD **)(a1 + 24) + v2;
scopeAddr[v1] = v3;
addIdToTable_noAddrMove((const char **)a1, (const char ***)&scope[v1]);
}

canonical_decompiled_code:
void __fastcall func7(__int64 a1)
{
int v1; // eax
int v2; // edx
int v3; // edx

v1 = currscope;
v2 = scopeAddr[currscope];
*(_DWORD *)(a1 + 8) = v2;
if ( *(_DWORD *)(a1 + 84) )
v3 = v2 + 4;
else
v3 = **(_DWORD **)(a1 + 24) + v2;
scopeAddr[v1] = v3;
func5((const char **)a1, (const char ***)&scope[v1]);
}

original_code:
void addVarToCurTable(ID* var) {
    var->id_addr = scopeAddr[currscope];
    if(var->pointer_p) {
        scopeAddr[currscope] += 4;
    } else {
        scopeAddr[currscope] += var->id_type->ty_size;
    }
    addIdToTable_noAddrMove(var, scope+currscope);
}

canonical_original_code:
void addVarToCurTable(struct id_info *var) {
    var->id_addr = scopeAddr[currscope];
    if(var->pointer_p) {
        scopeAddr[currscope] += 4;
    } else {
        scopeAddr[currscope] += var->id_type->ty_size;
    }
    addIdToTable_noAddrMove(var, scope+currscope);
}

variable_types: struct id_info { char *id_name; int id_addr; int id_label; int id_level; struct type_info { int ty_size; char *ty_name; enum type_kind { Integer=0, Char=1, Boolean=2, String=3, Array=4, Record=5, UndefinedType=6 } ty_kind; struct type_info *ty_next; union { struct { struct type_info *RangeType; int min; int max; } ty_subrange; struct { struct type_info *ElementType; struct type_info *IndexType; int min; int max; } ty_array; struct { struct id_info *FirstField; } ty_record; } ty_form; } *id_type; enum identifier_kind { Constant_id=0, Type=1, Variable=2, FParameter=3, Field=4, Procedure=5, Function=6 } id_kind; struct id_info *id_left; struct id_info *id_right; struct id_info *id_next; struct expression_struct { struct type_info *type; enum expr_kind_enum { constant_expr=0, operation_bin=1, operation_un=2, registerVal=3, globalVar=4, localVar=5, functionCall=6, typecast=7 } kind; int int_val; char char_val; int bool_val; char *str_val; int str_const_index; struct expression_struct *offsetExpr; int pointer_p; int to_pointer_p; union { struct { struct expression_struct *operand1; struct expression_struct *operand2; enum operator_enum { op_and=0, op_or=1, op_not=2, op_negate=3, op_add=4, op_sub=5, op_mult=6, op_div=7, op_mod=8, op_equal=9, op_nequal=10, op_gt=11, op_lt=12, op_gte=13, op_lte=14 } op; } opdata; int reg_number; struct id_info *id; struct stmt_struct { enum stmt_type_enum { assign_stmt=0, if_stmt=1, while_stmt=2, repeat_stmt=3, for_stmt=4, stop_stmt=5, return_stmt=6, read_stmt=7, write_stmt=8, proc_stmt=9, null_stmt=10 } type; union { struct htslist_struct { struct slist_struct { struct slist_struct *next; void *data; } *head; struct slist_struct *tail; } *if_conditionals; struct slist_struct *exprList; struct expression_struct *expression; struct { struct stmt_struct *init; struct conditional_struct { struct expression_struct *condition; enum BranchType_enum { bt_equal0=0, bt_nequal0=1 } branchType; struct htslist_struct *statements; } *cBlock; } loopdata; struct { struct expression_struct *lvalue; struct expression_struct *rvalue; } assigndata; struct { char *name; struct slist_struct *paramExprs; } procdata; } data; } *funcCall; struct expression_struct *innerExpr; } edata; } *const_expr; struct slist_struct *typedIdentLists; int param_size; int pointer_p; } *

return_type: void

user_defined_types: struct id_info { char *id_name; int id_addr; int id_label; int id_level; struct type_info *id_type; enum identifier_kind id_kind; struct id_info *id_left; struct id_info *id_right; struct id_info *id_next; struct expression_struct *const_expr; struct slist_struct *typedIdentLists; int param_size; int pointer_p; }

user_defined_types: struct type_info { int ty_size; char *ty_name; enum type_kind ty_kind; struct type_info *ty_next; union { struct { struct type_info *RangeType; int min; int max; } ty_subrange; struct { struct type_info *ElementType; struct type_info *IndexType; int min; int max; } ty_array; struct { struct id_info *FirstField; } ty_record; } ty_form; }

user_defined_types: struct expression_struct { struct type_info *type; enum expr_kind_enum kind; int int_val; char char_val; int bool_val; char *str_val; int str_const_index; struct expression_struct *offsetExpr; int pointer_p; int to_pointer_p; union { struct { struct expression_struct *operand1; struct expression_struct *operand2; enum operator_enum op; } opdata; int reg_number; struct id_info *id; struct stmt_struct *funcCall; struct expression_struct *innerExpr; } edata; }

user_defined_types: struct stmt_struct { enum stmt_type_enum type; union { struct htslist_struct *if_conditionals; struct slist_struct *exprList; struct expression_struct *expression; struct { struct stmt_struct *init; struct conditional_struct *cBlock; } loopdata; struct { struct expression_struct *lvalue; struct expression_struct *rvalue; } assigndata; struct { char *name; struct slist_struct *paramExprs; } procdata; } data; }

user_defined_types: struct htslist_struct { struct slist_struct *head; struct slist_struct *tail; }

user_defined_types: struct conditional_struct { struct expression_struct *condition; enum BranchType_enum branchType; struct htslist_struct *statements; }


getSizeOfScopeVars

decompiled_code:
__int64 __fastcall getSizeOfScopeVars(__int64 a1)
{
__int64 result; // rax
int v2; // ebp
int v3; // ebp

result = 0LL;
if ( a1 )
{
*(_DWORD *)(a1 + 32) = 2;
v2 = 4;
if ( !*(_DWORD *)(a1 + 84) )
v2 = **(_DWORD **)(a1 + 24);
v3 = getSizeOfScopeVars(*(_QWORD *)(a1 + 40)) + v2;
result = v3 + (unsigned int)getSizeOfScopeVars(*(_QWORD *)(a1 + 48));
}
return result;
}

canonical_decompiled_code:
__int64 __fastcall func8(__int64 a1)
{
__int64 result; // rax
int v2; // ebp
int v3; // ebp

result = 0LL;
if ( a1 )
{
*(_DWORD *)(a1 + 32) = 2;
v2 = 4;
if ( !*(_DWORD *)(a1 + 84) )
v2 = **(_DWORD **)(a1 + 24);
v3 = func8(*(_QWORD *)(a1 + 40)) + v2;
result = v3 + (unsigned int)func8(*(_QWORD *)(a1 + 48));
}
return result;
}

original_code:
int getSizeOfScopeVars(ID* scope) {
    int size = 0;
    if (scope != ((void *)0)) {
        if(scope->id_kind = Variable) {
            if(scope->pointer_p) {
                size += 4;
            } else {
                TYPE* t = scope->id_type;
                size += t->ty_size;
            }
        }
        size += getSizeOfScopeVars(scope->id_left);
        size += getSizeOfScopeVars(scope->id_right);
    }
    return size;
}

canonical_original_code:
int getSizeOfScopeVars(struct id_info *scope) {
    int size = 0;
    if (scope != ((void *)0)) {
        if(scope->id_kind = Variable) {
            if(scope->pointer_p) {
                size += 4;
            } else {
                struct type_info *t = scope->id_type;
                size += t->ty_size;
            }
        }
        size += getSizeOfScopeVars(scope->id_left);
        size += getSizeOfScopeVars(scope->id_right);
    }
    return size;
}

variable_types: size int

variable_types: struct type_info { int ty_size; char *ty_name; enum type_kind { Integer=0, Char=1, Boolean=2, String=3, Array=4, Record=5, UndefinedType=6 } ty_kind; struct type_info *ty_next; union { struct { struct type_info *RangeType; int min; int max; } ty_subrange; struct { struct type_info *ElementType; struct type_info *IndexType; int min; int max; } ty_array; struct { struct id_info { char *id_name; int id_addr; int id_label; int id_level; struct type_info *id_type; enum identifier_kind { Constant_id=0, Type=1, Variable=2, FParameter=3, Field=4, Procedure=5, Function=6 } id_kind; struct id_info *id_left; struct id_info *id_right; struct id_info *id_next; struct expression_struct { struct type_info *type; enum expr_kind_enum { constant_expr=0, operation_bin=1, operation_un=2, registerVal=3, globalVar=4, localVar=5, functionCall=6, typecast=7 } kind; int int_val; char char_val; int bool_val; char *str_val; int str_const_index; struct expression_struct *offsetExpr; int pointer_p; int to_pointer_p; union { struct { struct expression_struct *operand1; struct expression_struct *operand2; enum operator_enum { op_and=0, op_or=1, op_not=2, op_negate=3, op_add=4, op_sub=5, op_mult=6, op_div=7, op_mod=8, op_equal=9, op_nequal=10, op_gt=11, op_lt=12, op_gte=13, op_lte=14 } op; } opdata; int reg_number; struct id_info *id; struct stmt_struct { enum stmt_type_enum { assign_stmt=0, if_stmt=1, while_stmt=2, repeat_stmt=3, for_stmt=4, stop_stmt=5, return_stmt=6, read_stmt=7, write_stmt=8, proc_stmt=9, null_stmt=10 } type; union { struct htslist_struct { struct slist_struct { struct slist_struct *next; void *data; } *head; struct slist_struct *tail; } *if_conditionals; struct slist_struct *exprList; struct expression_struct *expression; struct { struct stmt_struct *init; struct conditional_struct { struct expression_struct *condition; enum BranchType_enum { bt_equal0=0, bt_nequal0=1 } branchType; struct htslist_struct *statements; } *cBlock; } loopdata; struct { struct expression_struct *lvalue; struct expression_struct *rvalue; } assigndata; struct { char *name; struct slist_struct *paramExprs; } procdata; } data; } *funcCall; struct expression_struct *innerExpr; } edata; } *const_expr; struct slist_struct *typedIdentLists; int param_size; int pointer_p; } *FirstField; } ty_record; } ty_form; } *

return_type: int


freeIdTree

decompiled_code:
void __fastcall freeIdTree(void *ptr)
{
if ( ptr )
{
freeIdTree(*((void **)ptr + 5));
freeIdTree(*((void **)ptr + 6));
free(ptr);
}
}

canonical_decompiled_code:
void __fastcall func9(void *ptr)
{
if ( ptr )
{
func9(*((void **)ptr + 5));
func9(*((void **)ptr + 6));
free(ptr);
}
}

original_code:
void freeIdTree(ID* tree) {
    if (tree == ((void *)0)) {
        return;
    }
    freeIdTree(tree->id_left);
    freeIdTree(tree->id_right);
    free(tree);
}

canonical_original_code:
void freeIdTree(struct id_info *tree) {
    if (tree == ((void *)0)) {
        return;
    }
    freeIdTree(tree->id_left);
    freeIdTree(tree->id_right);
    free(tree);
}


getTypeKindName

decompiled_code:
const char *__fastcall getTypeKindName(int a1)
{
const char *result; // rax

switch ( a1 )
{
case 0:
result = "Integer";
break;
case 1:
result = "Char";
break;
case 2:
result = "Boolean";
break;
case 3:
result = "String";
break;
case 4:
result = "Array";
break;
case 5:
result = "Record";
break;
case 6:
result = "UndefinedType";
break;
default:
return result;
}
return result;
}

canonical_decompiled_code:
const char *__fastcall func10(int a1)
{
const char *result; // rax

switch ( a1 )
{
case 0:
result = "Integer";
break;
case 1:
result = "Char";
break;
case 2:
result = "Boolean";
break;
case 3:
result = "String";
break;
case 4:
result = "Array";
break;
case 5:
result = "Record";
break;
case 6:
result = "UndefinedType";
break;
default:
return result;
}
return result;
}

original_code:
char* getTypeKindName(TY_KIND kind) {
    switch(kind) {
        case Integer:
            return "Integer";
        case Char:
            return "Char";
        case Boolean:
            return "Boolean";
        case String:
            return "String";
        case Array:
            return "Array";
        case Record:
            return "Record";
        case UndefinedType:
            return "UndefinedType";
    }
}

canonical_original_code:
char *getTypeKindName(enum type_kind kind) {
    switch(kind) {
        case Integer:
            return "Integer";
        case Char:
            return "Char";
        case Boolean:
            return "Boolean";
        case String:
            return "String";
        case Array:
            return "Array";
        case Record:
            return "Record";
        case UndefinedType:
            return "UndefinedType";
    }
}

variable_types: enum type_kind { Integer=0, Char=1, Boolean=2, String=3, Array=4, Record=5, UndefinedType=6 }

return_type: char *


printTypeInfo

decompiled_code:
int __fastcall printTypeInfo(unsigned int *a1)
{
const char *v1; // rax
int result; // eax
__int64 i; // rbx

v1 = getTypeKindName(a1[4]);
printf(" Type kind: %s\n", v1);
result = printf(" Type size: %i\n", *a1);
if ( a1[4] == 5 )
{
result = puts(" Layout:");
for ( i = *((_QWORD *)a1 + 4); i; i = *(_QWORD *)(i + 56) )
result = printf(" field %s of type %s\n", *(const char **)i, *(const char **)(*(_QWORD *)(i + 24) + 8LL));
}
if ( a1[4] == 4 )
{
printf(" Elem Type: %s\n", *(const char **)(*((_QWORD *)a1 + 4) + 8LL));
printf(" Min index: %i\n", a1[12]);
result = printf(" Max index: %i\n", a1[13]);
}
return result;
}

canonical_decompiled_code:
int __fastcall func11(unsigned int *a1)
{
const char *v1; // rax
int result; // eax
__int64 i; // rbx

v1 = func10(a1[4]);
printf(" Type kind: %s\n", v1);
result = printf(" Type size: %i\n", *a1);
if ( a1[4] == 5 )
{
result = puts(" Layout:");
for ( i = *((_QWORD *)a1 + 4); i; i = *(_QWORD *)(i + 56) )
result = printf(" field %s of type %s\n", *(const char **)i, *(const char **)(*(_QWORD *)(i + 24) + 8LL));
}
if ( a1[4] == 4 )
{
printf(" Elem Type: %s\n", *(const char **)(*((_QWORD *)a1 + 4) + 8LL));
printf(" Min index: %i\n", a1[12]);
result = printf(" Max index: %i\n", a1[13]);
}
return result;
}

original_code:
void printTypeInfo(TYPE* type) {
    printf(" Type kind: %s\n", getTypeKindName(type->ty_kind));
    printf(" Type size: %i\n", type->ty_size);
    if(type->ty_kind == Record) {
        printf(" Layout:\n");
        ID* id = type->ty_form.ty_record.FirstField;
        while(id != ((void *)0)) {
            printf("  field %s of type %s\n", id->id_name, id->id_type->ty_name);
            id = id->id_next;
        }
    }
    if(type->ty_kind == Array) {
        printf(" Elem Type: %s\n", type->ty_form.ty_array.ElementType->ty_name);
        printf(" Min index: %i\n", type->ty_form.ty_array.min);
        printf(" Max index: %i\n", type->ty_form.ty_array.max);
    }
}

canonical_original_code:
void printTypeInfo(struct type_info *type) {
    printf(" Type kind: %s\n", getTypeKindName(type->ty_kind));
    printf(" Type size: %i\n", type->ty_size);
    if(type->ty_kind == Record) {
        printf(" Layout:\n");
        struct id_info *id = type->ty_form.ty_record.FirstField;
        while(id != ((void *)0)) {
            printf("  field %s of type %s\n", id->id_name, id->id_type->ty_name);
            id = id->id_next;
        }
    }
    if(type->ty_kind == Array) {
        printf(" Elem Type: %s\n", type->ty_form.ty_array.ElementType->ty_name);
        printf(" Min index: %i\n", type->ty_form.ty_array.min);
        printf(" Max index: %i\n", type->ty_form.ty_array.max);
    }
}


printConstInfo

decompiled_code:
void __fastcall printConstInfo(__int64 a1)
{
__int64 v1; // rax
__int64 v2; // rdx

if ( a1 )
{
if ( !*(_DWORD *)(a1 + 32) )
{
v1 = *(_QWORD *)(a1 + 64);
if ( !*(_DWORD *)(v1 + 8) )
{
v2 = *(_QWORD *)(a1 + 24);
if ( v2 == int_type )
{
printf(" Value: %i\n", *(unsigned int *)(v1 + 12));
}
else if ( v2 == char_type )
{
printf(" Value: %c\n", (unsigned int)*(char *)(v1 + 16));
}
else if ( v2 == str_type )
{
printf(" Value: \"%s\"", *(const char **)(v1 + 24));
}
}
}
}
}

canonical_decompiled_code:
void __fastcall func12(__int64 a1)
{
__int64 v1; // rax
__int64 v2; // rdx

if ( a1 )
{
if ( !*(_DWORD *)(a1 + 32) )
{
v1 = *(_QWORD *)(a1 + 64);
if ( !*(_DWORD *)(v1 + 8) )
{
v2 = *(_QWORD *)(a1 + 24);
if ( v2 == int_type )
{
printf(" Value: %i\n", *(unsigned int *)(v1 + 12));
}
else if ( v2 == char_type )
{
printf(" Value: %c\n", (unsigned int)*(char *)(v1 + 16));
}
else if ( v2 == str_type )
{
printf(" Value: \"%s\"", *(const char **)(v1 + 24));
}
}
}
}
}

original_code:
void printConstInfo(ID* c) {
    if(c == ((void *)0) || c->id_kind != Constant_id) {
        return;
    }
    expr* e = c->const_expr;
    if(e->kind == constant_expr) {
        if(c->id_type == int_type) {
            printf(" Value: %i\n", e->int_val);
        } else if (c->id_type == char_type) {
            printf(" Value: %c\n", e->char_val);
        } else if (c->id_type == str_type) {
            printf(" Value: \"%s\"", e->str_val);
        }
    }
}

canonical_original_code:
void printConstInfo(struct id_info *c) {
    if(c == ((void *)0) || c->id_kind != Constant_id) {
        return;
    }
    struct expression_struct *e = c->const_expr;
    if(e->kind == constant_expr) {
        if(c->id_type == int_type) {
            printf(" Value: %i\n", e->int_val);
        } else if (c->id_type == char_type) {
            printf(" Value: %c\n", e->char_val);
        } else if (c->id_type == str_type) {
            printf(" Value: \"%s\"", e->str_val);
        }
    }
}

variable_types: struct expression_struct { struct type_info { int ty_size; char *ty_name; enum type_kind { Integer=0, Char=1, Boolean=2, String=3, Array=4, Record=5, UndefinedType=6 } ty_kind; struct type_info *ty_next; union { struct { struct type_info *RangeType; int min; int max; } ty_subrange; struct { struct type_info *ElementType; struct type_info *IndexType; int min; int max; } ty_array; struct { struct id_info { char *id_name; int id_addr; int id_label; int id_level; struct type_info *id_type; enum identifier_kind { Constant_id=0, Type=1, Variable=2, FParameter=3, Field=4, Procedure=5, Function=6 } id_kind; struct id_info *id_left; struct id_info *id_right; struct id_info *id_next; struct expression_struct *const_expr; struct slist_struct { struct slist_struct *next; void *data; } *typedIdentLists; int param_size; int pointer_p; } *FirstField; } ty_record; } ty_form; } *type; enum expr_kind_enum { constant_expr=0, operation_bin=1, operation_un=2, registerVal=3, globalVar=4, localVar=5, functionCall=6, typecast=7 } kind; int int_val; char char_val; int bool_val; char *str_val; int str_const_index; struct expression_struct *offsetExpr; int pointer_p; int to_pointer_p; union { struct { struct expression_struct *operand1; struct expression_struct *operand2; enum operator_enum { op_and=0, op_or=1, op_not=2, op_negate=3, op_add=4, op_sub=5, op_mult=6, op_div=7, op_mod=8, op_equal=9, op_nequal=10, op_gt=11, op_lt=12, op_gte=13, op_lte=14 } op; } opdata; int reg_number; struct id_info *id; struct stmt_struct { enum stmt_type_enum { assign_stmt=0, if_stmt=1, while_stmt=2, repeat_stmt=3, for_stmt=4, stop_stmt=5, return_stmt=6, read_stmt=7, write_stmt=8, proc_stmt=9, null_stmt=10 } type; union { struct htslist_struct { struct slist_struct *head; struct slist_struct *tail; } *if_conditionals; struct slist_struct *exprList; struct expression_struct *expression; struct { struct stmt_struct *init; struct conditional_struct { struct expression_struct *condition; enum BranchType_enum { bt_equal0=0, bt_nequal0=1 } branchType; struct htslist_struct *statements; } *cBlock; } loopdata; struct { struct expression_struct *lvalue; struct expression_struct *rvalue; } assigndata; struct { char *name; struct slist_struct *paramExprs; } procdata; } data; } *funcCall; struct expression_struct *innerExpr; } edata; } *


printVarInfo

decompiled_code:
int __fastcall printVarInfo(__int64 a1)
{
printf(" Size: %i\n", **(unsigned int **)(a1 + 24));
return printf(" Offset in scope space: %i\n", *(unsigned int *)(a1 + 8));
}

canonical_decompiled_code:
int __fastcall func13(__int64 a1)
{
printf(" Size: %i\n", **(unsigned int **)(a1 + 24));
return printf(" Offset in scope space: %i\n", *(unsigned int *)(a1 + 8));
}

original_code:
void printVarInfo(ID* v) {
    printf(" Size: %i\n", v->id_type->ty_size);
    printf(" Offset in scope space: %i\n", v->id_addr);
}

canonical_original_code:
void printVarInfo(struct id_info *v) {
    printf(" Size: %i\n", v->id_type->ty_size);
    printf(" Offset in scope space: %i\n", v->id_addr);
}


printIdTree

decompiled_code:
void __fastcall printIdTree(__int64 a1)
{
const char *v1; // rax
const char *v2; // rax

if ( a1 )
{
printIdTree(*(_QWORD *)(a1 + 40));
puts("Identifier:");
printf(" Name: %s\n", *(const char **)a1);
v1 = getIdKindName(*(_DWORD *)(a1 + 32));
printf(" Id Kind: %s\n", v1);
v2 = getTypeName(*(_QWORD *)(a1 + 24));
printf(" Type: %s\n", v2);
if ( *(_DWORD *)(a1 + 32) == 1 )
printTypeInfo(*(unsigned int **)(a1 + 24));
if ( !*(_DWORD *)(a1 + 32) )
printConstInfo(a1);
if ( *(_DWORD *)(a1 + 32) == 2 )
printVarInfo(a1);
printIdTree(*(_QWORD *)(a1 + 48));
}
}

original_code:
void printIdTree(ID* tree) {
    if (tree == ((void *)0)) {
        return;
    }
    printIdTree(tree->id_left);
    printf("Identifier:\n");
    printf(" Name: %s\n", tree->id_name);
    printf(" Id Kind: %s\n", getIdKindName(tree->id_kind));
    printf(" Type: %s\n", getTypeName(tree->id_type));
    if (tree->id_kind == Type) {
        printTypeInfo(tree->id_type);
    }
    if (tree->id_kind == Procedure || tree->id_kind == Function) {
    }
    if (tree->id_kind == Constant_id) {
        printConstInfo(tree);
    }
    if (tree->id_kind == Variable) {
        printVarInfo(tree);
    }
    printIdTree(tree->id_right);
}

canonical_original_code:
void printIdTree(struct id_info *tree) {
    if (tree == ((void *)0)) {
        return;
    }
    printIdTree(tree->id_left);
    printf("Identifier:\n");
    printf(" Name: %s\n", tree->id_name);
    printf(" Id Kind: %s\n", getIdKindName(tree->id_kind));
    printf(" Type: %s\n", getTypeName(tree->id_type));
    if (tree->id_kind == Type) {
        printTypeInfo(tree->id_type);
    }
    if (tree->id_kind == Procedure || tree->id_kind == Function) {
    }
    if (tree->id_kind == Constant_id) {
        printConstInfo(tree);
    }
    if (tree->id_kind == Variable) {
        printVarInfo(tree);
    }
    printIdTree(tree->id_right);
}


scopePrint

decompiled_code:
void __fastcall scopePrint(unsigned int a1)
{
printf("Printing symbol table at scope level %i:\n", a1);
printIdTree(scope[a1]);
}

canonical_decompiled_code:
void __fastcall func15(unsigned int a1)
{
printf("Printing symbol table at scope level %i:\n", a1);
func14(scope[a1]);
}

original_code:
void scopePrint(int s) {
    printf("Printing symbol table at scope level %i:\n", s);
    printIdTree(scope[s]);
}

variable_types: s int


reserveGlobal

decompiled_code:
__int64 __fastcall reserveGlobal(__int64 a1)
{
__int64 result; // rax

result = m_reserve_global_var(**(unsigned int **)(a1 + 24));
*(_DWORD *)(a1 + 12) = result;
return result;
}

canonical_decompiled_code:
__int64 __fastcall func16(__int64 a1)
{
__int64 result; // rax

result = m_reserve_global_var(**(unsigned int **)(a1 + 24));
*(_DWORD *)(a1 + 12) = result;
return result;
}

original_code:
void reserveGlobal(ID* gvar) {
    int size = gvar->id_type->ty_size;
    int reservation = m_reserve_global_var(size);
    gvar->id_label = reservation;
}

canonical_original_code:
void reserveGlobal(struct id_info *gvar) {
    int size = gvar->id_type->ty_size;
    int reservation = m_reserve_global_var(size);
    gvar->id_label = reservation;
}

variable_types: reservation int


isGlobal

decompiled_code:
_BOOL8 __fastcall isGlobal(__int64 a1)
{
return *(_DWORD *)(a1 + 16) <= 1;
}

canonical_decompiled_code:
_BOOL8 __fastcall func17(__int64 a1)
{
return *(_DWORD *)(a1 + 16) <= 1;
}

original_code:
int isGlobal(ID* id) {
    if(id->id_level < 2)
        return 1;
    return 0;
}

canonical_original_code:
int isGlobal(struct id_info *id) {
    if(id->id_level < 2)
        return 1;
    return 0;
}


reserveGlobals

decompiled_code:
void reserveGlobals()
{
reserveGlobals_recursive(scope[0]);
reserveGlobals_recursive(scope[1]);
}

canonical_decompiled_code:
void func19()
{
func18(scope[0]);
func18(scope[1]);
}

original_code:
void reserveGlobals() {
    _reserveGlobals_recursive(scope[0]);
    _reserveGlobals_recursive(scope[1]);
}


decompiled_code:
_BOOL8 __fastcall isByte_p(_DWORD *a1)
{
return *a1 == 1;
}

canonical_decompiled_code:
_BOOL8 __fastcall func20(_DWORD *a1)
{
return *a1 == 1;
}

original_code:
int isByte_p(TYPE* t) {
    return t->ty_size == 1;
}

canonical_original_code:
int isByte_p(struct type_info *t) {
    return t->ty_size == 1;
}


decompiled_code:
_BOOL8 __fastcall isWord_p(_DWORD *a1)
{
return *a1 == 4;
}

canonical_decompiled_code:
_BOOL8 __fastcall func21(_DWORD *a1)
{
return *a1 == 4;
}

original_code:
int isWord_p(TYPE* t) {
    return t->ty_size == 4;
}

canonical_original_code:
int isWord_p(struct type_info *t) {
    return t->ty_size == 4;
}


findRecordField

decompiled_code:
__int64 __fastcall findRecordField(__int64 a1, const char *a2)
{
__int64 i; // rbx

for ( i = *(_QWORD *)(a1 + 32); i; i = *(_QWORD *)(i + 56) )
{
if ( !strcmp(*(const char **)i, a2) )
break;
}
return i;
}

canonical_decompiled_code:
__int64 __fastcall func22(__int64 a1, const char *a2)
{
__int64 i; // rbx

for ( i = *(_QWORD *)(a1 + 32); i; i = *(_QWORD *)(i + 56) )
{
if ( !strcmp(*(const char **)i, a2) )
break;
}
return i;
}

original_code:
ID* findRecordField(TYPE* rtype, char* fname) {
    ID* field = rtype->ty_form.ty_record.FirstField;
    while(field != ((void *)0)) {
        if (!strcmp(field->id_name, fname)) {
            return field;
        }
        field = field->id_next;
    }
    return ((void *)0);
}

canonical_original_code:
struct id_info *findRecordField(struct type_info *rtype, char *fname) {
    struct id_info *field = rtype->ty_form.ty_record.FirstField;
    while(field != ((void *)0)) {
        if (!strcmp(field->id_name, fname)) {
            return field;
        }
        field = field->id_next;
    }
    return ((void *)0);
}

variable_types:
rtype
struct type_info *

variable_types:
fname
char *

return_type: struct id_info { char *id_name; int id_addr; int id_label; int id_level; struct type_info { int ty_size; char *ty_name; enum type_kind { Integer=0, Char=1, Boolean=2, String=3, Array=4, Record=5, UndefinedType=6 } ty_kind; struct type_info *ty_next; union { struct { struct type_info *RangeType; int min; int max; } ty_subrange; struct { struct type_info *ElementType; struct type_info *IndexType; int min; int max; } ty_array; struct { struct id_info *FirstField; } ty_record; } ty_form; } *id_type; enum identifier_kind { Constant_id=0, Type=1, Variable=2, FParameter=3, Field=4, Procedure=5, Function=6 } id_kind; struct id_info *id_left; struct id_info *id_right; struct id_info *id_next; struct expression_struct { struct type_info *type; enum expr_kind_enum { constant_expr=0, operation_bin=1, operation_un=2, registerVal=3, globalVar=4, localVar=5, functionCall=6, typecast=7 } kind; int int_val; char char_val; int bool_val; char *str_val; int str_const_index; struct expression_struct *offsetExpr; int pointer_p; int to_pointer_p; union { struct { struct expression_struct *operand1; struct expression_struct *operand2; enum operator_enum { op_and=0, op_or=1, op_not=2, op_negate=3, op_add=4, op_sub=5, op_mult=6, op_div=7, op_mod=8, op_equal=9, op_nequal=10, op_gt=11, op_lt=12, op_gte=13, op_lte=14 } op; } opdata; int reg_number; struct id_info *id; struct stmt_struct { enum stmt_type_enum { assign_stmt=0, if_stmt=1, while_stmt=2, repeat_stmt=3, for_stmt=4, stop_stmt=5, return_stmt=6, read_stmt=7, write_stmt=8, proc_stmt=9, null_stmt=10 } type; union { struct htslist_struct { struct slist_struct { struct slist_struct *next; void *data; } *head; struct slist_struct *tail; } *if_conditionals; struct slist_struct *exprList; struct expression_struct *expression; struct { struct stmt_struct *init; struct conditional_struct { struct expression_struct *condition; enum BranchType_enum { bt_equal0=0, bt_nequal0=1 } branchType; struct htslist_struct *statements; } *cBlock; } loopdata; struct { struct expression_struct *lvalue; struct expression_struct *rvalue; } assigndata; struct { char *name; struct slist_struct *paramExprs; } procdata; } data; } *funcCall; struct expression_struct *innerExpr; } edata; } *const_expr; struct slist_struct *typedIdentLists; int param_size; int pointer_p; } *


mkStopStmt

decompiled_code:
_DWORD *mkStopStmt()
{
_DWORD *result; // rax

result = malloc(0x18uLL);
*result = 5;
return result;
}

canonical_decompiled_code:
_DWORD *func0()
{
_DWORD *result; // rax

result = malloc(0x18uLL);
*result = 5;
return result;
}

original_code:
statement* mkStopStmt() {
    statement* s = malloc(sizeof(statement));
    s->type = stop_stmt;
    return s;
}

canonical_original_code:
struct stmt_struct *mkStopStmt() {
    struct stmt_struct *s = malloc(sizeof(statement));
    s->type = stop_stmt;
    return s;
}

variable_types: struct stmt_struct { enum stmt_type_enum { assign_stmt=0, if_stmt=1, while_stmt=2, repeat_stmt=3, for_stmt=4, stop_stmt=5, return_stmt=6, read_stmt=7, write_stmt=8, proc_stmt=9, null_stmt=10 } type; union { struct htslist_struct { struct slist_struct { struct slist_struct *next; void *data; } *head; struct slist_struct *tail; } *if_conditionals; struct slist_struct *exprList; struct expression_struct { struct type_info { int ty_size; char *ty_name; enum type_kind { Integer=0, Char=1, Boolean=2, String=3, Array=4, Record=5, UndefinedType=6 } ty_kind; struct type_info *ty_next; union { struct { struct type_info *RangeType; int min; int max; } ty_subrange; struct { struct type_info *ElementType; struct type_info *IndexType; int min; int max; } ty_array; struct { struct id_info { char *id_name; int id_addr; int id_label; int id_level; struct type_info *id_type; enum identifier_kind { Constant_id=0, Type=1, Variable=2, FParameter=3, Field=4, Procedure=5, Function=6 } id_kind; struct id_info *id_left; struct id_info *id_right; struct id_info *id_next; struct expression_struct *const_expr; struct slist_struct *typedIdentLists; int param_size; int pointer_p; } *FirstField; } ty_record; } ty_form; } *type; enum expr_kind_enum { constant_expr=0, operation_bin=1, operation_un=2, registerVal=3, globalVar=4, localVar=5, functionCall=6, typecast=7 } kind; int int_val; char char_val; int bool_val; char *str_val; int str_const_index; struct expression_struct *offsetExpr; int pointer_p; int to_pointer_p; union { struct { struct expression_struct *operand1; struct expression_struct *operand2; enum operator_enum { op_and=0, op_or=1, op_not=2, op_negate=3, op_add=4, op_sub=5, op_mult=6, op_div=7, op_mod=8, op_equal=9, op_nequal=10, op_gt=11, op_lt=12, op_gte=13, op_lte=14 } op; } opdata; int reg_number; struct id_info *id; struct stmt_struct *funcCall; struct expression_struct *innerExpr; } edata; } *expression; struct { struct stmt_struct *init; struct conditional_struct { struct expression_struct *condition; enum BranchType_enum { bt_equal0=0, bt_nequal0=1 } branchType; struct htslist_struct *statements; } *cBlock; } loopdata; struct { struct expression_struct *lvalue; struct expression_struct *rvalue; } assigndata; struct { char *name; struct slist_struct *paramExprs; } procdata; } data; } *


decompiled_code:
__int64 __fastcall stmt_eval_assign(__int64 a1)
{
return m_assign_stmt(*(_QWORD *)(a1 + 8), *(_QWORD *)(a1 + 16));
}

canonical_decompiled_code:
__int64 __fastcall func1(__int64 a1)
{
return m_assign_stmt(*(_QWORD *)(a1 + 8), *(_QWORD *)(a1 + 16));
}

original_code:
void stmt_eval_assign(statement* s) {
    m_assign_stmt(s->data.assigndata.lvalue, s->data.assigndata.rvalue);
}

canonical_original_code:
void stmt_eval_assign(struct stmt_struct *s) {
    m_assign_stmt(s->data.assigndata.lvalue, s->data.assigndata.rvalue);
}


decompiled_code:
__int64 __fastcall stmt_eval_if(__int64 a1)
{
return m_if_stmt(*(_QWORD *)(a1 + 8));
}

canonical_decompiled_code:
__int64 __fastcall func2(__int64 a1)
{
return m_if_stmt(*(_QWORD *)(a1 + 8));
}

original_code:
void stmt_eval_if(statement* s) {
    m_if_stmt(s->data.if_conditionals);
}

canonical_original_code:
void stmt_eval_if(struct stmt_struct *s) {
    m_if_stmt(s->data.if_conditionals);
}


decompiled_code:
__int64 __fastcall stmt_eval_while(__int64 a1)
{
return m_while_stmt(*(_QWORD *)(a1 + 16));
}

canonical_decompiled_code:
__int64 __fastcall func3(__int64 a1)
{
return m_while_stmt(*(_QWORD *)(a1 + 16));
}

original_code:
void stmt_eval_while(statement* s) {
    m_while_stmt(s->data.loopdata.cBlock);
}

canonical_original_code:
void stmt_eval_while(struct stmt_struct *s) {
    m_while_stmt(s->data.loopdata.cBlock);
}


decompiled_code:
__int64 __fastcall stmt_eval_repeat(__int64 a1)
{
return m_repeat_stmt(*(_QWORD *)(a1 + 16));
}

canonical_decompiled_code:
__int64 __fastcall func4(__int64 a1)
{
return m_repeat_stmt(*(_QWORD *)(a1 + 16));
}

original_code:
void stmt_eval_repeat(statement* s) {
    m_repeat_stmt(s->data.loopdata.cBlock);
}

canonical_original_code:
void stmt_eval_repeat(struct stmt_struct *s) {
    m_repeat_stmt(s->data.loopdata.cBlock);
}


decompiled_code:
__int64 __fastcall stmt_eval_for(__int64 a1)
{
return m_for_stmt(*(_QWORD *)(a1 + 8), *(_QWORD *)(a1 + 16));
}

canonical_decompiled_code:
__int64 __fastcall func5(__int64 a1)
{
return m_for_stmt(*(_QWORD *)(a1 + 8), *(_QWORD *)(a1 + 16));
}

original_code:
void stmt_eval_for(statement* s) {
    m_for_stmt(s->data.loopdata.init, s->data.loopdata.cBlock);
}

canonical_original_code:
void stmt_eval_for(struct stmt_struct *s) {
    m_for_stmt(s->data.loopdata.init, s->data.loopdata.cBlock);
}


decompiled_code:
__int64 stmt_eval_stop()
{
return m_stop_stmt();
}

canonical_decompiled_code:
__int64 func6()
{
return m_stop_stmt();
}

original_code:
void stmt_eval_stop(statement* s) {
    m_stop_stmt();
}

canonical_original_code:
void stmt_eval_stop(struct stmt_struct *s) {
    m_stop_stmt();
}


decompiled_code:
__int64 __fastcall stmt_eval_return(__int64 a1)
{
if ( *(_QWORD *)(a1 + 8) )
m_store_ret_val();
return m_function_end();
}

canonical_decompiled_code:
__int64 __fastcall func7(__int64 a1)
{
if ( *(_QWORD *)(a1 + 8) )
m_store_ret_val();
return m_function_end();
}

original_code:
void stmt_eval_return(statement* s) {
    expr* e = s->data.expression;
    if (e != ((void *)0)) {
        m_store_ret_val(e);
    }
    m_function_end();
}

canonical_original_code:
void stmt_eval_return(struct stmt_struct *s) {
    struct expression_struct *e = s->data.expression;
    if (e != ((void *)0)) {
        m_store_ret_val(e);
    }
    m_function_end();
}


decompiled_code:
__int64 __fastcall stmt_eval_read(__int64 a1)
{
return m_read_stmt(*(_QWORD *)(a1 + 8));
}

canonical_decompiled_code:
__int64 __fastcall func8(__int64 a1)
{
return m_read_stmt(*(_QWORD *)(a1 + 8));
}

original_code:
void stmt_eval_read(statement* s) {
    slist* lvalExprs = s->data.exprList;
    m_read_stmt(lvalExprs);
}

canonical_original_code:
void stmt_eval_read(struct stmt_struct *s) {
    struct slist_struct *lvalExprs = s->data.exprList;
    m_read_stmt(lvalExprs);
}

variable_types: struct slist_struct { struct slist_struct *next; void *data; } *


decompiled_code:
__int64 __fastcall stmt_eval_write(__int64 a1)
{
return m_write_stmt(*(_QWORD *)(a1 + 8));
}

canonical_decompiled_code:
__int64 __fastcall func9(__int64 a1)
{
return m_write_stmt(*(_QWORD *)(a1 + 8));
}

original_code:
void stmt_eval_write(statement* s) {
    slist* lvalExprs = s->data.exprList;
    m_write_stmt(lvalExprs);
}

canonical_original_code:
void stmt_eval_write(struct stmt_struct *s) {
    struct slist_struct *lvalExprs = s->data.exprList;
    m_write_stmt(lvalExprs);
}


decompiled_code:
__int64 __fastcall stmt_eval_proc(__int64 a1)
{
__int64 v1; // rbp
__int64 v2; // rbx
__int64 v3; // r12

v1 = *(_QWORD *)(a1 + 16);
v2 = scopeLookup(*(_QWORD *)(a1 + 8));
if ( !v2 )
yyerror("Unknown function or procedure name");
v3 = *(_QWORD *)(v2 + 24);
funcArgList_checkAndAddPointerPs(v2, v1);
return m_func_call(*(unsigned int *)(v2 + 12), v1, v3);
}

canonical_decompiled_code:
__int64 __fastcall func10(__int64 a1)
{
__int64 v1; // rbp
__int64 v2; // rbx
__int64 v3; // r12

v1 = *(_QWORD *)(a1 + 16);
v2 = scopeLookup(*(_QWORD *)(a1 + 8));
if ( !v2 )
yyerror("Unknown function or procedure name");
v3 = *(_QWORD *)(v2 + 24);
funcArgList_checkAndAddPointerPs(v2, v1);
return m_func_call(*(unsigned int *)(v2 + 12), v1, v3);
}

original_code:
void stmt_eval_proc(statement* s) {
    char* name = s->data.procdata.name;
    slist* paramExprs = s->data.procdata.paramExprs;
    ID* proc = scopeLookup(name);
    if (proc == ((void *)0)) {
        yyerror("Unknown function or procedure name");
    }
    TYPE* t = proc->id_type;
    funcArgList_checkAndAddPointerPs(proc, paramExprs);
    int funcLabel = proc->id_label;
    m_func_call(funcLabel, paramExprs, t);
}

canonical_original_code:
void stmt_eval_proc(struct stmt_struct *s) {
    char *name = s->data.procdata.name;
    struct slist_struct *paramExprs = s->data.procdata.paramExprs;
    struct id_info *proc = scopeLookup(name);
    if (proc == ((void *)0)) {
        yyerror("Unknown function or procedure name");
    }
    struct type_info *t = proc->id_type;
    funcArgList_checkAndAddPointerPs(proc, paramExprs);
    int funcLabel = proc->id_label;
    m_func_call(funcLabel, paramExprs, t);
}

variable_types:
name
char *

variable_types: funcLabel int


decompiled_code:
__int64 __fastcall stmt_eval(_DWORD *a1)
{
__int64 result; // rax

if ( a1 )
{
result = (unsigned int)*a1;
switch ( *a1 )
{
case 0:
result = stmt_eval_assign((__int64)a1);
break;
case 1:
result = stmt_eval_if((__int64)a1);
break;
case 2:
result = stmt_eval_while((__int64)a1);
break;
case 3:
result = stmt_eval_repeat((__int64)a1);
break;
case 4:
result = stmt_eval_for((__int64)a1);
break;
case 5:
result = stmt_eval_stop();
break;
case 6:
result = stmt_eval_return((__int64)a1);
break;
case 7:
result = stmt_eval_read((__int64)a1);
break;
case 8:
result = stmt_eval_write((__int64)a1);
break;
case 9:
result = stmt_eval_proc((__int64)a1);
break;
default:
return result;
}
}
return result;
}

canonical_decompiled_code:
__int64 __fastcall func11(_DWORD *a1)
{
__int64 result; // rax

if ( a1 )
{
result = (unsigned int)*a1;
switch ( *a1 )
{
case 0:
result = func1((__int64)a1);
break;
case 1:
result = func2((__int64)a1);
break;
case 2:
result = func3((__int64)a1);
break;
case 3:
result = func4((__int64)a1);
break;
case 4:
result = func5((__int64)a1);
break;
case 5:
result = func6();
break;
case 6:
result = func7((__int64)a1);
break;
case 7:
result = func8((__int64)a1);
break;
case 8:
result = func9((__int64)a1);
break;
case 9:
result = func10((__int64)a1);
break;
default:
return result;
}
}
return result;
}

original_code:
void stmt_eval(statement* s) {
    if (s == ((void *)0)) {
        return;
    }
    stmt_type t = s->type;
    switch(t) {
        case assign_stmt:
            stmt_eval_assign(s);
            return;
        case if_stmt:
            stmt_eval_if(s);
            return;
        case while_stmt:
            stmt_eval_while(s);
            return;
        case repeat_stmt:
            stmt_eval_repeat(s);
            return;
        case for_stmt:
            stmt_eval_for(s);
            return;
        case stop_stmt:
            stmt_eval_stop(s);
            return;
        case return_stmt:
            stmt_eval_return(s);
            return;
        case read_stmt:
            stmt_eval_read(s);
            return;
        case write_stmt:
            stmt_eval_write(s);
            return;
        case proc_stmt:
            stmt_eval_proc(s);
            return;
        default:
            return;
    }
}

canonical_original_code:
void stmt_eval(struct stmt_struct *s) {
    if (s == ((void *)0)) {
        return;
    }
    enum stmt_type_enum t = s->type;
    switch(t) {
        case assign_stmt:
            stmt_eval_assign(s);
            return;
        case if_stmt:
            stmt_eval_if(s);
            return;
        case while_stmt:
            stmt_eval_while(s);
            return;
        case repeat_stmt:
            stmt_eval_repeat(s);
            return;
        case for_stmt:
            stmt_eval_for(s);
            return;
        case stop_stmt:
            stmt_eval_stop(s);
            return;
        case return_stmt:
            stmt_eval_return(s);
            return;
        case read_stmt:
            stmt_eval_read(s);
            return;
        case write_stmt:
            stmt_eval_write(s);
            return;
        case proc_stmt:
            stmt_eval_proc(s);
            return;
        default:
            return;
    }
}

variable_types: enum stmt_type_enum { assign_stmt=0, if_stmt=1, while_stmt=2, repeat_stmt=3, for_stmt=4, stop_stmt=5, return_stmt=6, read_stmt=7, write_stmt=8, proc_stmt=9, null_stmt=10 }


freeSlist

decompiled_code:
__int64 __fastcall freeSlist(__int64 *a1)
{
__int64 v1; // rbx
__int64 result; // rax

if ( a1 )
{
v1 = *a1;
free(a1);
result = freeSlist(v1);
}
return result;
}

canonical_decompiled_code:
__int64 __fastcall func0(__int64 *a1)
{
__int64 v1; // rbx
__int64 result; // rax

if ( a1 )
{
v1 = *a1;
free(a1);
result = func0(v1);
}
return result;
}

original_code:
void freeSlist(slist* list) {
    if (list == ((void *)0)) {
        return;
    }
    slist* n = list->next;
    free(list);
    freeSlist(n);
}

canonical_original_code:
void freeSlist(struct slist_struct *list) {
    if (list == ((void *)0)) {
        return;
    }
    struct slist_struct *n = list->next;
    free(list);
    freeSlist(n);
}


mkHtslist

decompiled_code:
_QWORD *mkHtslist()
{
_QWORD *result; // rax

result = malloc(0x10uLL);
*result = 0LL;
result[1] = 0LL;
return result;
}

canonical_decompiled_code:
_QWORD *func1()
{
_QWORD *result; // rax

result = malloc(0x10uLL);
*result = 0LL;
result[1] = 0LL;
return result;
}

original_code:
htslist* mkHtslist() {
    htslist* l;
    l = malloc(sizeof(htslist));
    l->head = ((void *)0);
    l->tail = ((void *)0);
    return l;
}

canonical_original_code:
struct htslist_struct *mkHtslist() {
    struct htslist_struct *l;
    l = malloc(sizeof(htslist));
    l->head = ((void *)0);
    l->tail = ((void *)0);
    return l;
}

variable_types: struct htslist_struct { struct slist_struct { struct slist_struct *next; void *data; } *head; struct slist_struct *tail; } *


decompiled_code:
void __fastcall slist_append(_QWORD *a1, __int64 a2)
{
if ( a1 )
{
if ( *a1 )
slist_append();
else
*a1 = mkSlist(a2);
}
}

canonical_decompiled_code:
void __fastcall func2(_QWORD *a1, __int64 a2)
{
if ( a1 )
{
if ( *a1 )
func2();
else
*a1 = mkSlist(a2);
}
}

original_code:
void slist_append(slist* ls, void* elem) {
    if (ls == ((void *)0)) {
    } else if (ls->next == ((void *)0)) {
        ls->next = mkSlist(elem);
    } else {
        slist_append(ls->next, elem);
    }
}

canonical_original_code:
void slist_append(struct slist_struct *ls, void *elem) {
    if (ls == ((void *)0)) {
    } else if (ls->next == ((void *)0)) {
        ls->next = mkSlist(elem);
    } else {
        slist_append(ls->next, elem);
    }
}

variable_types:
elem
void *


decompiled_code:
_DWORD *init_registerState()
{
registerState = (__int64)malloc(0x44uLL);
return clear_regstate((_DWORD *)registerState);
}

canonical_decompiled_code:
_DWORD *func0()
{
registerState = (__int64)malloc(0x44uLL);
return clear_regstate((_DWORD *)registerState);
}

original_code:
void init_registerState() {
    registerState = malloc(sizeof(regstate));
    clear_regstate(registerState);
}


decompiled_code:
__int64 __fastcall cp_regstate(__int64 a1, __int64 a2)
{
__int64 result; // rax

for ( result = 0LL; result != 68; result += 4LL )
*(_DWORD *)(a2 + result) = *(_DWORD *)(a1 + result);
return result;
}

canonical_decompiled_code:
__int64 __fastcall func1(__int64 a1, __int64 a2)
{
__int64 result; // rax

for ( result = 0LL; result != 68; result += 4LL )
*(_DWORD *)(a2 + result) = *(_DWORD *)(a1 + result);
return result;
}

original_code:
void cp_regstate(regstate* in, regstate* out) {
    for (int i = 0; i < 17; ++i) {
        out->reg[i] = in->reg[i];
    }
}

canonical_original_code:
void cp_regstate(struct regstate_struct *in, struct regstate_struct *out) {
    for (int i = 0; i < 17; ++i) {
        out->reg[i] = in->reg[i];
    }
}

variable_types: struct regstate_struct { int reg[17]; } *

variable_types:
out
struct regstate_struct *

variable_types: i int


getReg

decompiled_code:
__int64 __fastcall getReg(__int64 a1)
{
__int64 v1; // rax

v1 = 0LL;
while ( *(_DWORD *)(a1 + 4 * v1) )
{
if ( ++v1 == 17 )
return 0xFFFFFFFFLL;
}
*(_DWORD *)(a1 + 4LL * (int)v1) = 1;
return (unsigned int)(v1 + 8);
}

canonical_decompiled_code:
__int64 __fastcall func2(__int64 a1)
{
__int64 v1; // rax

v1 = 0LL;
while ( *(_DWORD *)(a1 + 4 * v1) )
{
if ( ++v1 == 17 )
return 0xFFFFFFFFLL;
}
*(_DWORD *)(a1 + 4LL * (int)v1) = 1;
return (unsigned int)(v1 + 8);
}

original_code:
int getReg(regstate* state) {
    for (int i = 0; i < 17; ++i) {
        if (!state->reg[i]) {
            state->reg[i] = 1;
            return i + 8;
        }
    }
    return -1;
}

canonical_original_code:
int getReg(struct regstate_struct *state) {
    for (int i = 0; i < 17; ++i) {
        if (!state->reg[i]) {
            state->reg[i] = 1;
            return i + 8;
        }
    }
    return -1;
}


freeReg

decompiled_code:
void __fastcall freeReg(__int64 a1, int a2)
{
if ( a2 )
*(_DWORD *)(a1 + 4LL * (a2 - 8)) = 0;
}

canonical_decompiled_code:
void __fastcall func3(__int64 a1, int a2)
{
if ( a2 )
*(_DWORD *)(a1 + 4LL * (a2 - 8)) = 0;
}

original_code:
void freeReg(regstate* state, int r) {
    if (r == 0)
        return;
    state->reg[r-8] = 0;
}

canonical_original_code:
void freeReg(struct regstate_struct *state, int r) {
    if (r == 0)
        return;
    state->reg[r-8] = 0;
}

variable_types: r int


doUnaryOperator

decompiled_code:
__int64 __fastcall doUnaryOperator(int a1, __int64 a2)
{
unsigned int v2; // eax
unsigned int v3; // ebx

v2 = evalExpr(a2);
v3 = v2;
if ( a1 == 2 )
{
m_not(v2, v2);
}
else if ( a1 == 3 )
{
m_negate(v2, v2);
}
return v3;
}

canonical_decompiled_code:
__int64 __fastcall func0(int a1, __int64 a2)
{
unsigned int v2; // eax
unsigned int v3; // ebx

v2 = func1(a2);
v3 = v2;
if ( a1 == 2 )
{
m_not(v2, v2);
}
else if ( a1 == 3 )
{
m_negate(v2, v2);
}
return v3;
}

original_code:
int doUnaryOperator(openum op, expr* operand) {
    int reg1 = evalExpr(operand);
    switch(op) {
        case op_not:
            m_not(reg1, reg1);
            break;
        case op_negate:
            m_negate(reg1, reg1);
            break;
    }
    return reg1;
}

canonical_original_code:
int doUnaryOperator(enum operator_enum op, struct expression_struct *operand) {
    int reg1 = evalExpr(operand);
    switch(op) {
        case op_not:
            m_not(reg1, reg1);
            break;
        case op_negate:
            m_negate(reg1, reg1);
            break;
    }
    return reg1;
}

variable_types: enum operator_enum { op_and=0, op_or=1, op_not=2, op_negate=3, op_add=4, op_sub=5, op_mult=6, op_div=7, op_mod=8, op_equal=9, op_nequal=10, op_gt=11, op_lt=12, op_gte=13, op_lte=14 }


evalExpr

decompiled_code:
__int64 __fastcall evalExpr(__int64 a1)
{
_DWORD *v1; // r12
__int64 v2; // rbp
__int64 v4; // r13
_DWORD *v5; // rax
_DWORD *v6; // rax
__int64 v7; // rbx
unsigned int v8; // eax
__int64 v9; // rax
unsigned int v10; // er13
__int64 v11; // rbx
_DWORD *v12; // rsi
_DWORD *v13; // rax
unsigned int v14; // eax
__int64 v15; // r14
_DWORD *v16; // rax
_DWORD *v17; // rax
unsigned int v18; // eax
_DWORD *v19; // r12
_DWORD *v20; // rax
_DWORD *v21; // rax
unsigned int v22; // eax
_DWORD *v23; // rax

v1 = *(_DWORD **)a1;
switch ( *(_DWORD *)(a1 + 8) )
{
case 0:
v2 = (unsigned int)getReg(registerState);
m_load_constant(a1, v2);
break;
case 1:
LODWORD(v2) = doBinaryOperator(*(unsigned int *)(a1 + 72), *(_QWORD *)(a1 + 56), *(_QWORD *)(a1 + 64));
break;
case 2:
LODWORD(v2) = doUnaryOperator(*(_DWORD *)(a1 + 72), *(_QWORD *)(a1 + 56));
break;
case 3:
LODWORD(v2) = *(_DWORD *)(a1 + 56);
break;
case 4:
LODWORD(v2) = getReg(registerState);
v4 = (unsigned int)getReg(registerState);
m_load_global_address(*(unsigned int *)(*(_QWORD *)(a1 + 56) + 12LL), v4);
v5 = newRegExpr(v4, int_type);
v6 = newBinOpExpr(4u, *(_QWORD *)(a1 + 40), (__int64)v5);
LODWORD(v7) = evalExpr(v6);
if ( (unsigned int)isWord_p(v1) || (unsigned int)isByte_p(v1) )
{
v8 = isByte_p(v1);
m_load_word_from_addr((unsigned int)v2, (unsigned int)v7, 0LL, v8);
}
else
{
m_copy_reg((unsigned int)v2, (unsigned int)v7);
}
goto LABEL_10;
case 5:
LODWORD(v2) = getReg(registerState);
v9 = *(_QWORD *)(a1 + 56);
v10 = *(_DWORD *)(v9 + 8);
if ( *(_DWORD *)(a1 + 48) || *(_DWORD *)(v9 + 84) )
{
m_load_frame_word((unsigned int)v2, v10, 0LL, 0LL, 0LL);
v11 = *(_QWORD *)(a1 + 40);
v12 = newRegExpr(v2, int_type);
v13 = newBinOpExpr(4u, (__int64)v12, v11);
LODWORD(v2) = evalExpr(v13);
if ( (unsigned int)isWord_p(v1) || (unsigned int)isByte_p(v1) )
{
v14 = isByte_p(v1);
m_load_frame_word((unsigned int)v2, 0LL, v14, 0LL, (unsigned int)v2);
}
}
else
{
v15 = (unsigned int)getReg(registerState);
m_copy_fp(v15);
v16 = newRegExpr(v15, int_type);
v17 = newBinOpExpr(4u, *(_QWORD *)(a1 + 40), (__int64)v16);
LODWORD(v7) = evalExpr(v17);
if ( (unsigned int)isWord_p(v1) || (unsigned int)isByte_p(v1) )
{
v18 = isByte_p(v1);
m_load_frame_word((unsigned int)v2, v10, v18, 0LL, (unsigned int)v7);
}
else
{
v19 = newNumExpr(v10);
v20 = newRegExpr(v7, int_type);
v21 = newBinOpExpr(4u, (__int64)v20, (__int64)v19);
v7 = (unsigned int)evalExpr(v21);
m_copy_reg((unsigned int)v2, v7);
}
LABEL_10:
freeReg(registerState, (unsigned int)v7);
}
break;
case 6:
stmt_eval(*(_QWORD *)(a1 + 56));
if ( (unsigned int)isWord_p(v1) || (unsigned int)isByte_p(v1) )
{
LODWORD(v2) = getReg(registerState);
v22 = isByte_p(v1);
m_load_frame_word((unsigned int)v2, (unsigned int)-*v1, v22, 1LL, 0LL);
m_move_stack_ptr((unsigned int)-*v1);
}
else
{
LODWORD(v2) = getReg(registerState);
v23 = newNumExpr(-*v1);
m_load_constant(v23, (unsigned int)v2);
m_bin_op_to_r1("add", (unsigned int)v2, 29LL);
}
break;
case 7:
LODWORD(v2) = evalExpr(*(_QWORD *)(a1 + 56));
break;
default:
LODWORD(v2) = -1;
break;
}
return (unsigned int)v2;
}

canonical_decompiled_code:
__int64 __fastcall func1(__int64 a1)
{
_DWORD *v1; // r12
__int64 v2; // rbp
__int64 v4; // r13
_DWORD *v5; // rax
_DWORD *v6; // rax
__int64 v7; // rbx
unsigned int v8; // eax
__int64 v9; // rax
unsigned int v10; // er13
__int64 v11; // rbx
_DWORD *v12; // rsi
_DWORD *v13; // rax
unsigned int v14; // eax
__int64 v15; // r14
_DWORD *v16; // rax
_DWORD *v17; // rax
unsigned int v18; // eax
_DWORD *v19; // r12
_DWORD *v20; // rax
_DWORD *v21; // rax
unsigned int v22; // eax
_DWORD *v23; // rax

v1 = *(_DWORD **)a1;
switch ( *(_DWORD *)(a1 + 8) )
{
case 0:
v2 = (unsigned int)getReg(registerState);
m_load_constant(a1, v2);
break;
case 1:
LODWORD(v2) = func3(*(unsigned int *)(a1 + 72), *(_QWORD *)(a1 + 56), *(_QWORD *)(a1 + 64));
break;
case 2:
LODWORD(v2) = func0(*(_DWORD *)(a1 + 72), *(_QWORD *)(a1 + 56));
break;
case 3:
LODWORD(v2) = *(_DWORD *)(a1 + 56);
break;
case 4:
LODWORD(v2) = getReg(registerState);
v4 = (unsigned int)getReg(registerState);
m_load_global_address(*(unsigned int *)(*(_QWORD *)(a1 + 56) + 12LL), v4);
v5 = newRegExpr(v4, int_type);
v6 = newBinOpExpr(4u, *(_QWORD *)(a1 + 40), (__int64)v5);
LODWORD(v7) = func1(v6);
if ( (unsigned int)isWord_p(v1) || (unsigned int)isByte_p(v1) )
{
v8 = isByte_p(v1);
m_load_word_from_addr((unsigned int)v2, (unsigned int)v7, 0LL, v8);
}
else
{
m_copy_reg((unsigned int)v2, (unsigned int)v7);
}
goto LABEL_10;
case 5:
LODWORD(v2) = getReg(registerState);
v9 = *(_QWORD *)(a1 + 56);
v10 = *(_DWORD *)(v9 + 8);
if ( *(_DWORD *)(a1 + 48) || *(_DWORD *)(v9 + 84) )
{
m_load_frame_word((unsigned int)v2, v10, 0LL, 0LL, 0LL);
v11 = *(_QWORD *)(a1 + 40);
v12 = newRegExpr(v2, int_type);
v13 = newBinOpExpr(4u, (__int64)v12, v11);
LODWORD(v2) = func1(v13);
if ( (unsigned int)isWord_p(v1) || (unsigned int)isByte_p(v1) )
{
v14 = isByte_p(v1);
m_load_frame_word((unsigned int)v2, 0LL, v14, 0LL, (unsigned int)v2);
}
}
else
{
v15 = (unsigned int)getReg(registerState);
m_copy_fp(v15);
v16 = newRegExpr(v15, int_type);
v17 = newBinOpExpr(4u, *(_QWORD *)(a1 + 40), (__int64)v16);
LODWORD(v7) = func1(v17);
if ( (unsigned int)isWord_p(v1) || (unsigned int)isByte_p(v1) )
{
v18 = isByte_p(v1);
m_load_frame_word((unsigned int)v2, v10, v18, 0LL, (unsigned int)v7);
}
else
{
v19 = newNumExpr(v10);
v20 = newRegExpr(v7, int_type);
v21 = newBinOpExpr(4u, (__int64)v20, (__int64)v19);
v7 = (unsigned int)func1(v21);
m_copy_reg((unsigned int)v2, v7);
}
LABEL_10:
freeReg(registerState, (unsigned int)v7);
}
break;
case 6:
stmt_eval(*(_QWORD *)(a1 + 56));
if ( (unsigned int)isWord_p(v1) || (unsigned int)isByte_p(v1) )
{
LODWORD(v2) = getReg(registerState);
v22 = isByte_p(v1);
m_load_frame_word((unsigned int)v2, (unsigned int)-*v1, v22, 1LL, 0LL);
m_move_stack_ptr((unsigned int)-*v1);
}
else
{
LODWORD(v2) = getReg(registerState);
v23 = newNumExpr(-*v1);
m_load_constant(v23, (unsigned int)v2);
m_bin_op_to_r1("add", (unsigned int)v2, 29LL);
}
break;
case 7:
LODWORD(v2) = func1(*(_QWORD *)(a1 + 56));
break;
default:
LODWORD(v2) = -1;
break;
}
return (unsigned int)v2;
}

original_code:
int evalExpr(expr* e) {
    int reg = -1;
    int offsetReg, addrReg;
    TYPE* t = e->type;
    switch(e->kind) {
        case constant_expr:
            reg = getReg(registerState);
            m_load_constant(e, reg);
            break;
        case operation_bin:
            reg = doBinaryOperator(e->edata.opdata.op, e->edata.opdata.operand1, e->edata.opdata.operand2);
            break;
        case operation_un:
            reg = doUnaryOperator(e->edata.opdata.op, e->edata.opdata.operand1);
            break;
        case typecast:
            reg = evalExpr(e->edata.innerExpr);
            break;
        case globalVar:
            reg = getReg(registerState);
            int addrReg = getReg(registerState);
            int globalIndex = e->edata.id->id_label;
            m_load_global_address(globalIndex, addrReg);
            addrReg = evalExpr(newBinOpExpr(op_add, e->offsetExpr, newRegExpr(addrReg, int_type)));
            if(isWord_p(t) || isByte_p(t)) {
                m_load_word_from_addr(reg, addrReg, 0, isByte_p(t));
            } else {
                m_copy_reg(reg, addrReg);
            }
            freeReg(registerState, addrReg);
            break;
        case localVar:
            reg = getReg(registerState);
            int staticOffset = e->edata.id->id_addr;
            if(e->pointer_p || e->edata.id->pointer_p) {
                m_load_frame_word(reg, staticOffset, 0, 0, 0);
                reg = evalExpr(newBinOpExpr(op_add, newRegExpr(reg, int_type), e->offsetExpr));
                if(isWord_p(t) || isByte_p(t)) {
                    m_load_frame_word(reg, 0, isByte_p(t), 0, reg);
                }
            } else {
                addrReg = getReg(registerState);
                m_copy_fp(addrReg);
                addrReg = evalExpr(newBinOpExpr(op_add, e->offsetExpr, newRegExpr(addrReg, int_type)));
                if(isWord_p(t) || isByte_p(t)) {
                    m_load_frame_word(reg, staticOffset, isByte_p(t), 0, addrReg);
                } else {
                    addrReg = evalExpr(newBinOpExpr(op_add, newRegExpr(addrReg, int_type), newNumExpr(staticOffset)));
                    m_copy_reg(reg, addrReg);
                }
                freeReg(registerState, addrReg);
            }
            break;
        case functionCall:
            stmt_eval(e->edata.funcCall);
            if(isWord_p(t) || isByte_p(t)) {
                reg = getReg(registerState);
                m_load_frame_word(reg, -(t->ty_size), isByte_p(t), 1, 0);
                m_move_stack_ptr(-t->ty_size);
            } else {
                reg = getReg(registerState);
                m_load_constant(newNumExpr(-t->ty_size), reg);
                m_bin_op_to_r1("add", reg, 29);
            }
            break;
        case registerVal:
            reg = e->edata.reg_number;
        default:
            break;
    }
    return reg;
}

canonical_original_code:
int evalExpr(struct expression_struct *e) {
    int reg = -1;
    int offsetReg; int addrReg;
    struct type_info *t = e->type;
    switch(e->kind) {
        case constant_expr:
            reg = getReg(registerState);
            m_load_constant(e, reg);
            break;
        case operation_bin:
            reg = doBinaryOperator(e->edata.opdata.op, e->edata.opdata.operand1, e->edata.opdata.operand2);
            break;
        case operation_un:
            reg = doUnaryOperator(e->edata.opdata.op, e->edata.opdata.operand1);
            break;
        case typecast:
            reg = evalExpr(e->edata.innerExpr);
            break;
        case globalVar:
            reg = getReg(registerState);
            int addrReg = getReg(registerState);
            int globalIndex = e->edata.id->id_label;
            m_load_global_address(globalIndex, addrReg);
            addrReg = evalExpr(newBinOpExpr(op_add, e->offsetExpr, newRegExpr(addrReg, int_type)));
            if(isWord_p(t) || isByte_p(t)) {
                m_load_word_from_addr(reg, addrReg, 0, isByte_p(t));
            } else {
                m_copy_reg(reg, addrReg);
            }
            freeReg(registerState, addrReg);
            break;
        case localVar:
            reg = getReg(registerState);
            int staticOffset = e->edata.id->id_addr;
            if(e->pointer_p || e->edata.id->pointer_p) {
                m_load_frame_word(reg, staticOffset, 0, 0, 0);
                reg = evalExpr(newBinOpExpr(op_add, newRegExpr(reg, int_type), e->offsetExpr));
                if(isWord_p(t) || isByte_p(t)) {
                    m_load_frame_word(reg, 0, isByte_p(t), 0, reg);
                }
            } else {
                addrReg = getReg(registerState);
                m_copy_fp(addrReg);
                addrReg = evalExpr(newBinOpExpr(op_add, e->offsetExpr, newRegExpr(addrReg, int_type)));
                if(isWord_p(t) || isByte_p(t)) {
                    m_load_frame_word(reg, staticOffset, isByte_p(t), 0, addrReg);
                } else {
                    addrReg = evalExpr(newBinOpExpr(op_add, newRegExpr(addrReg, int_type), newNumExpr(staticOffset)));
                    m_copy_reg(reg, addrReg);
                }
                freeReg(registerState, addrReg);
            }
            break;
        case functionCall:
            stmt_eval(e->edata.funcCall);
            if(isWord_p(t) || isByte_p(t)) {
                reg = getReg(registerState);
                m_load_frame_word(reg, -(t->ty_size), isByte_p(t), 1, 0);
                m_move_stack_ptr(-t->ty_size);
            } else {
                reg = getReg(registerState);
                m_load_constant(newNumExpr(-t->ty_size), reg);
                m_bin_op_to_r1("add", reg, 29);
            }
            break;
        case registerVal:
            reg = e->edata.reg_number;
        default:
            break;
    }
    return reg;
}

variable_types: struct expression_struct { struct type_info { int ty_size; char *ty_name; enum type_kind { Integer=0, Char=1, Boolean=2, String=3, Array=4, Record=5, UndefinedType=6 } ty_kind; struct type_info *ty_next; union { struct { struct type_info *RangeType; int min; int max; } ty_subrange; struct { struct type_info *ElementType; struct type_info *IndexType; int min; int max; } ty_array; struct { struct id_info { char *id_name; int id_addr; int id_label; int id_level; struct type_info *id_type; enum identifier_kind { Constant_id=0, Type=1, Variable=2, FParameter=3, Field=4, Procedure=5, Function=6 } id_kind; struct id_info *id_left; struct id_info *id_right; struct id_info *id_next; struct expression_struct *const_expr; struct slist_struct { struct slist_struct *next; void *data; } *typedIdentLists; int param_size; int pointer_p; } *FirstField; } ty_record; } ty_form; } *type; enum expr_kind_enum { constant_expr=0, operation_bin=1, operation_un=2, registerVal=3, globalVar=4, localVar=5, functionCall=6, typecast=7 } kind; int int_val; char char_val; int bool_val; char *str_val; int str_const_index; struct expression_struct *offsetExpr; int pointer_p; int to_pointer_p; union { struct { struct expression_struct *operand1; struct expression_struct *operand2; enum operator_enum { op_and=0, op_or=1, op_not=2, op_negate=3, op_add=4, op_sub=5, op_mult=6, op_div=7, op_mod=8, op_equal=9, op_nequal=10, op_gt=11, op_lt=12, op_gte=13, op_lte=14 } op; } opdata; int reg_number; struct id_info *id; struct stmt_struct { enum stmt_type_enum { assign_stmt=0, if_stmt=1, while_stmt=2, repeat_stmt=3, for_stmt=4, stop_stmt=5, return_stmt=6, read_stmt=7, write_stmt=8, proc_stmt=9, null_stmt=10 } type; union { struct htslist_struct { struct slist_struct *head; struct slist_struct *tail; } *if_conditionals; struct slist_struct *exprList; struct expression_struct *expression; struct { struct stmt_struct *init; struct conditional_struct { struct expression_struct *condition; enum BranchType_enum { bt_equal0=0, bt_nequal0=1 } branchType; struct htslist_struct *statements; } *cBlock; } loopdata; struct { struct expression_struct *lvalue; struct expression_struct *rvalue; } assigndata; struct { char *name; struct slist_struct *paramExprs; } procdata; } data; } *funcCall; struct expression_struct *innerExpr; } edata; } *

variable_types: reg int

variable_types: offsetReg int

variable_types: addrReg int

variable_types: struct type_info { int ty_size; char *ty_name; enum type_kind { Integer=0, Char=1, Boolean=2, String=3, Array=4, Record=5, UndefinedType=6 } ty_kind; struct type_info *ty_next; union { struct { struct type_info *RangeType; int min; int max; } ty_subrange; struct { struct type_info *ElementType; struct type_info *IndexType; int min; int max; } ty_array; struct { struct id_info { char *id_name; int id_addr; int id_label; int id_level; struct type_info *id_type; enum identifier_kind { Constant_id=0, Type=1, Variable=2, FParameter=3, Field=4, Procedure=5, Function=6 } id_kind; struct id_info *id_left; struct id_info *id_right; struct id_info *id_next; struct expression_struct { struct type_info *type; enum expr_kind_enum { constant_expr=0, operation_bin=1, operation_un=2, registerVal=3, globalVar=4, localVar=5, functionCall=6, typecast=7 } kind; int int_val; char char_val; int bool_val; char *str_val; int str_const_index; struct expression_struct *offsetExpr; int pointer_p; int to_pointer_p; union { struct { struct expression_struct *operand1; struct expression_struct *operand2; enum operator_enum { op_and=0, op_or=1, op_not=2, op_negate=3, op_add=4, op_sub=5, op_mult=6, op_div=7, op_mod=8, op_equal=9, op_nequal=10, op_gt=11, op_lt=12, op_gte=13, op_lte=14 } op; } opdata; int reg_number; struct id_info *id; struct stmt_struct { enum stmt_type_enum { assign_stmt=0, if_stmt=1, while_stmt=2, repeat_stmt=3, for_stmt=4, stop_stmt=5, return_stmt=6, read_stmt=7, write_stmt=8, proc_stmt=9, null_stmt=10 } type; union { struct htslist_struct { struct slist_struct { struct slist_struct *next; void *data; } *head; struct slist_struct *tail; } *if_conditionals; struct slist_struct *exprList; struct expression_struct *expression; struct { struct stmt_struct *init; struct conditional_struct { struct expression_struct *condition; enum BranchType_enum { bt_equal0=0, bt_nequal0=1 } branchType; struct htslist_struct *statements; } *cBlock; } loopdata; struct { struct expression_struct *lvalue; struct expression_struct *rvalue; } assigndata; struct { char *name; struct slist_struct *paramExprs; } procdata; } data; } *funcCall; struct expression_struct *innerExpr; } edata; } *const_expr; struct slist_struct *typedIdentLists; int param_size; int pointer_p; } *FirstField; } ty_record; } ty_form; } *

variable_types: globalIndex int

variable_types: staticOffset int


evalExprToPointer

decompiled_code:
__int64 __fastcall evalExprToPointer(__int64 a1)
{
unsigned int v1; // eax
int v2; // ebx
__int64 v3; // r12
_DWORD *v4; // rbp
_DWORD *v5; // rax
_DWORD *v6; // rax
_DWORD *v7; // rax
_DWORD *v8; // rax

v1 = getReg(registerState);
v2 = v1;
v3 = *(_QWORD *)(a1 + 40);
if ( *(_DWORD *)(a1 + 8) == 4 )
{
m_load_global_address(*(unsigned int *)(*(_QWORD *)(a1 + 56) + 12LL), v1);
}
else
{
m_copy_fp(v1);
v4 = newNumExpr(*(_DWORD *)(*(_QWORD *)(a1 + 56) + 8LL));
v5 = newRegExpr(v2, int_type);
v6 = newBinOpExpr(4u, (__int64)v5, (__int64)v4);
v2 = evalExpr((__int64)v6);
}
v7 = newRegExpr(v2, int_type);
v8 = newBinOpExpr(4u, (__int64)v7, v3);
return evalExpr((__int64)v8);
}

canonical_decompiled_code:
__int64 __fastcall func2(__int64 a1)
{
unsigned int v1; // eax
int v2; // ebx
__int64 v3; // r12
_DWORD *v4; // rbp
_DWORD *v5; // rax
_DWORD *v6; // rax
_DWORD *v7; // rax
_DWORD *v8; // rax

v1 = getReg(registerState);
v2 = v1;
v3 = *(_QWORD *)(a1 + 40);
if ( *(_DWORD *)(a1 + 8) == 4 )
{
m_load_global_address(*(unsigned int *)(*(_QWORD *)(a1 + 56) + 12LL), v1);
}
else
{
m_copy_fp(v1);
v4 = newNumExpr(*(_DWORD *)(*(_QWORD *)(a1 + 56) + 8LL));
v5 = newRegExpr(v2, int_type);
v6 = newBinOpExpr(4u, (__int64)v5, (__int64)v4);
v2 = func1((__int64)v6);
}
v7 = newRegExpr(v2, int_type);
v8 = newBinOpExpr(4u, (__int64)v7, v3);
return func1((__int64)v8);
}

original_code:
int evalExprToPointer(expr* e) {
        int reg = getReg(registerState);
        expr* offsetExpr = e->offsetExpr;
        int globalP = e->kind == globalVar;
        if (globalP) {
            m_load_global_address(e->edata.id->id_label, reg);
        } else {
            m_copy_fp(reg);
            reg = evalExpr(newBinOpExpr(op_add, newRegExpr(reg, int_type), newNumExpr(e->edata.id->id_addr)));
        }
        reg = evalExpr(newBinOpExpr(op_add, newRegExpr(reg, int_type), offsetExpr));
        return reg;
}

canonical_original_code:
int evalExprToPointer(struct expression_struct *e) {
        int reg = getReg(registerState);
        struct expression_struct *offsetExpr = e->offsetExpr;
        int globalP = e->kind == globalVar;
        if (globalP) {
            m_load_global_address(e->edata.id->id_label, reg);
        } else {
            m_copy_fp(reg);
            reg = evalExpr(newBinOpExpr(op_add, newRegExpr(reg, int_type), newNumExpr(e->edata.id->id_addr)));
        }
        reg = evalExpr(newBinOpExpr(op_add, newRegExpr(reg, int_type), offsetExpr));
        return reg;
}

variable_types: globalP int


doBinaryOperator

decompiled_code:
__int64 __fastcall doBinaryOperator(int a1, __int64 a2, __int64 a3)
{
unsigned int v4; // ebp
unsigned int v5; // eax
unsigned int v6; // er12

v4 = evalExpr(a2);
v5 = evalExpr(a3);
v6 = v5;
switch ( a1 )
{
case 0:
m_bin_op_to_r1("and", v4, v5);
freeReg(registerState, v6);
break;
case 1:
m_bin_op_to_r1("or", v4, v5);
freeReg(registerState, v6);
break;
case 4:
m_bin_op_to_r1("add", v4, v5);
freeReg(registerState, v6);
break;
case 5:
m_bin_op_to_r1("sub", v4, v5);
freeReg(registerState, v6);
break;
case 6:
m_mult_op(v4, v5, v4);
freeReg(registerState, v6);
break;
case 7:
m_divide_op(v4, v5, v4);
freeReg(registerState, v6);
break;
case 8:
m_modulo_op(v4, v5, v4);
freeReg(registerState, v6);
break;
case 9:
m_compare_mips_op("beq", v4, v5, v4);
freeReg(registerState, v6);
break;
case 10:
m_compare_mips_op("bne", v4, v5, v4);
freeReg(registerState, v6);
break;
case 11:
m_compare_mips_op("bgtz", v4, v5, v4);
freeReg(registerState, v6);
break;
case 12:
m_compare_mips_op("bltz", v4, v5, v4);
freeReg(registerState, v6);
break;
case 13:
m_compare_mips_op("bgez", v4, v5, v4);
freeReg(registerState, v6);
break;
case 14:
m_compare_mips_op("blez", v4, v5, v4);
freeReg(registerState, v6);
break;
default:
return v4;
}
return v4;
}

canonical_decompiled_code:
__int64 __fastcall func3(int a1, __int64 a2, __int64 a3)
{
unsigned int v4; // ebp
unsigned int v5; // eax
unsigned int v6; // er12

v4 = func1(a2);
v5 = func1(a3);
v6 = v5;
switch ( a1 )
{
case 0:
m_bin_op_to_r1("and", v4, v5);
freeReg(registerState, v6);
break;
case 1:
m_bin_op_to_r1("or", v4, v5);
freeReg(registerState, v6);
break;
case 4:
m_bin_op_to_r1("add", v4, v5);
freeReg(registerState, v6);
break;
case 5:
m_bin_op_to_r1("sub", v4, v5);
freeReg(registerState, v6);
break;
case 6:
m_mult_op(v4, v5, v4);
freeReg(registerState, v6);
break;
case 7:
m_divide_op(v4, v5, v4);
freeReg(registerState, v6);
break;
case 8:
m_modulo_op(v4, v5, v4);
freeReg(registerState, v6);
break;
case 9:
m_compare_mips_op("beq", v4, v5, v4);
freeReg(registerState, v6);
break;
case 10:
m_compare_mips_op("bne", v4, v5, v4);
freeReg(registerState, v6);
break;
case 11:
m_compare_mips_op("bgtz", v4, v5, v4);
freeReg(registerState, v6);
break;
case 12:
m_compare_mips_op("bltz", v4, v5, v4);
freeReg(registerState, v6);
break;
case 13:
m_compare_mips_op("bgez", v4, v5, v4);
freeReg(registerState, v6);
break;
case 14:
m_compare_mips_op("blez", v4, v5, v4);
freeReg(registerState, v6);
break;
default:
return v4;
}
return v4;
}

original_code:
int doBinaryOperator(openum op, expr* operand1, expr* operand2) {
    int reg1 = evalExpr(operand1);
    int reg2 = evalExpr(operand2);
    switch(op) {
        case op_and:
            m_bin_op_to_r1("and", reg1, reg2);
            freeReg(registerState, reg2);
            break;
        case op_or:
            m_bin_op_to_r1("or", reg1, reg2);
            freeReg(registerState, reg2);
            break;
        case op_add:
            m_bin_op_to_r1("add", reg1, reg2);
            freeReg(registerState, reg2);
            break;
        case op_sub:
            m_bin_op_to_r1("sub", reg1, reg2);
            freeReg(registerState, reg2);
            break;
        case op_mult:
            m_mult_op(reg1, reg2, reg1);
            freeReg(registerState, reg2);
            break;
        case op_div:
            m_divide_op(reg1, reg2, reg1);
            freeReg(registerState, reg2);
            break;
        case op_mod:
            m_modulo_op(reg1, reg2, reg1);
            freeReg(registerState, reg2);
            break;
        case op_equal:
            m_compare_mips_op("beq", reg1, reg2, reg1);
            freeReg(registerState, reg2);
            break;
        case op_nequal:
            m_compare_mips_op("bne", reg1, reg2, reg1);
            freeReg(registerState, reg2);
            break;
        case op_gt:
            m_compare_mips_op("bgtz", reg1, reg2, reg1);
            freeReg(registerState, reg2);
            break;
        case op_lt:
            m_compare_mips_op("bltz", reg1, reg2, reg1);
            freeReg(registerState, reg2);
            break;
        case op_gte:
            m_compare_mips_op("bgez", reg1, reg2, reg1);
            freeReg(registerState, reg2);
            break;
        case op_lte:
            m_compare_mips_op("blez", reg1, reg2, reg1);
            freeReg(registerState, reg2);
            break;
    }
    return reg1;
}

canonical_original_code:
int doBinaryOperator(enum operator_enum op, struct expression_struct *operand1, struct expression_struct *operand2) {
    int reg1 = evalExpr(operand1);
    int reg2 = evalExpr(operand2);
    switch(op) {
        case op_and:
            m_bin_op_to_r1("and", reg1, reg2);
            freeReg(registerState, reg2);
            break;
        case op_or:
            m_bin_op_to_r1("or", reg1, reg2);
            freeReg(registerState, reg2);
            break;
        case op_add:
            m_bin_op_to_r1("add", reg1, reg2);
            freeReg(registerState, reg2);
            break;
        case op_sub:
            m_bin_op_to_r1("sub", reg1, reg2);
            freeReg(registerState, reg2);
            break;
        case op_mult:
            m_mult_op(reg1, reg2, reg1);
            freeReg(registerState, reg2);
            break;
        case op_div:
            m_divide_op(reg1, reg2, reg1);
            freeReg(registerState, reg2);
            break;
        case op_mod:
            m_modulo_op(reg1, reg2, reg1);
            freeReg(registerState, reg2);
            break;
        case op_equal:
            m_compare_mips_op("beq", reg1, reg2, reg1);
            freeReg(registerState, reg2);
            break;
        case op_nequal:
            m_compare_mips_op("bne", reg1, reg2, reg1);
            freeReg(registerState, reg2);
            break;
        case op_gt:
            m_compare_mips_op("bgtz", reg1, reg2, reg1);
            freeReg(registerState, reg2);
            break;
        case op_lt:
            m_compare_mips_op("bltz", reg1, reg2, reg1);
            freeReg(registerState, reg2);
            break;
        case op_gte:
            m_compare_mips_op("bgez", reg1, reg2, reg1);
            freeReg(registerState, reg2);
            break;
        case op_lte:
            m_compare_mips_op("blez", reg1, reg2, reg1);
            freeReg(registerState, reg2);
            break;
    }
    return reg1;
}


decompiled_code:
__int64 __fastcall evalExpr_pointerUpdate(__int64 a1)
{
unsigned int v1; // ebx
__int64 v2; // rbp
_DWORD *v3; // rax

v1 = getReg(registerState);
m_load_frame_word(v1, *(unsigned int *)(*(_QWORD *)(a1 + 56) + 8LL), 0LL, 0LL, 0LL);
v2 = *(_QWORD *)(a1 + 40);
v3 = newRegExpr(v1, int_type);
return doBinaryOperator(4, (__int64)v3, v2);
}

canonical_decompiled_code:
__int64 __fastcall func4(__int64 a1)
{
unsigned int v1; // ebx
__int64 v2; // rbp
_DWORD *v3; // rax

v1 = getReg(registerState);
m_load_frame_word(v1, *(unsigned int *)(*(_QWORD *)(a1 + 56) + 8LL), 0LL, 0LL, 0LL);
v2 = *(_QWORD *)(a1 + 40);
v3 = newRegExpr(v1, int_type);
return func3(4, (__int64)v3, v2);
}

original_code:
int evalExpr_pointerUpdate(expr* e) {
    int ptrReg = getReg(registerState);
    int staticOffset = e->edata.id->id_addr;
    m_load_frame_word(ptrReg, staticOffset, 0, 0, 0);
    ptrReg = doBinaryOperator(op_add, newRegExpr(ptrReg, int_type), e->offsetExpr);
    return ptrReg;
}

canonical_original_code:
int evalExpr_pointerUpdate(struct expression_struct *e) {
    int ptrReg = getReg(registerState);
    int staticOffset = e->edata.id->id_addr;
    m_load_frame_word(ptrReg, staticOffset, 0, 0, 0);
    ptrReg = doBinaryOperator(op_add, newRegExpr(ptrReg, int_type), e->offsetExpr);
    return ptrReg;
}

variable_types: ptrReg int


getFPLabel

decompiled_code:
__int64 getFPLabel()
{
return (unsigned int)fplabelcounter++;
}

canonical_decompiled_code:
__int64 func0()
{
return (unsigned int)fplabelcounter++;
}

original_code:
int getFPLabel() {
    return fplabelcounter++;
}


decompiled_code:
_BOOL8 __fastcall typedidentlists_equalp(_QWORD *a1, _QWORD *a2)
{
_BOOL8 result; // rax
__int64 **v3; // rbx
__int64 **v4; // rbp
bool v5; // al
bool v6; // dl

result = 0LL;
if ( *a1 == *a2 )
{
v3 = (__int64 **)a1[2];
v4 = (__int64 **)a2[2];
v5 = v3 != 0LL;
v6 = v4 != 0LL;
if ( v3 && v4 )
{
while ( !strcmp((const char *)v3[1], (const char *)v4[1]) )
{
v3 = (__int64 **)*v3;
v4 = (__int64 **)*v4;
v5 = v3 != 0LL;
v6 = v4 != 0LL;
if ( !v3 || !v4 )
goto LABEL_7;
}
result = 0LL;
}
else
{
LABEL_7:
result = !v6 && !v5;
}
}
return result;
}

original_code:
int typedidentlists_equalp(typedidentlist* l, typedidentlist* r) {
    if (l->type != r->type) {
        return 0;
    }
    slist* nl = l->names;
    slist* nr = r->names;
    while(nl != ((void *)0) && nr != ((void *)0)) {
        if (strcmp(nl->data, nr->data)) {
            return 0;
        }
        nl = nl->next;
        nr = nr->next;
    }
    if (nl != ((void *)0) || nr != ((void *)0)) {
        return 0;
    }
    return 1;
}

canonical_original_code:
int typedidentlists_equalp(struct typedidentlist_struct *l, struct typedidentlist_struct *r) {
    if (l->type != r->type) {
        return 0;
    }
    struct slist_struct *nl = l->names;
    struct slist_struct *nr = r->names;
    while(nl != ((void *)0) && nr != ((void *)0)) {
        if (strcmp(nl->data, nr->data)) {
            return 0;
        }
        nl = nl->next;
        nr = nr->next;
    }
    if (nl != ((void *)0) || nr != ((void *)0)) {
        return 0;
    }
    return 1;
}

variable_types: struct typedidentlist_struct { struct type_info { int ty_size; char *ty_name; enum type_kind { Integer=0, Char=1, Boolean=2, String=3, Array=4, Record=5, UndefinedType=6 } ty_kind; struct type_info *ty_next; union { struct { struct type_info *RangeType; int min; int max; } ty_subrange; struct { struct type_info *ElementType; struct type_info *IndexType; int min; int max; } ty_array; struct { struct id_info { char *id_name; int id_addr; int id_label; int id_level; struct type_info *id_type; enum identifier_kind { Constant_id=0, Type=1, Variable=2, FParameter=3, Field=4, Procedure=5, Function=6 } id_kind; struct id_info *id_left; struct id_info *id_right; struct id_info *id_next; struct expression_struct { struct type_info *type; enum expr_kind_enum { constant_expr=0, operation_bin=1, operation_un=2, registerVal=3, globalVar=4, localVar=5, functionCall=6, typecast=7 } kind; int int_val; char char_val; int bool_val; char *str_val; int str_const_index; struct expression_struct *offsetExpr; int pointer_p; int to_pointer_p; union { struct { struct expression_struct *operand1; struct expression_struct *operand2; enum operator_enum { op_and=0, op_or=1, op_not=2, op_negate=3, op_add=4, op_sub=5, op_mult=6, op_div=7, op_mod=8, op_equal=9, op_nequal=10, op_gt=11, op_lt=12, op_gte=13, op_lte=14 } op; } opdata; int reg_number; struct id_info *id; struct stmt_struct { enum stmt_type_enum { assign_stmt=0, if_stmt=1, while_stmt=2, repeat_stmt=3, for_stmt=4, stop_stmt=5, return_stmt=6, read_stmt=7, write_stmt=8, proc_stmt=9, null_stmt=10 } type; union { struct htslist_struct { struct slist_struct { struct slist_struct *next; void *data; } *head; struct slist_struct *tail; } *if_conditionals; struct slist_struct *exprList; struct expression_struct *expression; struct { struct stmt_struct *init; struct conditional_struct { struct expression_struct *condition; enum BranchType_enum { bt_equal0=0, bt_nequal0=1 } branchType; struct htslist_struct *statements; } *cBlock; } loopdata; struct { struct expression_struct *lvalue; struct expression_struct *rvalue; } assigndata; struct { char *name; struct slist_struct *paramExprs; } procdata; } data; } *funcCall; struct expression_struct *innerExpr; } edata; } *const_expr; struct slist_struct *typedIdentLists; int param_size; int pointer_p; } *FirstField; } ty_record; } ty_form; } *type; int pointerP; struct slist_struct *names; } *

variable_types:
r
struct typedidentlist_struct *

user_defined_types: struct typedidentlist_struct { struct type_info *type; int pointerP; struct slist_struct *names; }


decompiled_code:
_BOOL8 __fastcall typedIdentList_list_equalp(__int64 **a1, __int64 **a2)
{
bool v2; // al
bool v3; // dl
__int64 **v4; // rbx
__int64 **v5; // rbp
_BOOL8 result; // rax

v2 = a1 != 0LL;
v3 = a2 != 0LL;
if ( !a1 )
return !v3 && !v2;
v4 = a1;
v5 = a2;
if ( !a2 )
return !v3 && !v2;
while ( 1 )
{
result = typedidentlists_equalp(v4[1], v5[1]);
if ( !result )
break;
v4 = (__int64 **)*v4;
v5 = (__int64 **)*v5;
v2 = v4 != 0LL;
v3 = v5 != 0LL;
if ( !v4 || !v5 )
return !v3 && !v2;
}
return result;
}

original_code:
int typedIdentList_list_equalp(slist* l, slist* r) {
    while(l != ((void *)0) && r != ((void *)0)) {
        if(!typedidentlists_equalp(l->data, r->data)) {
            return 0;
        }
        l = l->next;
        r = r->next;
    }
    if(l != ((void *)0) || r != ((void *)0)) {
        return 0;
    }
    return 1;
}

canonical_original_code:
int typedIdentList_list_equalp(struct slist_struct *l, struct slist_struct *r) {
    while(l != ((void *)0) && r != ((void *)0)) {
        if(!typedidentlists_equalp(l->data, r->data)) {
            return 0;
        }
        l = l->next;
        r = r->next;
    }
    if(l != ((void *)0) || r != ((void *)0)) {
        return 0;
    }
    return 1;
}

variable_types: struct slist_struct { struct slist_struct *next; void *data; } *

variable_types:
r
struct slist_struct *


decompiled_code:
__int64 __fastcall calcSize_typedIdentList_list(_QWORD *a1)
{
unsigned int v1; // edx
__int64 v2; // rax
int v3; // esi
int v4; // ecx
_QWORD *v5; // rax

if ( !a1 )
return 0;
v1 = 0;
do
{
v2 = a1[1];
v3 = *(_DWORD *)(v2 + 8);
v4 = **(_DWORD **)v2;
v5 = *(_QWORD **)(v2 + 16);
if ( v5 )
{
if ( v3 )
v4 = 4;
do
{
v1 += v4;
v5 = (_QWORD *)*v5;
}
while ( v5 );
}
a1 = (_QWORD *)*a1;
}
while ( a1 );
return v1;
}

canonical_decompiled_code:
__int64 __fastcall func3(_QWORD *a1)
{
unsigned int v1; // edx
__int64 v2; // rax
int v3; // esi
int v4; // ecx
_QWORD *v5; // rax

if ( !a1 )
return 0;
v1 = 0;
do
{
v2 = a1[1];
v3 = *(_DWORD *)(v2 + 8);
v4 = **(_DWORD **)v2;
v5 = *(_QWORD **)(v2 + 16);
if ( v5 )
{
if ( v3 )
v4 = 4;
do
{
v1 += v4;
v5 = (_QWORD *)*v5;
}
while ( v5 );
}
a1 = (_QWORD *)*a1;
}
while ( a1 );
return v1;
}

original_code:
int calcSize_typedIdentList_list(slist* params) {
    int size = 0;
    while (params != ((void *)0)) {
        typedidentlist* til = params->data;
        TYPE* ty = til->type;
        int pointerP = til->pointerP;
        int tysize = ty->ty_size;
        slist* names = til->names;
        while (names != ((void *)0)) {
            size += pointerP ? 4 : tysize;
            names = names->next;
        }
        params = params->next;
    }
    return size;
}

canonical_original_code:
int calcSize_typedIdentList_list(struct slist_struct *params) {
    int size = 0;
    while (params != ((void *)0)) {
        struct typedidentlist_struct *til = params->data;
        struct type_info *ty = til->type;
        int pointerP = til->pointerP;
        int tysize = ty->ty_size;
        struct slist_struct *names = til->names;
        while (names != ((void *)0)) {
            size += pointerP ? 4 : tysize;
            names = names->next;
        }
        params = params->next;
    }
    return size;
}

variable_types: size int

variable_types: pointerP int

variable_types: tysize int


declareFunc

decompiled_code:
__int64 __fastcall declareFunc(__int64 a1, __int64 **a2, __int64 a3, __int64 a4)
{
unsigned int v4; // er15
__int64 v7; // rax
int v8; // er14
__int64 v9; // rbx
__int64 result; // rax
int v11; // er12
int v12; // ebx
__int64 v13; // rbx

v7 = IDsearch(a1, *((_QWORD *)&scope + currscope - 1));
v8 = 5 - ((a4 == 0) - 1);
if ( v7 )
{
v9 = v7;
if ( *(_DWORD *)(v7 + 32) == v8 )
{
result = typedIdentList_list_equalp(*(__int64 ***)(v7 + 72), a2);
if ( (_DWORD)result )
v4 = *(_DWORD *)(v9 + 12);
else
result = yyerror("Formal parameters differ between function declarations");
}
else
{
result = yyerror("Identifier already defined");
}
}
else
{
v4 = getFPLabel();
v13 = newid(a1);
*(_DWORD *)(v13 + 32) = v8;
*(_QWORD *)(v13 + 24) = a4;
*(_QWORD *)(v13 + 72) = a2;
*(_DWORD *)(v13 + 12) = v4;
*(_DWORD *)(v13 + 80) = calcSize_typedIdentList_list(a2);
result = addIdToTable_noAddrMove(v13, (char *)&scope + 8 * currscope - 8);
}
if ( a3 )
{
m_add_function_label(v4);
v11 = calcSize_typedIdentList_list(a2);
v12 = getSizeOfScopeVars(*((_QWORD *)&scope + currscope));
m_move_stack_ptr((unsigned int)(v12 - v11));
m_set_fp_to_sp((unsigned int)-v12);
eval_stmt_list(a3);
result = m_function_end(v4);
}
return result;
}

canonical_decompiled_code:
__int64 __fastcall func4(__int64 a1, __int64 **a2, __int64 a3, __int64 a4)
{
unsigned int v4; // er15
__int64 v7; // rax
int v8; // er14
__int64 v9; // rbx
__int64 result; // rax
int v11; // er12
int v12; // ebx
__int64 v13; // rbx

v7 = IDsearch(a1, *((_QWORD *)&scope + currscope - 1));
v8 = 5 - ((a4 == 0) - 1);
if ( v7 )
{
v9 = v7;
if ( *(_DWORD *)(v7 + 32) == v8 )
{
result = func2(*(__int64 ***)(v7 + 72), a2);
if ( (_DWORD)result )
v4 = *(_DWORD *)(v9 + 12);
else
result = yyerror("Formal parameters differ between function declarations");
}
else
{
result = yyerror("Identifier already defined");
}
}
else
{
v4 = func0();
v13 = newid(a1);
*(_DWORD *)(v13 + 32) = v8;
*(_QWORD *)(v13 + 24) = a4;
*(_QWORD *)(v13 + 72) = a2;
*(_DWORD *)(v13 + 12) = v4;
*(_DWORD *)(v13 + 80) = func3(a2);
result = addIdToTable_noAddrMove(v13, (char *)&scope + 8 * currscope - 8);
}
if ( a3 )
{
m_add_function_label(v4);
v11 = func3(a2);
v12 = getSizeOfScopeVars(*((_QWORD *)&scope + currscope));
m_move_stack_ptr((unsigned int)(v12 - v11));
m_set_fp_to_sp((unsigned int)-v12);
eval_stmt_list(a3);
result = m_function_end(v4);
}
return result;
}

original_code:
void declareFunc(char* name, slist* params, htslist* body, TYPE* t) {
    ID* func = IDsearch(name, scope[currscope-1]);
    int flabel, predeclared = 0;
    ID_KIND funcproc = t == ((void *)0) ? Procedure : Function;
    if (func != ((void *)0)) {
        predeclared = 1;
        if (func->id_kind != funcproc) {
            yyerror("Identifier already defined");
        } else if (!typedIdentList_list_equalp(func->typedIdentLists, params)) {
            yyerror("Formal parameters differ between function declarations");
        } else {
            flabel = func->id_label;
        }
    } else {
        flabel = getFPLabel();
        func = newid(name);
        func->id_kind = funcproc;
        func->id_type = t;
        func->typedIdentLists = params;
        func->id_label = flabel;
        func->param_size = calcSize_typedIdentList_list(params);
        addIdToTable_noAddrMove(func, scope+(currscope-1));
    }
    if (body != ((void *)0)) {
        m_add_function_label(flabel);
        int paramSize = calcSize_typedIdentList_list(params);
        int fullScopeSize = getSizeOfScopeVars(scope[currscope]);
        int nonParamSize = fullScopeSize - paramSize;
        m_move_stack_ptr(nonParamSize);
        m_set_fp_to_sp(-fullScopeSize);
        eval_stmt_list(body);
        m_function_end(flabel);
    }
}

canonical_original_code:
void declareFunc(char *name, struct slist_struct *params, struct htslist_struct *body, struct type_info *t) {
    struct id_info *func = IDsearch(name, scope[currscope-1]);
    int flabel; int predeclared = 0;
    enum identifier_kind funcproc = t == ((void *)0) ? Procedure : Function;
    if (func != ((void *)0)) {
        predeclared = 1;
        if (func->id_kind != funcproc) {
            yyerror("Identifier already defined");
        } else if (!typedIdentList_list_equalp(func->typedIdentLists, params)) {
            yyerror("Formal parameters differ between function declarations");
        } else {
            flabel = func->id_label;
        }
    } else {
        flabel = getFPLabel();
        func = newid(name);
        func->id_kind = funcproc;
        func->id_type = t;
        func->typedIdentLists = params;
        func->id_label = flabel;
        func->param_size = calcSize_typedIdentList_list(params);
        addIdToTable_noAddrMove(func, scope+(currscope-1));
    }
    if (body != ((void *)0)) {
        m_add_function_label(flabel);
        int paramSize = calcSize_typedIdentList_list(params);
        int fullScopeSize = getSizeOfScopeVars(scope[currscope]);
        int nonParamSize = fullScopeSize - paramSize;
        m_move_stack_ptr(nonParamSize);
        m_set_fp_to_sp(-fullScopeSize);
        eval_stmt_list(body);
        m_function_end(flabel);
    }
}

variable_types:
name
char *

variable_types: struct htslist_struct { struct slist_struct *head; struct slist_struct *tail; } *

variable_types: struct type_info { int ty_size; char *ty_name; enum type_kind { Integer=0, Char=1, Boolean=2, String=3, Array=4, Record=5, UndefinedType=6 } ty_kind; struct type_info *ty_next; union { struct { struct type_info *RangeType; int min; int max; } ty_subrange; struct { struct type_info *ElementType; struct type_info *IndexType; int min; int max; } ty_array; struct { struct id_info { char *id_name; int id_addr; int id_label; int id_level; struct type_info *id_type; enum identifier_kind { Constant_id=0, Type=1, Variable=2, FParameter=3, Field=4, Procedure=5, Function=6 } id_kind; struct id_info *id_left; struct id_info *id_right; struct id_info *id_next; struct expression_struct { struct type_info *type; enum expr_kind_enum { constant_expr=0, operation_bin=1, operation_un=2, registerVal=3, globalVar=4, localVar=5, functionCall=6, typecast=7 } kind; int int_val; char char_val; int bool_val; char *str_val; int str_const_index; struct expression_struct *offsetExpr; int pointer_p; int to_pointer_p; union { struct { struct expression_struct *operand1; struct expression_struct *operand2; enum operator_enum { op_and=0, op_or=1, op_not=2, op_negate=3, op_add=4, op_sub=5, op_mult=6, op_div=7, op_mod=8, op_equal=9, op_nequal=10, op_gt=11, op_lt=12, op_gte=13, op_lte=14 } op; } opdata; int reg_number; struct id_info *id; struct stmt_struct { enum stmt_type_enum { assign_stmt=0, if_stmt=1, while_stmt=2, repeat_stmt=3, for_stmt=4, stop_stmt=5, return_stmt=6, read_stmt=7, write_stmt=8, proc_stmt=9, null_stmt=10 } type; union { struct htslist_struct *if_conditionals; struct slist_struct *exprList; struct expression_struct *expression; struct { struct stmt_struct *init; struct conditional_struct { struct expression_struct *condition; enum BranchType_enum { bt_equal0=0, bt_nequal0=1 } branchType; struct htslist_struct *statements; } *cBlock; } loopdata; struct { struct expression_struct *lvalue; struct expression_struct *rvalue; } assigndata; struct { char *name; struct slist_struct *paramExprs; } procdata; } data; } *funcCall; struct expression_struct *innerExpr; } edata; } *const_expr; struct slist_struct *typedIdentLists; int param_size; int pointer_p; } *FirstField; } ty_record; } ty_form; } *

variable_types: struct id_info { char *id_name; int id_addr; int id_label; int id_level; struct type_info { int ty_size; char *ty_name; enum type_kind { Integer=0, Char=1, Boolean=2, String=3, Array=4, Record=5, UndefinedType=6 } ty_kind; struct type_info *ty_next; union { struct { struct type_info *RangeType; int min; int max; } ty_subrange; struct { struct type_info *ElementType; struct type_info *IndexType; int min; int max; } ty_array; struct { struct id_info *FirstField; } ty_record; } ty_form; } *id_type; enum identifier_kind { Constant_id=0, Type=1, Variable=2, FParameter=3, Field=4, Procedure=5, Function=6 } id_kind; struct id_info *id_left; struct id_info *id_right; struct id_info *id_next; struct expression_struct { struct type_info *type; enum expr_kind_enum { constant_expr=0, operation_bin=1, operation_un=2, registerVal=3, globalVar=4, localVar=5, functionCall=6, typecast=7 } kind; int int_val; char char_val; int bool_val; char *str_val; int str_const_index; struct expression_struct *offsetExpr; int pointer_p; int to_pointer_p; union { struct { struct expression_struct *operand1; struct expression_struct *operand2; enum operator_enum { op_and=0, op_or=1, op_not=2, op_negate=3, op_add=4, op_sub=5, op_mult=6, op_div=7, op_mod=8, op_equal=9, op_nequal=10, op_gt=11, op_lt=12, op_gte=13, op_lte=14 } op; } opdata; int reg_number; struct id_info *id; struct stmt_struct { enum stmt_type_enum { assign_stmt=0, if_stmt=1, while_stmt=2, repeat_stmt=3, for_stmt=4, stop_stmt=5, return_stmt=6, read_stmt=7, write_stmt=8, proc_stmt=9, null_stmt=10 } type; union { struct htslist_struct { struct slist_struct { struct slist_struct *next; void *data; } *head; struct slist_struct *tail; } *if_conditionals; struct slist_struct *exprList; struct expression_struct *expression; struct { struct stmt_struct *init; struct conditional_struct { struct expression_struct *condition; enum BranchType_enum { bt_equal0=0, bt_nequal0=1 } branchType; struct htslist_struct *statements; } *cBlock; } loopdata; struct { struct expression_struct *lvalue; struct expression_struct *rvalue; } assigndata; struct { char *name; struct slist_struct *paramExprs; } procdata; } data; } *funcCall; struct expression_struct *innerExpr; } edata; } *const_expr; struct slist_struct *typedIdentLists; int param_size; int pointer_p; } *

variable_types: flabel int

variable_types: predeclared int

variable_types: paramSize int

variable_types: fullScopeSize int

variable_types: nonParamSize int