// File: /workspace/github_cpp_makefile_star2_O1/acliusBackHome[P]kamaya/dist/ParseExpressionConstCalculate.cpp
// Function: ParseExpression::calculate_const()
void ParseExpression::calculate_const() {
    if (const_value) {
        return;
    }
    // 只有const_value等于0时才计算常量
    switch (expr_type) {
        //双目运算符
        case E_ADD:
        case E_SUB:
        case E_MUL:
        case E_DIV:
        case E_POW:
        case E_MOD:
            // 比较运算符

        case E_G:
        case E_GE:
        case E_EQUAL:
        case E_NE:
        case E_L:
        case E_LE: {
            if (!get_expression(child[0]).is_const() || !get_expression(child[1]).is_const()) {
                // 不是常量退出
                break;
            }
            const ParseConstant &const1 = get_expression(child[0]).get_const(),
                    &const2 = get_expression(child[1]).get_const();
            if (expr_type == E_POW) {
                // 求幂运算比较特殊 直接返回long double
                const_value = (size_t)
                        new ParseConstant(powl(const1.get_float(), const2.get_float()));
                return;
            }
            ConstValueType cal_type =
                    ParseConstant::wider_const_type(const1.get_type(), const2.get_type());
            if (cal_type == C_UNDEFINED) {
                break;
            }
            switch (expr_type) {
                case E_ADD: {
                    calculate_const_add(cal_type, const1, const2);
                    return;
                }
                case E_SUB: {
                    calculate_const_sub(cal_type, const1, const2);
                    return;
                }
                case E_MUL: {
                    calculate_const_mul(cal_type, const1, const2);
                    return;
                }
                case E_DIV: {
                    calculate_const_div(cal_type, const1, const2);
                    return;
                }
                case E_MOD: {
                    calculate_const_mod(cal_type, const1, const2);
                    return;
                }
                    // 比较运算符
                case E_G: {
                    calculate_const_g(cal_type, const1, const2);
                    return;
                }
                case E_GE: {
                    calculate_const_ge(cal_type, const1, const2);
                    return;
                }
                case E_EQUAL: {
                    calculate_const_eq(cal_type, const1, const2);
                    return;
                }
                case E_NE: {
                    calculate_const_ne(cal_type, const1, const2);
                    return;
                }
                case E_L: {
                    calculate_const_l(cal_type, const1, const2);
                    return;
                }
                case E_LE: {
                    calculate_const_le(cal_type, const1, const2);
                    return;
                }
                default:
                    break;
            }
            break;
        }
            // 单目运算符

        case E_ADR:
        case E_PTR: {
            // 还未实现的调用
            string info = "ParseExpression::calculate_const() not implemented calling address operator";
            throw ParseException(EX_NOT_IMPLEMENTED, info);
        }
        case E_NEG:
        case E_POS:
        case E_BIT_NOT:
        case E_NOT: {
            if (!get_expression(child[0]).is_const()) {
                // 不是常量退出
                break;
            }
            const ParseConstant &constant = get_expression(child[0]).get_const();
            switch (expr_type) {
                case E_NEG: {
                    calculate_const_neg(constant.get_type(), constant);
                    return;
                }
                case E_POS: {
                    const_value = (size_t)
                            new ParseConstant(constant);
                    return;
                }
                case E_BIT_NOT: {
                    calculate_const_bit_not(constant.get_type(), constant);
                    return;
                }
                case E_NOT: {
                    calculate_const_not(constant.get_type(), constant);
                    return;
                }
                default:
                    break;
            }
            return;
        }
            // 逻辑运算符
        case E_LOGIC_OR:
        case E_LOGIC_AND: {
            if (!get_expression(child[0]).is_const() || !get_expression(child[1]).is_const()) {
                // 不是常量退出
                break;
            }
            const ParseConstant &const1 = get_expression(child[0]).get_const(),
                    &const2 = get_expression(child[1]).get_const();
            switch (expr_type) {
                case E_LOGIC_OR:
                    const_value = (size_t)
                            new ParseConstant(const1.get_bool() || const2.get_bool());
                    return;
                case E_LOGIC_AND:
                    const_value = (size_t)
                            new ParseConstant(const1.get_bool() && const2.get_bool());
                    return;
                default:
                    break;
            }
            break;
        }
        case E_CONST:
            const_value = child[0];
            break;
        case E_ASSIGN:// 赋值语句肯定不是常量
        case E_UNDEFINED:
        case E_VAR:
        case E_GET_ITEM: // 能进行后缀表达式运算的都不会是常量
            // 变量或者常量, 未定义不会计算常量
            break;
    }
    const_value = (size_t) -1;
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
pushq %r15
pushq %r14
pushq %r12
pushq %rbx
subq $0x50, %rsp
cmpq $0x0, 0x18(%rdi)
jne 0x34602
movq %rdi, %rbx
movl 0x28(%rdi), %eax
addl $-0x3, %eax
cmpl $0x15, %eax
ja 0x345fa
leaq 0x14165(%rip), %rcx     # 0x4853c
movslq (%rcx,%rax,4), %rax
addq %rcx, %rax
jmpq *%rax
movq (%rbx), %rdi
callq 0x2b8a6
movq %rax, %rdi
callq 0x2bb90
testb %al, %al
je 0x345fa
movq 0x8(%rbx), %rdi
callq 0x2b8a6
movq %rax, %rdi
callq 0x2bb90
testb %al, %al
je 0x345fa
movq (%rbx), %rdi
callq 0x2b8a6
movq %rax, %rdi
callq 0x2d488
movq %rax, %r15
movq 0x8(%rbx), %rdi
callq 0x2b8a6
movq %rax, %rdi
callq 0x2d488
movq %rax, %r14
cmpl $0xa, 0x28(%rbx)
jne 0x3459a
movl $0x10, %edi
callq 0x42e0
movq %rax, %r12
movq %r15, %rdi
callq 0x2f996
fstpt -0x2c(%rbp)
fldz
fstp %st(0)
movq %r14, %rdi
callq 0x2f996
fstpt 0x10(%rsp)
fldt -0x2c(%rbp)
fstpt (%rsp)
callq 0x4520
fstpt (%rsp)
movq %r12, %rdi
callq 0x2f814
fldz
fstp %st(0)
movq %r12, 0x18(%rbx)
jmp 0x34602
movq (%rbx), %rdi
callq 0x2b8a6
movq %rax, %rdi
callq 0x2bb90
testb %al, %al
je 0x345fa
movq (%rbx), %rdi
callq 0x2b8a6
movq %rax, %rdi
callq 0x2d488
movq %rax, %r14
movl 0x28(%rbx), %eax
addl $-0xb, %eax
cmpl $0x5, %eax
ja 0x34602
leaq 0x140c6(%rip), %rcx     # 0x48594
movslq (%rcx,%rax,4), %rax
addq %rcx, %rax
jmpq *%rax
movq %r14, %rdi
callq 0x2fdda
movq %rbx, %rdi
movl %eax, %esi
movq %r14, %rdx
addq $0x50, %rsp
popq %rbx
popq %r12
popq %r14
popq %r15
popq %rbp
jmp 0x358e4
movq (%rbx), %rdi
callq 0x2b8a6
movq %rax, %rdi
callq 0x2bb90
testb %al, %al
je 0x345fa
movq 0x8(%rbx), %rdi
callq 0x2b8a6
movq %rax, %rdi
callq 0x2bb90
testb %al, %al
je 0x345fa
movq (%rbx), %rdi
callq 0x2b8a6
movq %rax, %rdi
callq 0x2d488
movq %rax, %r12
movq 0x8(%rbx), %rdi
callq 0x2b8a6
movq %rax, %rdi
callq 0x2d488
movq %rax, %r14
movl 0x28(%rbx), %eax
cmpl $0x12, %eax
je 0x3466b
cmpl $0x11, %eax
jne 0x345fa
movl $0x10, %edi
callq 0x42e0
movq %rax, %r15
movq %r12, %rdi
callq 0x2fa16
movl %eax, %ecx
movb $0x1, %al
testb %cl, %cl
jne 0x3458a
movq %r14, %rdi
callq 0x2fa16
movzbl %al, %esi
movq %r15, %rdi
callq 0x2f7ec
jmp 0x3469b
movq %r15, %rdi
callq 0x2fdda
movl %eax, %r12d
movq %r14, %rdi
callq 0x2fdda
movl %r12d, %edi
movl %eax, %esi
callq 0x2fde2
cmpl $0x5, %eax
je 0x345fa
movl 0x28(%rbx), %ecx
addl $-0x5, %ecx
cmpl $0x13, %ecx
ja 0x345fa
leaq 0x13fde(%rip), %rdx     # 0x485ac
movslq (%rdx,%rcx,4), %rcx
addq %rdx, %rcx
jmpq *%rcx
movq %rbx, %rdi
movl %eax, %esi
movq %r15, %rdx
movq %r14, %rcx
addq $0x50, %rsp
popq %rbx
popq %r12
popq %r14
popq %r15
popq %rbp
jmp 0x34850
movq (%rbx), %rax
movq %rax, 0x18(%rbx)
movq $-0x1, 0x18(%rbx)
addq $0x50, %rsp
popq %rbx
popq %r12
popq %r14
popq %r15
popq %rbp
retq
movl $0x10, %edi
callq 0x42e0
movq %rax, %r15
movq %rax, %rdi
movq %r14, %rsi
callq 0x2f6c6
jmp 0x3469b
movq %r14, %rdi
callq 0x2fdda
movq %rbx, %rdi
movl %eax, %esi
movq %r14, %rdx
addq $0x50, %rsp
popq %rbx
popq %r12
popq %r14
popq %r15
popq %rbp
jmp 0x35782
movq %r14, %rdi
callq 0x2fdda
movq %rbx, %rdi
movl %eax, %esi
movq %r14, %rdx
addq $0x50, %rsp
popq %rbx
popq %r12
popq %r14
popq %r15
popq %rbp
jmp 0x35852
movl $0x10, %edi
callq 0x42e0
movq %rax, %r15
movq %r12, %rdi
callq 0x2fa16
testb %al, %al
je 0x3468e
movq %r14, %rdi
callq 0x2fa16
jmp 0x34690
xorl %eax, %eax
movzbl %al, %esi
movq %r15, %rdi
callq 0x2f7ec
movq %r15, 0x18(%rbx)
jmp 0x34602
movq %rbx, %rdi
movl %eax, %esi
movq %r15, %rdx
movq %r14, %rcx
addq $0x50, %rsp
popq %rbx
popq %r12
popq %r14
popq %r15
popq %rbp
jmp 0x35676
movq %rbx, %rdi
movl %eax, %esi
movq %r15, %rdx
movq %r14, %rcx
addq $0x50, %rsp
popq %rbx
popq %r12
popq %r14
popq %r15
popq %rbp
jmp 0x34dfa
movq %rbx, %rdi
movl %eax, %esi
movq %r15, %rdx
movq %r14, %rcx
addq $0x50, %rsp
popq %rbx
popq %r12
popq %r14
popq %r15
popq %rbp
jmp 0x34fcc
movq %rbx, %rdi
movl %eax, %esi
movq %r15, %rdx
movq %r14, %rcx
addq $0x50, %rsp
popq %rbx
popq %r12
popq %r14
popq %r15
popq %rbp
jmp 0x34b4c
movq %rbx, %rdi
movl %eax, %esi
movq %r15, %rdx
movq %r14, %rcx
addq $0x50, %rsp
popq %rbx
popq %r12
popq %r14
popq %r15
popq %rbp
jmp 0x34a4c
movq %rbx, %rdi
movl %eax, %esi
movq %r15, %rdx
movq %r14, %rcx
addq $0x50, %rsp
popq %rbx
popq %r12
popq %r14
popq %r15
popq %rbp
jmp 0x3494e
movq %rbx, %rdi
movl %eax, %esi
movq %r15, %rdx
movq %r14, %rcx
addq $0x50, %rsp
popq %rbx
popq %r12
popq %r14
popq %r15
popq %rbp
jmp 0x350d6
movq %rbx, %rdi
movl %eax, %esi
movq %r15, %rdx
movq %r14, %rcx
addq $0x50, %rsp
popq %rbx
popq %r12
popq %r14
popq %r15
popq %rbp
jmp 0x351e0
movq %rbx, %rdi
movl %eax, %esi
movq %r15, %rdx
movq %r14, %rcx
addq $0x50, %rsp
popq %rbx
popq %r12
popq %r14
popq %r15
popq %rbp
jmp 0x3556a
movq %rbx, %rdi
movl %eax, %esi
movq %r15, %rdx
movq %r14, %rcx
addq $0x50, %rsp
popq %rbx
popq %r12
popq %r14
popq %r15
popq %rbp
jmp 0x353a6
leaq -0x40(%rbp), %r15
movq %r15, -0x10(%r15)
leaq 0x13ef9(%rip), %rsi     # 0x486c4
leaq 0x13f3d(%rip), %rdx     # 0x4870f
leaq -0x50(%rbp), %rdi
callq 0xf65c
movl $0x28, %edi
callq 0x4190
movq %rax, %r14
leaq -0x50(%rbp), %rdx
movq %rax, %rdi
movl $0x13, %esi
callq 0x33d12
leaq 0x27570(%rip), %rsi     # 0x5bd70
leaq -0x2644d(%rip), %rdx    # 0xe3ba
movq %r14, %rdi
callq 0x4540
jmp 0x34813
jmp 0x34813
movq %rax, %rbx
movq %r15, %rdi
jmp 0x34843
movq %rax, %rbx
jmp 0x3482b
movq %rax, %rbx
movq %r14, %rdi
callq 0x4250
movq -0x50(%rbp), %rdi
cmpq %r15, %rdi
jne 0x34843
jmp 0x34848
movq %rax, %rbx
jmp 0x34848
fstp %st(0)
movq %rax, %rbx
movq %r12, %rdi
callq 0x42b0
movq %rbx, %rdi
callq 0x4560