// File: yanlinlin82[P]icpp/icpp.cpp
// Function: print_vm_env(int, int, int, int)
void print_vm_env(int ax, int ip, int sp, int bp)
{
	log("\tax = %08X, ip = %08X, sp = %08X, bp = %08X\n", ax, ip, sp, bp);
	log("\t[stack]: ");
	size_t i = 0;
	for (; i < 6 && sp + i < MEM_SIZE; ++i) {
		if (i > 0) { log(", "); }
		log("0x%08X", m[sp + i]);
	}
	if (sp + i < MEM_SIZE) {
		log(", ...");
	}
	log("\n");
	for (size_t i = 0; i < 10 && bp != MEM_SIZE; ++i) {
		log("\t[#%zd backtrace]: bp = %08X", i, bp);
		if (bp == m[bp]) break;
		log("\tm[bp] = %08X", m[bp]);
		log("\tm[bp+1] = %08X", m[bp+1]);
		log("\tm[bp+2] = %08X", m[bp+2]);
		log("\tm[bp+3] = %08X", m[bp+3]);
		log("\tm[bp+4] = %08X", m[bp+4]);
		bp = m[bp];
		log("\n");
	}
	if (i == 10) {
		log("...\n");
	}
	log("\n");
	return;
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
subq $0x30, %rsp
movl %edi, -0x4(%rbp)
movl %esi, -0x8(%rbp)
movl %edx, -0xc(%rbp)
movl %ecx, -0x10(%rbp)
movl -0x4(%rbp), %esi
movl -0x8(%rbp), %edx
movl -0xc(%rbp), %ecx
movl -0x10(%rbp), %r8d
leaq 0x213ac(%rip), %rdi     # 0x38064
movb $0x0, %al
callq 0x19420
leaq 0x213cb(%rip), %rdi     # 0x38091
movb $0x0, %al
callq 0x19420
movq $0x0, -0x18(%rbp)
xorl %eax, %eax
cmpq $0x6, -0x18(%rbp)
movb %al, -0x21(%rbp)
jae 0x16cf5
movslq -0xc(%rbp), %rax
addq -0x18(%rbp), %rax
cmpq $0x100000, %rax         # imm = 0x100000
setb %al
movb %al, -0x21(%rbp)
movb -0x21(%rbp), %al
testb $0x1, %al
jne 0x16cfe
jmp 0x16d45
cmpq $0x0, -0x18(%rbp)
jbe 0x16d13
leaq 0x20486(%rip), %rdi     # 0x37192
movb $0x0, %al
callq 0x19420
movslq -0xc(%rbp), %rsi
addq -0x18(%rbp), %rsi
leaq 0x3977e(%rip), %rdi     # 0x504a0
callq 0x19cf0
movl (%rax), %esi
leaq 0x2131a(%rip), %rdi     # 0x3804a
movb $0x0, %al
callq 0x19420
movq -0x18(%rbp), %rax
addq $0x1, %rax
movq %rax, -0x18(%rbp)
jmp 0x16cd5
movslq -0xc(%rbp), %rax
addq -0x18(%rbp), %rax
cmpq $0x100000, %rax         # imm = 0x100000
jae 0x16d63
leaq 0x21340(%rip), %rdi     # 0x3809c
movb $0x0, %al
callq 0x19420
leaq 0x214eb(%rip), %rdi     # 0x38255
movb $0x0, %al
callq 0x19420
movq $0x0, -0x20(%rbp)
xorl %eax, %eax
cmpq $0xa, -0x20(%rbp)
movb %al, -0x22(%rbp)
jae 0x16d92
cmpl $0x100000, -0x10(%rbp)  # imm = 0x100000
setne %al
movb %al, -0x22(%rbp)
movb -0x22(%rbp), %al
testb $0x1, %al
jne 0x16d9e
jmp 0x16ec0
movq -0x20(%rbp), %rsi
movl -0x10(%rbp), %edx
leaq 0x212f6(%rip), %rdi     # 0x380a2
movb $0x0, %al
callq 0x19420
movl -0x10(%rbp), %eax
movl %eax, -0x28(%rbp)
movslq -0x10(%rbp), %rsi
leaq 0x396dc(%rip), %rdi     # 0x504a0
callq 0x19cf0
movq %rax, %rcx
movl -0x28(%rbp), %eax
cmpl (%rcx), %eax
jne 0x16dd8
jmp 0x16ec0
movslq -0x10(%rbp), %rsi
leaq 0x396bd(%rip), %rdi     # 0x504a0
callq 0x19cf0
movl (%rax), %esi
leaq 0x212ce(%rip), %rdi     # 0x380bf
movb $0x0, %al
callq 0x19420
movl -0x10(%rbp), %eax
addl $0x1, %eax
movslq %eax, %rsi
leaq 0x39698(%rip), %rdi     # 0x504a0
callq 0x19cf0
movl (%rax), %esi
leaq 0x212b7(%rip), %rdi     # 0x380cd
movb $0x0, %al
callq 0x19420
movl -0x10(%rbp), %eax
addl $0x2, %eax
movslq %eax, %rsi
leaq 0x39673(%rip), %rdi     # 0x504a0
callq 0x19cf0
movl (%rax), %esi
leaq 0x212a2(%rip), %rdi     # 0x380dd
movb $0x0, %al
callq 0x19420
movl -0x10(%rbp), %eax
addl $0x3, %eax
movslq %eax, %rsi
leaq 0x3964e(%rip), %rdi     # 0x504a0
callq 0x19cf0
movl (%rax), %esi
leaq 0x2128d(%rip), %rdi     # 0x380ed
movb $0x0, %al
callq 0x19420
movl -0x10(%rbp), %eax
addl $0x4, %eax
movslq %eax, %rsi
leaq 0x39629(%rip), %rdi     # 0x504a0
callq 0x19cf0
movl (%rax), %esi
leaq 0x21278(%rip), %rdi     # 0x380fd
movb $0x0, %al
callq 0x19420
movslq -0x10(%rbp), %rsi
leaq 0x39609(%rip), %rdi     # 0x504a0
callq 0x19cf0
movl (%rax), %eax
movl %eax, -0x10(%rbp)
leaq 0x213ad(%rip), %rdi     # 0x38255
movb $0x0, %al
callq 0x19420
movq -0x20(%rbp), %rax
addq $0x1, %rax
movq %rax, -0x20(%rbp)
jmp 0x16d79
cmpq $0xa, -0x18(%rbp)
jne 0x16ed5
leaq 0x2155c(%rip), %rdi     # 0x3842a
movb $0x0, %al
callq 0x19420
leaq 0x21379(%rip), %rdi     # 0x38255
movb $0x0, %al
callq 0x19420
addq $0x30, %rsp
popq %rbp
retq
nopl (%rax)