// File: /workspace/github_c_makefile_star2_O0/jiribenes[P]scheme/src/core.c
// Function: builtin_let
static value_t builtin_let(vm_t *vm, env_t *env, value_t args) {
    // (let ((a 10) (b 20) ...) <exprs...>)
    arity_check(vm, "let", args, 2, true);
    value_t bindings = AS_CONS(args)->car;
    if (!IS_CONS(bindings) && !IS_NIL(bindings)) {
        error_runtime(vm, "let: bindings (first argument) must be a list!");
        return UNDEFINED_VAL;
    }

    value_t vars = NIL_VAL;
    value_t vals = NIL_VAL;
    if (!IS_NIL(bindings)) {
        value_t binding, iter;
        SCM_FOREACH (binding, AS_CONS(bindings), iter) {
            if (!IS_CONS(binding) || cons_len(binding) != 2) {
                error_runtime(vm,
                              "let: binding is not of type (variable value)!");
                return UNDEFINED_VAL;
            }
            value_t var = AS_CONS(binding)->car;
            value_t val = AS_CONS(AS_CONS(binding)->cdr)->car;
            if (!IS_SYMBOL(var)) {
                error_runtime(vm,
                              "let: left side of the binding is not a symbol!");
                return UNDEFINED_VAL;
            }
            value_t temp = cons_fn(vm, var, vars);
            vars = temp;

            value_t val_eval = eval(vm, env, val);

            // If value in binding is an unnamed function,
            // set it's name to var in binding
            if (IS_FUNCTION(val_eval)) {
                function_t *func = AS_FUNCTION(val_eval);
                symbol_t *sym = AS_SYMBOL(var);
                if (func->name == NULL) {
                    func->name = sym;
                }
            }
            temp = cons_fn(vm, val_eval, vals);
            vals = temp;
        }
    }

    env_t *new_env = env_push(vm, env, vars, vals);
    value_t body = AS_CONS(args)->cdr;
    return begin(vm, new_env, body);
}

// Assembly:
subq $0x88, %rsp
movq %rdi, 0x78(%rsp)
movq %rsi, 0x70(%rsp)
movq %rdx, 0x68(%rsp)
movq 0x78(%rsp), %rdi
movq 0x68(%rsp), %rdx
leaq 0x6cd4(%rip), %rsi      # 0xa13b
movl $0x2, %ecx
movl $0x1, %r8d
callq 0x12a0
movabsq $0x3ffffffffffff, %rax  # imm = 0x3FFFFFFFFFFFF
andq 0x68(%rsp), %rax
movq 0x10(%rax), %rax
movq %rax, 0x60(%rsp)
movq 0x60(%rsp), %rdi
xorl %esi, %esi
callq 0x4d50
testb $0x1, %al
jne 0x34da
movabsq $0x7ffc000000000001, %rax # imm = 0x7FFC000000000001
cmpq %rax, 0x60(%rsp)
je 0x34da
movq 0x78(%rsp), %rdi
leaq 0x6f34(%rip), %rsi      # 0xa3f0
movb $0x0, %al
callq 0x73a0
movabsq $0x7ffc000000000004, %rax # imm = 0x7FFC000000000004
movq %rax, 0x80(%rsp)
jmp 0x3755
movabsq $0x7ffc000000000001, %rax # imm = 0x7FFC000000000001
movq %rax, 0x58(%rsp)
movabsq $0x7ffc000000000001, %rax # imm = 0x7FFC000000000001
movq %rax, 0x50(%rsp)
movabsq $0x7ffc000000000001, %rax # imm = 0x7FFC000000000001
cmpq %rax, 0x60(%rsp)
je 0x3705
movabsq $0x3ffffffffffff, %rdi  # imm = 0x3FFFFFFFFFFFF
andq 0x60(%rsp), %rdi
callq 0x4d10
movq %rax, 0x40(%rsp)
movabsq $0x7ffc000000000001, %rax # imm = 0x7FFC000000000001
cmpq %rax, 0x40(%rsp)
sete %al
xorb $-0x1, %al
testb $0x1, %al
jne 0x3543
jmp 0x3703
movabsq $0x3ffffffffffff, %rax  # imm = 0x3FFFFFFFFFFFF
andq 0x40(%rsp), %rax
movq 0x10(%rax), %rax
movq %rax, 0x48(%rsp)
movb $0x1, %al
testb $0x1, %al
jne 0x3566
jmp 0x36e4
movq 0x48(%rsp), %rdi
xorl %esi, %esi
callq 0x4d50
testb $0x1, %al
jne 0x3578
jmp 0x3587
movq 0x48(%rsp), %rdi
callq 0x6d70
cmpl $0x2, %eax
je 0x35b1
movq 0x78(%rsp), %rdi
leaq 0x6e8c(%rip), %rsi      # 0xa41f
movb $0x0, %al
callq 0x73a0
movabsq $0x7ffc000000000004, %rax # imm = 0x7FFC000000000004
movq %rax, 0x80(%rsp)
jmp 0x3755
movabsq $0x3ffffffffffff, %rax  # imm = 0x3FFFFFFFFFFFF
andq 0x48(%rsp), %rax
movq 0x10(%rax), %rax
movq %rax, 0x38(%rsp)
movabsq $0x3ffffffffffff, %rcx  # imm = 0x3FFFFFFFFFFFF
andq 0x48(%rsp), %rcx
movabsq $0x3ffffffffffff, %rax  # imm = 0x3FFFFFFFFFFFF
andq 0x18(%rcx), %rax
movq 0x10(%rax), %rax
movq %rax, 0x30(%rsp)
movq 0x38(%rsp), %rdi
movl $0x2, %esi
callq 0x4d50
testb $0x1, %al
jne 0x362c
movq 0x78(%rsp), %rdi
leaq 0x6e3f(%rip), %rsi      # 0xa44d
movb $0x0, %al
callq 0x73a0
movabsq $0x7ffc000000000004, %rax # imm = 0x7FFC000000000004
movq %rax, 0x80(%rsp)
jmp 0x3755
movq 0x78(%rsp), %rdi
movq 0x38(%rsp), %rsi
movq 0x58(%rsp), %rdx
callq 0x6d00
movq %rax, 0x28(%rsp)
movq 0x28(%rsp), %rax
movq %rax, 0x58(%rsp)
movq 0x78(%rsp), %rdi
movq 0x70(%rsp), %rsi
movq 0x30(%rsp), %rdx
callq 0x85b0
movq %rax, 0x20(%rsp)
movq 0x20(%rsp), %rdi
movl $0x4, %esi
callq 0x4d50
testb $0x1, %al
jne 0x367d
jmp 0x36c1
movabsq $0x3ffffffffffff, %rax  # imm = 0x3FFFFFFFFFFFF
andq 0x20(%rsp), %rax
movq %rax, 0x18(%rsp)
movabsq $0x3ffffffffffff, %rax  # imm = 0x3FFFFFFFFFFFF
andq 0x38(%rsp), %rax
movq %rax, 0x10(%rsp)
movq 0x18(%rsp), %rax
cmpq $0x0, 0x10(%rax)
jne 0x36bf
movq 0x10(%rsp), %rcx
movq 0x18(%rsp), %rax
movq %rcx, 0x10(%rax)
jmp 0x36c1
movq 0x78(%rsp), %rdi
movq 0x20(%rsp), %rsi
movq 0x50(%rsp), %rdx
callq 0x6d00
movq %rax, 0x28(%rsp)
movq 0x28(%rsp), %rax
movq %rax, 0x50(%rsp)
jmp 0x36e6
movabsq $0x3ffffffffffff, %rax  # imm = 0x3FFFFFFFFFFFF
andq 0x40(%rsp), %rax
movq 0x18(%rax), %rax
movq %rax, 0x40(%rsp)
jmp 0x3526
jmp 0x3705
movq 0x78(%rsp), %rdi
movq 0x70(%rsp), %rsi
movq 0x58(%rsp), %rdx
movq 0x50(%rsp), %rcx
callq 0x7cf0
movq %rax, 0x8(%rsp)
movabsq $0x3ffffffffffff, %rax  # imm = 0x3FFFFFFFFFFFF
andq 0x68(%rsp), %rax
movq 0x18(%rax), %rax
movq %rax, (%rsp)
movq 0x78(%rsp), %rdi
movq 0x8(%rsp), %rsi
movq (%rsp), %rdx
callq 0x8960
movq %rax, 0x80(%rsp)
movq 0x80(%rsp), %rax
addq $0x88, %rsp
retq
nopw %cs:(%rax,%rax)