// File: /workspace/github_c_makefile_star2_O0/Yamsman[P]scc/src/gen.c
// Function: gen_fdef
void gen_fdef(asm_f *f, ast_n *n) {
	//Make label
	symbol *fsym = n->dat.decl.sym;
	char *fnc_name = fsym->name;
	asmf_add_inst(f, mk_label(fnc_name));
	f->fsym = fsym;

	//Function preamble
	asmf_add_inst(f, mk_inst(INST_PUSH, 1,
		mk_oprd(OPRD_REG, RBP)
	));
	asmf_add_inst(f, mk_inst(INST_MOV, 2,
		mk_oprd(OPRD_REG, RBP),	
		mk_oprd(OPRD_REG, RSP)
	));

	//Calculate local variable area size
	int vsize = 0;
	for (int i=0; i<fsym->lvars.len; i++) {
		symbol *var = fsym->lvars.table[i];
		vsize += type_sizeof(var->type);
	}
	if (vsize > 0) {
		asmf_add_inst(f, mk_inst(INST_SUB, 2,
			mk_oprd(OPRD_REG, RSP),
			mk_oprd(OPRD_IMM, vsize)
		));
	}

	//Function body
	gen_stmt_cmpd(f, n->dat.decl.block);

	//Function end
	//Only generate a return statemnt if one isn't present
	if (f->text_cur->op != INST_RET) {
		//Only 'main' has a defined return value of zero
		//if no return statement is present
		if (!strcmp(fsym->name, "main")) {
			asmf_add_inst(f, mk_inst(INST_MOV, 2,
				mk_oprd(OPRD_REG, RAX),
				mk_oprd(OPRD_IMM, 0)
			));
		}

		asmf_add_inst(f, mk_inst(INST_LEAVE, 0));
		asmf_add_inst(f, mk_inst(INST_RET, 0));
	}
	f->fsym = NULL;
	return;
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
subq $0x190, %rsp            # imm = 0x190
movq %rdi, -0x8(%rbp)
movq %rsi, -0x10(%rbp)
movq -0x10(%rbp), %rax
movq 0x10(%rax), %rax
movq %rax, -0x18(%rbp)
movq -0x18(%rbp), %rax
movq (%rax), %rax
movq %rax, -0x20(%rbp)
movq -0x8(%rbp), %rax
movq %rax, -0x128(%rbp)
movq -0x20(%rbp), %rdi
callq 0x65a0
movq -0x128(%rbp), %rdi
movq %rax, %rsi
callq 0x68f0
movq -0x18(%rbp), %rcx
movq -0x8(%rbp), %rax
movq %rcx, 0x20(%rax)
movq -0x8(%rbp), %rax
movq %rax, -0x120(%rbp)
leaq -0x40(%rbp), %rdi
xorl %esi, %esi
movl $0x17, %edx
callq 0x63c0
movl $0x36, %edi
movl $0x1, %esi
leaq -0x40(%rbp), %rax
movq (%rax), %rcx
movq %rcx, (%rsp)
movq 0x8(%rax), %rcx
movq %rcx, 0x8(%rsp)
movq 0x10(%rax), %rcx
movq %rcx, 0x10(%rsp)
movq 0x18(%rax), %rax
movq %rax, 0x18(%rsp)
movb $0x0, %al
callq 0x6460
movq -0x120(%rbp), %rdi
movq %rax, %rsi
callq 0x68f0
movq -0x8(%rbp), %rax
movq %rax, -0x118(%rbp)
leaq -0x60(%rbp), %rdi
xorl %esi, %esi
movl $0x17, %edx
callq 0x63c0
leaq -0x80(%rbp), %rdi
xorl %esi, %esi
movl $0x14, %edx
callq 0x63c0
movl $0x3e, %edi
movl $0x2, %esi
leaq -0x60(%rbp), %rcx
leaq -0x80(%rbp), %rax
movq (%rcx), %rdx
movq %rdx, (%rsp)
movq 0x8(%rcx), %rdx
movq %rdx, 0x8(%rsp)
movq 0x10(%rcx), %rdx
movq %rdx, 0x10(%rsp)
movq 0x18(%rcx), %rcx
movq %rcx, 0x18(%rsp)
movq (%rax), %rcx
movq %rcx, 0x20(%rsp)
movq 0x8(%rax), %rcx
movq %rcx, 0x28(%rsp)
movq 0x10(%rax), %rcx
movq %rcx, 0x30(%rsp)
movq 0x18(%rax), %rax
movq %rax, 0x38(%rsp)
movb $0x0, %al
callq 0x6460
movq -0x118(%rbp), %rdi
movq %rax, %rsi
callq 0x68f0
movl $0x0, -0x84(%rbp)
movl $0x0, -0x88(%rbp)
movl -0x88(%rbp), %eax
movq -0x18(%rbp), %rcx
cmpl 0x28(%rcx), %eax
jge 0x614c
movq -0x18(%rbp), %rax
movq 0x20(%rax), %rax
movslq -0x88(%rbp), %rcx
movq (%rax,%rcx,8), %rax
movq %rax, -0x90(%rbp)
movq -0x90(%rbp), %rax
movq 0x8(%rax), %rdi
callq 0x100a0
addl -0x84(%rbp), %eax
movl %eax, -0x84(%rbp)
movl -0x88(%rbp), %eax
addl $0x1, %eax
movl %eax, -0x88(%rbp)
jmp 0x60f6
cmpl $0x0, -0x84(%rbp)
jle 0x6201
movq -0x8(%rbp), %rax
movq %rax, -0x130(%rbp)
leaq -0xb0(%rbp), %rdi
xorl %esi, %esi
movl $0x14, %edx
callq 0x63c0
movl -0x84(%rbp), %edx
leaq -0xd0(%rbp), %rdi
movl $0x1, %esi
callq 0x63c0
movl $0x33, %edi
movl $0x2, %esi
leaq -0xb0(%rbp), %rcx
leaq -0xd0(%rbp), %rax
movq (%rcx), %rdx
movq %rdx, (%rsp)
movq 0x8(%rcx), %rdx
movq %rdx, 0x8(%rsp)
movq 0x10(%rcx), %rdx
movq %rdx, 0x10(%rsp)
movq 0x18(%rcx), %rcx
movq %rcx, 0x18(%rsp)
movq (%rax), %rcx
movq %rcx, 0x20(%rsp)
movq 0x8(%rax), %rcx
movq %rcx, 0x28(%rsp)
movq 0x10(%rax), %rcx
movq %rcx, 0x30(%rsp)
movq 0x18(%rax), %rax
movq %rax, 0x38(%rsp)
movb $0x0, %al
callq 0x6460
movq -0x130(%rbp), %rdi
movq %rax, %rsi
callq 0x68f0
movq -0x8(%rbp), %rdi
movq -0x10(%rbp), %rax
movq 0x20(%rax), %rsi
callq 0x54d0
movq -0x8(%rbp), %rax
movq 0x8(%rax), %rax
cmpl $0x41, (%rax)
je 0x6330
movq -0x18(%rbp), %rax
movq (%rax), %rdi
leaq 0xb458(%rip), %rsi      # 0x11689
callq 0x3120
cmpl $0x0, %eax
jne 0x62e0
movq -0x8(%rbp), %rax
movq %rax, -0x138(%rbp)
leaq -0xf0(%rbp), %rdi
xorl %edx, %edx
movl %edx, %esi
callq 0x63c0
leaq -0x110(%rbp), %rdi
movl $0x1, %esi
xorl %edx, %edx
callq 0x63c0
movl $0x3e, %edi
movl $0x2, %esi
leaq -0xf0(%rbp), %rcx
leaq -0x110(%rbp), %rax
movq (%rcx), %rdx
movq %rdx, (%rsp)
movq 0x8(%rcx), %rdx
movq %rdx, 0x8(%rsp)
movq 0x10(%rcx), %rdx
movq %rdx, 0x10(%rsp)
movq 0x18(%rcx), %rcx
movq %rcx, 0x18(%rsp)
movq (%rax), %rcx
movq %rcx, 0x20(%rsp)
movq 0x8(%rax), %rcx
movq %rcx, 0x28(%rsp)
movq 0x10(%rax), %rcx
movq %rcx, 0x30(%rsp)
movq 0x18(%rax), %rax
movq %rax, 0x38(%rsp)
movb $0x0, %al
callq 0x6460
movq -0x138(%rbp), %rdi
movq %rax, %rsi
callq 0x68f0
movq -0x8(%rbp), %rax
movq %rax, -0x148(%rbp)
movl $0x42, %edi
xorl %esi, %esi
movb $0x0, %al
callq 0x6460
movq -0x148(%rbp), %rdi
movq %rax, %rsi
callq 0x68f0
movq -0x8(%rbp), %rax
movq %rax, -0x140(%rbp)
movl $0x41, %edi
xorl %esi, %esi
movb $0x0, %al
callq 0x6460
movq -0x140(%rbp), %rdi
movq %rax, %rsi
callq 0x68f0
movq -0x8(%rbp), %rax
movq $0x0, 0x20(%rax)
addq $0x190, %rsp            # imm = 0x190
popq %rbp
retq
nopw %cs:(%rax,%rax)