// File: /workspace/github_c_makefile_star2_O1/Gaurang18[P]Compiler-Project-BITS-Pilani/./codegen.c
// Function: GenerateCodeStmts
void GenerateCodeStmts(FILE *fpdummy, parsetree head, FILE *fp, char *scope){

	if(head==NULL)
		return;

	if(head->value== 4)
		strcpy(scope, "driver");

	if(head->value==106 && head->parent->value==7)
		strcpy(scope, head->Lex->tk->value);

	switch(head->value){

		case 22:

		if(head->generated!=1){

				if(head->rule==40){

				expstate = 0;
				fprintf(fp,".while%d:\n",whilenum);
				ExpressionCode(fpdummy,head->child->right,fp,scope);
				fprintf(fp,"pop eax\ncmp eax,0000h\nje .endwhile%d\n", whilenum);

				GenerateCodeStmts(fpdummy,head->child->right->right->right, fp, scope);
				fprintf(fp,"jmp .while%d\n", whilenum);
				fprintf(fp,".endwhile%d:\n", whilenum);
				whilenum++;
			


			}

			if(head->rule==39){

				expstate = 0;
				fprintf(fp, ".for%d\n", fornum);
				parsetree id = head->child->right;

				fprintf(fp,"push dword[%s]\n",id->Lex->tk->value);
				fprintf(fp, "pop eax\n");
				// printf("%s\n", id->right->Lex->tk->value);
				// printf("%s\n", id->right->right->child->right->right->Lex->tk->value);

				int start = atoi(id->right->right->child->Lex->tk->value);
				int end = atoi(id->right->right->child->right->right->Lex->tk->value);
				// assert(0);
				fprintf(fp, "mov ecx, %d\n", start);
				fprintf(fp, "cmp eax, ecx\n");
				fprintf(fp, "jl .endfor%d\n", fornum);
				fprintf(fp, "mov ecx, %d\n", end);
				fprintf(fp, "cmp eax, ecx\n");
				fprintf(fp, "jg .endfor%d\n", fornum);
				GenerateCodeStmts(fpdummy,head->child->right->right->right->right, fp, scope);
				fprintf(fp,"jmp .for%d\n", fornum);
				fprintf(fp,".endfor%d:\n", fornum);
				fornum++;





			}

			

		}	head->generated = 1;

			break;
		case 18:
			if(head->generated!=1){
			if(head->child->value==63)
				 {
			fprintf(fp,"\n\tpush %s\n\tcall printf\n",head->child->right->Lex->tk->value);
			//fprintf(fp,"\n\tmov edi, numberout_form\n\tmov esi,[%s]\n\tmov al, 0\n\tcall printf\n",head->child->right->Lex->tk->value);
				 		

				 }			 				 
				 	// else
				 	// fprintf(fp,"call _UserInput\nmov dword[%s.%s], eax\n",stmt->children[1]->children[0]->str,stmt->children[1]->children[1]->str );
				 
			else
				 {	
				 	if(!(head->child->right->rule==41 && head->child->right->child->right->rule==44)){
				 		if(head->child->right->rule==41)
		fprintf(fp,"\n\tpush %s\n\tpush numberin_form\n\tcall scanf\n",head->child->right->child->Lex->tk->value);
				 		else
				 		{
		fprintf(fp,"\n\tpush %s\n\tpush numberin_form\n\tcall scanf\n",head->child->right->child->Lex->tk->value);
				 		}

				 	}	
				 }}

				 head->generated = 1;
				 break;

	}


	GenerateCodeStmts(fpdummy,head->child, fp, scope);

	switch(head->value){

		case 4: strcpy(scope, "driver");
				// assert(0);
				break;

		case 106: if(head->parent->value==7)
        			{
            			strcpy(scope, head->Lex->tk->value);
        			}				

        		break;

		case 100: 



			if(head->generated!=1){

			if(head->parent->value==28){

				parsetree id = head->parent->parent->parent->child;

				// printf("%s %s\n", id->Lex->tk->value, scope);

				int type = TypeChecker(fpdummy,id, scope);
				 // printf("%d\n", type);
				if(type==0){
					// assert(0);
					ExpressionCode(fpdummy,head->right, fp, scope);
					
					fprintf(fp,"pop eax\nmov dword[%s],eax\n",id->Lex->tk->value);
					//assert(0);

				}

				head->generated = 1;

				}


			}

			

			break;

		


	}



	GenerateCodeStmts(fpdummy,head->right, fp, scope);




}

// Assembly:
pushq %rbp
movq %rsp, %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x18, %rsp
movq %rcx, %rbx
movq %rdx, %r14
movq %rsi, %r15
movq %rdi, %r13
movq %rdi, -0x30(%rbp)
testq %r15, %r15
je 0x7b17
cmpl $0x4, 0x8(%r15)
jne 0x776d
movl $0x726576, 0x3(%rbx)    # imm = 0x726576
movl $0x76697264, (%rbx)     # imm = 0x76697264
cmpl $0x6a, 0x8(%r15)
jne 0x7790
movq 0x30(%r15), %rax
cmpl $0x7, 0x8(%rax)
jne 0x7790
movq (%r15), %rax
movq (%rax), %rsi
addq $0x1e, %rsi
movq %rbx, %rdi
callq 0x2060
movl 0x8(%r15), %eax
cmpl $0x12, %eax
je 0x79e6
cmpl $0x16, %eax
jne 0x7a43
leaq 0x10(%r15), %r12
cmpl $0x1, 0x10(%r15)
je 0x7a3b
cmpl $0x28, 0xc(%r15)
jne 0x7860
movl $0x0, 0x18706(%rip)     # 0x1fed0
movl 0x18708(%rip), %edx     # 0x1fed8
movq %r14, %rdi
leaq 0x2beb(%rip), %rsi      # 0xa3c5
xorl %eax, %eax
callq 0x2130
movq 0x18(%r15), %rax
movq 0x28(%rax), %rsi
movq %r13, %rdi
movq %r14, %rdx
movq %rbx, %rcx
callq 0x6d10
movl 0x186db(%rip), %edx     # 0x1fed8
movq %r14, %rdi
leaq 0x2bc9(%rip), %rsi      # 0xa3d0
xorl %eax, %eax
callq 0x2130
movq 0x18(%r15), %rax
movq 0x28(%rax), %rax
movq 0x28(%rax), %rax
movq 0x28(%rax), %rsi
movq %r13, %rdi
movq %r14, %rdx
movq %rbx, %rcx
callq 0x772f
movl 0x186a6(%rip), %edx     # 0x1fed8
movq %r14, %rdi
leaq 0x2bba(%rip), %rsi      # 0xa3f6
xorl %eax, %eax
callq 0x2130
movl 0x1868f(%rip), %edx     # 0x1fed8
movq %r14, %rdi
leaq 0x2bb1(%rip), %rsi      # 0xa404
xorl %eax, %eax
callq 0x2130
incl 0x18678(%rip)           # 0x1fed8
cmpl $0x27, 0xc(%r15)
jne 0x7a3b
movl $0x0, 0x1865b(%rip)     # 0x1fed0
movl 0x18669(%rip), %edx     # 0x1fee4
movq %r14, %rdi
leaq 0x2bd1(%rip), %rsi      # 0xa456
xorl %eax, %eax
callq 0x2130
movq 0x18(%r15), %rax
movq 0x28(%rax), %r13
movq (%r13), %rax
movq (%rax), %rdx
addq $0x1e, %rdx
movq %r14, %rdi
leaq 0x281c(%rip), %rsi      # 0xa0c5
xorl %eax, %eax
callq 0x2130
movl $0x8, %esi
movl $0x1, %edx
leaq 0x2b51(%rip), %rdi      # 0xa412
movq %r14, %rcx
callq 0x21d0
movq 0x28(%r13), %rax
movq 0x28(%rax), %rax
movq 0x18(%rax), %r13
movq (%r13), %rax
movq (%rax), %rdi
addq $0x1e, %rdi
callq 0x2190
movl %eax, -0x34(%rbp)
movq 0x28(%r13), %rax
movq -0x30(%rbp), %r13
movq 0x28(%rax), %rax
movq (%rax), %rax
movq (%rax), %rdi
addq $0x1e, %rdi
callq 0x2190
movl %eax, -0x38(%rbp)
movq %r14, %rdi
leaq 0x2b0b(%rip), %rsi      # 0xa41b
movl -0x34(%rbp), %edx
xorl %eax, %eax
callq 0x2130
movl $0xd, %esi
movl $0x1, %edx
leaq 0x2afd(%rip), %rdi      # 0xa428
movq %r14, %rcx
callq 0x21d0
movl 0x185ab(%rip), %edx     # 0x1fee4
movq %r14, %rdi
leaq 0x2af3(%rip), %rsi      # 0xa436
xorl %eax, %eax
callq 0x2130
movq %r14, %rdi
leaq 0x2ac7(%rip), %rsi      # 0xa41b
movl -0x38(%rbp), %edx
xorl %eax, %eax
callq 0x2130
movl $0xd, %esi
movl $0x1, %edx
leaq 0x2ab9(%rip), %rdi      # 0xa428
movq %r14, %rcx
callq 0x21d0
movl 0x18567(%rip), %edx     # 0x1fee4
movq %r14, %rdi
leaq 0x2abd(%rip), %rsi      # 0xa444
xorl %eax, %eax
callq 0x2130
movq 0x18(%r15), %rax
movq 0x28(%rax), %rax
movq 0x28(%rax), %rax
movq 0x28(%rax), %rax
movq 0x28(%rax), %rsi
movq %r13, %rdi
movq %r14, %rdx
movq %rbx, %rcx
callq 0x772f
movl 0x1852e(%rip), %edx     # 0x1fee4
movq %r14, %rdi
leaq 0x2a92(%rip), %rsi      # 0xa452
xorl %eax, %eax
callq 0x2130
movl 0x18517(%rip), %edx     # 0x1fee4
movq %r14, %rdi
leaq 0x2a87(%rip), %rsi      # 0xa45e
xorl %eax, %eax
callq 0x2130
incl 0x18500(%rip)           # 0x1fee4
jmp 0x7a3b
leaq 0x10(%r15), %r12
cmpl $0x1, 0x10(%r15)
je 0x7a3b
movq 0x18(%r15), %rax
cmpl $0x3f, 0x8(%rax)
movq 0x28(%rax), %rax
jne 0x7a08
leaq 0x2a64(%rip), %rsi      # 0xa46a
jmp 0x7a27
cmpl $0x29, 0xc(%rax)
jne 0x7a1c
movq 0x18(%rax), %rcx
movq 0x28(%rcx), %rcx
cmpl $0x2c, 0xc(%rcx)
je 0x7a3b
movq 0x18(%rax), %rax
leaq 0x2a5b(%rip), %rsi      # 0xa482
movq (%rax), %rax
movq (%rax), %rdx
addq $0x1e, %rdx
movq %r14, %rdi
xorl %eax, %eax
callq 0x2130
movl $0x1, (%r12)
movq 0x18(%r15), %rsi
movq %r13, %rdi
movq %r14, %rdx
movq %rbx, %rcx
callq 0x772f
movl 0x8(%r15), %eax
cmpl $0x6a, %eax
je 0x7af2
cmpl $0x64, %eax
je 0x7a82
cmpl $0x4, %eax
jne 0x7b0e
movl $0x726576, 0x3(%rbx)    # imm = 0x726576
movl $0x76697264, (%rbx)     # imm = 0x76697264
jmp 0x7b0e
cmpl $0x1, 0x10(%r15)
je 0x7b0e
movq 0x30(%r15), %rax
cmpl $0x1c, 0x8(%rax)
jne 0x7b0e
movq 0x30(%rax), %rax
movq 0x30(%rax), %rax
movq %r13, %rdi
movq 0x18(%rax), %r13
movq %r13, %rsi
movq %rbx, %rdx
callq 0x5427
testl %eax, %eax
jne 0x7ae4
movq 0x28(%r15), %rsi
movq -0x30(%rbp), %rdi
movq %r14, %rdx
movq %rbx, %rcx
callq 0x6d10
movq (%r13), %rax
movq (%rax), %rdx
addq $0x1e, %rdx
movq %r14, %rdi
leaq 0x29d0(%rip), %rsi      # 0xa4ad
xorl %eax, %eax
callq 0x2130
movl $0x1, 0x10(%r15)
movq -0x30(%rbp), %r13
jmp 0x7b0e
movq 0x30(%r15), %rax
cmpl $0x7, 0x8(%rax)
jne 0x7b0e
movq (%r15), %rax
movq (%rax), %rsi
addq $0x1e, %rsi
movq %rbx, %rdi
callq 0x2060
movq 0x28(%r15), %r15
jmp 0x7750
addq $0x18, %rsp
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq