// File: /workspace/github_c_makefile_star2_O1/mbitsnbites[P]SoftFP/./softfp_template.h
// Function: fma_sf128
F_UINT fma_sf(F_UINT a, F_UINT b, F_UINT c, RoundingModeEnum rm,
              uint32_t *pfflags)
{
    uint32_t a_sign, b_sign, c_sign, r_sign;
    int32_t a_exp, b_exp, c_exp, r_exp, shift;
    F_UINT a_mant, b_mant, c_mant, r_mant1, r_mant0, c_mant1, c_mant0, mask;

    a_sign = a >> (F_SIZE - 1);
    b_sign = b >> (F_SIZE - 1);
    c_sign = c >> (F_SIZE - 1);
    r_sign = a_sign ^ b_sign;
    a_exp = (a >> MANT_SIZE) & EXP_MASK;
    b_exp = (b >> MANT_SIZE) & EXP_MASK;
    c_exp = (c >> MANT_SIZE) & EXP_MASK;
    a_mant = a & MANT_MASK;
    b_mant = b & MANT_MASK;
    c_mant = c & MANT_MASK;
    if (a_exp == EXP_MASK || b_exp == EXP_MASK || c_exp == EXP_MASK) {
        if (isnan_sf(a) || isnan_sf(b) || isnan_sf(c)) {
            if (issignan_sf(a) || issignan_sf(b) || issignan_sf(c)) {
                *pfflags |= FFLAG_INVALID_OP;
            }
            return F_QNAN;
        } else {
            /* infinities */
            if ((a_exp == EXP_MASK && (b_exp == 0 && b_mant == 0)) ||
                (b_exp == EXP_MASK && (a_exp == 0 && a_mant == 0)) ||
                ((a_exp == EXP_MASK || b_exp == EXP_MASK) &&
                 (c_exp == EXP_MASK && r_sign != c_sign))) {
                *pfflags |= FFLAG_INVALID_OP;
                return F_QNAN;
            } else if (c_exp == EXP_MASK) {
                return pack_sf(c_sign, EXP_MASK, 0);
            } else {
                return pack_sf(r_sign, EXP_MASK, 0);
            }
        }
    }
    if (a_exp == 0) {
        if (a_mant == 0)
            goto mul_zero;
        a_mant = normalize_subnormal_sf(&a_exp, a_mant);
    } else {
        a_mant |= (F_UINT)1 << MANT_SIZE;
    }
    if (b_exp == 0) {
        if (b_mant == 0) {
        mul_zero:
            if (c_exp == 0 && c_mant == 0) {
                if (c_sign != r_sign)
                    r_sign = (rm == RM_RDN);
                return pack_sf(r_sign, 0, 0);
            } else {
                return c;
            }
        }
        b_mant = normalize_subnormal_sf(&b_exp, b_mant);
    } else {
        b_mant |= (F_UINT)1 << MANT_SIZE;
    }
    /* multiply */
    r_exp = a_exp + b_exp - (1 << (EXP_SIZE - 1)) + 3;
    
    r_mant1 = mul_u(&r_mant0, a_mant << RND_SIZE, b_mant << RND_SIZE);
    /* normalize to F_SIZE - 3 */
    if (r_mant1 < ((F_UINT)1 << (F_SIZE - 3))) {
        r_mant1 = (r_mant1 << 1) | (r_mant0 >> (F_SIZE - 1));
        r_mant0 <<= 1;
        r_exp--;
    }

    /* add */
    if (c_exp == 0) {
        if (c_mant == 0) {
            /* add zero */
            r_mant1 |= (r_mant0 != 0);
            return normalize_sf(r_sign, r_exp, r_mant1, rm, pfflags);
        }
        c_mant = normalize_subnormal_sf(&c_exp, c_mant);
    } else {
        c_mant |= (F_UINT)1 << MANT_SIZE;
    }
    c_exp++;
    c_mant1 = c_mant << (RND_SIZE - 1);
    c_mant0 = 0;

    //    printf("r_s=%d r_exp=%d r_mant=%08x %08x\n", r_sign, r_exp, (uint32_t)r_mant1, (uint32_t)r_mant0);
    //    printf("c_s=%d c_exp=%d c_mant=%08x %08x\n", c_sign, c_exp, (uint32_t)c_mant1, (uint32_t)c_mant0);

    /* ensure that abs(r) >= abs(c) */
    if (!(r_exp > c_exp || (r_exp == c_exp && r_mant1 >= c_mant1))) {
        F_UINT tmp;
        int32_t c_tmp;
        /* swap */
        tmp = r_mant1; r_mant1 = c_mant1; c_mant1 = tmp;
        tmp = r_mant0; r_mant0 = c_mant0; c_mant0 = tmp;
        c_tmp = r_exp; r_exp = c_exp; c_exp = c_tmp;
        c_tmp = r_sign; r_sign = c_sign; c_sign = c_tmp;
    }
    /* right shift c_mant */
    shift = r_exp - c_exp;
    if (shift >= 2 * F_SIZE) {
        c_mant0 = (c_mant0 | c_mant1) != 0;
        c_mant1 = 0;
    } else if (shift >= F_SIZE + 1) {
        c_mant0 = rshift_rnd(c_mant1, shift - F_SIZE);
        c_mant1 = 0;
    } else if (shift == F_SIZE) {
        c_mant0 = c_mant1 | (c_mant0 != 0);
        c_mant1 = 0;
    } else if (shift != 0) {
        mask = ((F_UINT)1 << shift) - 1;
        c_mant0 = (c_mant1 << (F_SIZE - shift)) | (c_mant0 >> shift) | ((c_mant0 & mask) != 0);
        c_mant1 = c_mant1 >> shift;
    }
    //    printf("  r_mant=%08x %08x\n", (uint32_t)r_mant1, (uint32_t)r_mant0);
    //    printf("  c_mant=%08x %08x\n", (uint32_t)c_mant1, (uint32_t)c_mant0);
    /* add or subtract */
    if (r_sign == c_sign) {
        r_mant0 += c_mant0;
        r_mant1 += c_mant1 + (r_mant0 < c_mant0);
    } else {
        F_UINT tmp;
        tmp = r_mant0;
        r_mant0 -= c_mant0;
        r_mant1 = r_mant1 - c_mant1 - (r_mant0 > tmp);
        if ((r_mant0 | r_mant1) == 0) {
            /* zero result : the sign needs a specific handling */
            r_sign = (rm == RM_RDN);
        }
    }
#if 0
    //    printf("  r1_mant=%08x %08x\n", (uint32_t)r_mant1, (uint32_t)r_mant0);
    /* normalize */
    if (r_mant1 == 0) {
        r_mant1 = r_mant0;
        r_exp -= F_SIZE;
    } else {
        shift = clz(r_mant1) - (F_SIZE - 1 - IMANT_SIZE);
        if (shift != 0) {
            r_mant1 = (r_mant1 << shift) | (r_mant0 >> (F_SIZE - shift));
            r_mant0 <<= shift;
            r_exp -= shift;
        }
        r_mant1 |= (r_mant0 != 0);
    }
    return normalize_sf(r_sign, r_exp, r_mant1, rm, pfflags);
#else
    return normalize2_sf(r_sign, r_exp, r_mant1, r_mant0, rm, pfflags);
#endif
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x38, %rsp
movq %r8, 0x10(%rsp)
movq %r9, %rax
shrq $0x3f, %rax
movq %rax, 0x20(%rsp)
movq %rcx, %r10
xorq %rsi, %r10
movq %r10, %rax
shrq $0x3f, %rax
movq %rax, 0x18(%rsp)
movq %rsi, %r15
shrq $0x30, %r15
movl $0x7fff, %r11d          # imm = 0x7FFF
andl %r11d, %r15d
movq %rcx, %r12
shrq $0x30, %r12
andl %r11d, %r12d
movq %r9, %r13
shrq $0x30, %r13
andl %r11d, %r13d
movabsq $0xffffffffffff, %rbx   # imm = 0xFFFFFFFFFFFF
movq %rsi, %rax
andq %rbx, %rax
movq %rcx, %r8
andq %rbx, %r8
andq %r9, %rbx
cmpl %r11d, %r15d
sete %r14b
cmpl %r11d, %r12d
sete %bpl
orb %r14b, %bpl
cmpl %r11d, %r13d
sete %r11b
orb %bpl, %r11b
movq 0x78(%rsp), %r14
cmpb $0x1, %r11b
jne 0x7f31
movabsq $0x7fff000000000000, %r11 # imm = 0x7FFF000000000000
movq %rsi, %r14
notq %r14
testq %r11, %r14
sete %bpl
movq %rdi, %r14
orq %rax, %r14
setne %r14b
testb %r14b, %bpl
jne 0x7f43
movq %rcx, %r14
notq %r14
testq %r14, %r11
setne %bpl
movq %rdx, %r14
orq %r8, %r14
sete %r14b
orb %bpl, %r14b
cmpb $0x1, %r14b
jne 0x7f43
movq %r9, %r14
notq %r14
testq %r14, %r11
setne %bpl
movq 0x10(%rsp), %r14
orq %rbx, %r14
sete %r14b
orb %bpl, %r14b
je 0x7f43
movl %r15d, %ecx
xorl $0x7fff, %ecx           # imm = 0x7FFF
orl %r12d, %ecx
sete %cl
orq %r8, %rdx
sete %dl
testb %dl, %cl
movq 0x78(%rsp), %rdx
jne 0x7f22
movl %r12d, %ecx
xorl $0x7fff, %ecx           # imm = 0x7FFF
orl %r15d, %ecx
sete %cl
orq %rax, %rdi
sete %al
testb %al, %cl
jne 0x7f22
movl $0x7fff, %ecx           # imm = 0x7FFF
cmpl %ecx, %r12d
sete %al
cmpl %ecx, %r15d
sete %cl
movq 0x20(%rsp), %rsi
cmpl %esi, 0x18(%rsp)
je 0x84da
orb %al, %cl
je 0x84da
cmpl $0x7fff, %r13d          # imm = 0x7FFF
jne 0x84da
movabsq $0x7fff800000000000, %r10 # imm = 0x7FFF800000000000
orb $0x10, (%rdx)
jmp 0x7f95
testl %r15d, %r15d
je 0x7f9c
btsq $0x30, %rax
movq %rdi, %rsi
jmp 0x7fee
orq %rax, %rdi
setne %al
movabsq $0x7fff800000000000, %r10 # imm = 0x7FFF800000000000
andq %r10, %rsi
cmpq %r11, %rsi
sete %sil
testb %al, %sil
movq 0x78(%rsp), %rsi
jne 0x7f92
andq %r10, %rcx
cmpq %r11, %rcx
setne %al
orq %r8, %rdx
sete %cl
orb %al, %cl
cmpb $0x1, %cl
jne 0x7f92
andq %r10, %r9
cmpq %r11, %r9
setne %al
orq %rbx, 0x10(%rsp)
sete %cl
orb %al, %cl
jne 0x7f95
orb $0x10, (%rsi)
xorl %eax, %eax
jmp 0x83f7
movq %rdi, %rcx
orq %rax, %rcx
je 0x8029
movq %rdi, %rcx
orq %rax, %rcx
je 0x7fc9
bsrq %rax, %rsi
xorl $0x3f, %esi
bsrq %rdi, %rcx
xorl $0x3f, %ecx
orl $0x40, %ecx
testq %rax, %rax
cmovnel %esi, %ecx
jmp 0x7fce
movl $0x80, %ecx
movl $0x10, %r15d
subl %ecx, %r15d
addb $-0xf, %cl
shldq %cl, %rdi, %rax
shlq %cl, %rdi
xorl %esi, %esi
testb $0x40, %cl
cmovneq %rdi, %rax
cmoveq %rdi, %rsi
testl %r12d, %r12d
je 0x8000
btsq $0x30, %r8
movq %rdx, %rcx
jmp 0x8093
movq %rdx, %rcx
orq %r8, %rcx
je 0x8029
movq %rdx, %rcx
orq %r8, %rcx
je 0x806a
bsrq %r8, %rcx
xorl $0x3f, %ecx
bsrq %rdx, %rdi
xorl $0x3f, %edi
orl $0x40, %edi
testq %r8, %r8
cmovnel %ecx, %edi
jmp 0x806f
testl %r13d, %r13d
sete %dl
movq 0x10(%rsp), %rax
orq %rax, %rbx
sete %cl
andb %dl, %cl
movq %r9, %r10
cmpb $0x1, %cl
jne 0x83f7
xorl %r10d, %r10d
cmpl $0x2, 0x70(%rsp)
sete %r10b
movq 0x18(%rsp), %rax
cmpl %eax, 0x20(%rsp)
cmoveq %rax, %r10
shlq $0x3f, %r10
jmp 0x7f95
movl $0x80, %edi
movl $0x10, %r12d
subl %edi, %r12d
addb $-0xf, %dil
movl %edi, %ecx
shldq %cl, %rdx, %r8
shlq %cl, %rdx
xorl %ecx, %ecx
testb $0x40, %dil
cmovneq %rdx, %r8
cmoveq %rdx, %rcx
shldq $0xe, %rsi, %rax
shlq $0xe, %rsi
shldq $0xe, %rcx, %r8
shlq $0xe, %rcx
movq %rsp, %rdi
movq %rax, %rdx
callq 0x7d49
movq %rax, %r10
movq %rdx, %r9
movq %rdx, %rax
shrq $0x3d, %rax
jne 0x80ef
addl %r15d, %r12d
movq (%rsp), %rax
movq 0x8(%rsp), %rcx
shldq $0x1, %r10, %r9
shldq $0x1, %rcx, %r10
shldq $0x1, %rax, %rcx
addq %rax, %rax
movq %rax, (%rsp)
movq %rcx, 0x8(%rsp)
addl $0xffffc002, %r12d      # imm = 0xFFFFC002
jmp 0x80f9
addl %r15d, %r12d
addl $0xffffc003, %r12d      # imm = 0xFFFFC003
movq 0x18(%rsp), %rdi
movq 0x10(%rsp), %rdx
testl %r13d, %r13d
je 0x8112
btsq $0x30, %rbx
movq %rdx, %r15
jmp 0x818d
movq %rdx, %rax
orq %rbx, %rax
je 0x813b
movq %rdx, %rax
orq %rbx, %rax
je 0x8167
bsrq %rbx, %rax
xorl $0x3f, %eax
bsrq %rdx, %rcx
xorl $0x3f, %ecx
orl $0x40, %ecx
testq %rbx, %rbx
cmovnel %eax, %ecx
jmp 0x816c
movq (%rsp), %rax
xorl %ecx, %ecx
orq 0x8(%rsp), %rax
setne %cl
orq %rcx, %r10
movl %r12d, %esi
movq %r10, %rdx
movq %r9, %rcx
movl 0x70(%rsp), %r8d
movq %r14, %r9
callq 0x7a5b
jmp 0x83f4
movl $0x80, %ecx
movl $0x10, %r13d
subl %ecx, %r13d
addb $-0xf, %cl
shldq %cl, %rdx, %rbx
shlq %cl, %rdx
xorl %r15d, %r15d
testb $0x40, %cl
cmovneq %rdx, %rbx
cmoveq %rdx, %r15
shldq $0xd, %r15, %rbx
incl %r13d
shlq $0xd, %r15
xorl %eax, %eax
cmpl %r13d, %r12d
jg 0x81af
jne 0x81c8
xorl %eax, %eax
cmpq %r15, %r10
movq %r9, %rcx
sbbq %rbx, %rcx
jb 0x81c8
movl %r13d, %r8d
xorl %esi, %esi
movq %r15, %rdx
movq %rbx, %rbp
movq %r10, %r15
movq %r9, %rbx
movl %r12d, %r10d
movl %edi, %r11d
jmp 0x81ec
movq (%rsp), %rax
movq 0x8(%rsp), %rsi
xorps %xmm0, %xmm0
movaps %xmm0, (%rsp)
movl %r12d, %r8d
movq %r10, %rdx
movq %r9, %rbp
movl %r13d, %r10d
movq 0x20(%rsp), %rcx
movl %ecx, %r11d
movl %r10d, %ecx
subl %r8d, %ecx
cmpl $0x100, %ecx            # imm = 0x100
jl 0x820c
orq %rax, %rdx
orq %rsi, %rbp
xorl %eax, %eax
orq %rdx, %rbp
setne %al
xorl %esi, %esi
jmp 0x8257
cmpl $0x81, %ecx
jl 0x823a
addl $-0x80, %ecx
movq %rdx, %rdi
movq %rbp, %rsi
movl %ecx, %edx
movl %r10d, %ebp
movl %r11d, %r12d
callq 0x79ea
movl %r12d, %r11d
movl %ebp, %r10d
movq 0x18(%rsp), %rdi
movq %rdx, %rsi
jmp 0x8257
cmpl $0x80, %ecx
jne 0x8409
xorl %ecx, %ecx
orq %rsi, %rax
setne %cl
orq %rcx, %rdx
movq %rdx, %rax
movq %rbp, %rsi
xorl %edx, %edx
xorl %ebp, %ebp
movq (%rsp), %r9
movq 0x8(%rsp), %rcx
cmpl 0x20(%rsp), %edi
movl 0x70(%rsp), %r8d
jne 0x828e
addq %r15, %rdx
adcq %rbx, %rbp
addq %rax, %r9
adcq %rsi, %rcx
movq %r9, (%rsp)
movq %rcx, 0x8(%rsp)
adcq $0x0, %rdx
adcq $0x0, %rbp
jmp 0x82c7
subq %rdx, %r15
sbbq %rbp, %rbx
subq %rax, %r9
sbbq %rsi, %rcx
movq %r9, (%rsp)
movq %rcx, 0x8(%rsp)
sbbq $0x0, %r15
sbbq $0x0, %rbx
orq %r15, %r9
orq %rbx, %rcx
xorl %eax, %eax
cmpl $0x2, %r8d
sete %al
orq %r9, %rcx
cmovel %eax, %r11d
movq %r15, %rdx
movq %rbx, %rbp
movq (%rsp), %rdi
movq 0x8(%rsp), %r9
movq %rdx, %rax
orq %rbp, %rax
je 0x82f1
bsrq %rbp, %rax
xorl $0x3f, %eax
bsrq %rdx, %rsi
xorl $0x3f, %esi
orl $0x40, %esi
testq %rbp, %rbp
cmovnel %eax, %esi
jmp 0x831d
movq %rdi, %rax
orq %r9, %rax
je 0x8318
bsrq %r9, %rax
xorl $0x3f, %eax
bsrq %rdi, %rsi
xorl $0x3f, %esi
orl $0x40, %esi
testq %r9, %r9
cmovnel %eax, %esi
orl $0x80, %esi
jmp 0x831d
movl $0x100, %esi            # imm = 0x100
testl %esi, %esi
jle 0x8508
movl %esi, %eax
decl %eax
je 0x83b5
cmpl $0x80, %esi
jg 0x83c2
movq %r14, %r8
movq %rdi, %r14
movl %eax, %ecx
shlq %cl, %r14
xorl %ebx, %ebx
testb $0x40, %al
movl %r10d, %r13d
movq %r14, %r10
cmovneq %rbx, %r10
movl %r11d, %r12d
movq %r9, %r11
shldq %cl, %rdi, %r11
testb $0x40, %al
cmovneq %r14, %r11
movq %rdx, %r14
shlq %cl, %r14
testb $0x40, %al
movq %r14, %r15
cmovneq %rbx, %r15
shldq %cl, %rdx, %rbp
testb $0x40, %al
cmovneq %r14, %rbp
movq %r8, %r14
movl 0x70(%rsp), %r8d
movb $-0x7f, %cl
subb %sil, %cl
shrdq %cl, %r9, %rdi
shrq %cl, %r9
testb $0x40, %cl
cmovneq %r9, %rdi
cmovneq %rbx, %r9
orq %r9, %rbp
orq %r15, %rdi
xorl %edx, %edx
orq %r10, %r11
movl %r12d, %r11d
movl %r13d, %r10d
setne %dl
orq %rdi, %rdx
jmp 0x83e0
xorl %ecx, %ecx
orq %r9, %rdi
setne %cl
orq %rcx, %rdx
jmp 0x83e0
addb $0x7f, %sil
movl %esi, %ecx
shldq %cl, %rdi, %r9
shlq %cl, %rdi
xorl %edx, %edx
testb $0x40, %sil
cmovneq %rdi, %r9
cmoveq %rdi, %rdx
movq %r9, %rbp
subl %eax, %r10d
movl %r11d, %edi
movl %r10d, %esi
movq %rbp, %rcx
movq %r14, %r9
callq 0x98fc
movq %rdx, %r10
movq %r10, %rdx
addq $0x38, %rsp
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
cmpl %r13d, %r12d
je 0x825b
movq %rbp, %r8
shrq %cl, %r8
xorl %r12d, %r12d
testb $0x40, %cl
movq %r8, %r9
cmovneq %r12, %r9
movq %r9, 0x30(%rsp)
movl %r11d, 0x2c(%rsp)
movq %rdx, %r11
shrdq %cl, %rbp, %r11
testb $0x40, %cl
cmovneq %r8, %r11
movq %rsi, %r8
shrq %cl, %r8
testb $0x40, %cl
movq %r8, %r12
movl $0x0, %r9d
cmovneq %r9, %r12
movl %r10d, 0x10(%rsp)
movq %rax, %r10
shrdq %cl, %rsi, %r10
testb $0x40, %cl
cmovneq %r8, %r10
movq $-0x1, %r13
movq $-0x1, %r8
shlq %cl, %r8
testb $0x40, %cl
cmovneq %r8, %r13
cmovneq %r9, %r8
movb $-0x80, %r9b
subb %cl, %r9b
movl %r9d, %ecx
shldq %cl, %rdx, %rbp
notq %r8
shlq %cl, %rdx
testb $0x40, %r9b
cmovneq %rdx, %rbp
movl $0x0, %ecx
cmovneq %rcx, %rdx
notq %r13
orq %r12, %rbp
orq %r10, %rdx
movl 0x10(%rsp), %r10d
andq %rsi, %r13
andq %rax, %r8
xorl %eax, %eax
orq %r13, %r8
setne %al
orq %rdx, %rax
movq %rbp, %rsi
movq %r11, %rdx
movl 0x2c(%rsp), %r11d
movq 0x30(%rsp), %rbp
jmp 0x825b
movabsq $-0x8000000000000000, %rax # imm = 0x8000000000000000
cmpl $0x7fff, %r13d          # imm = 0x7FFF
jne 0x84fd
andq %rax, %r9
orq %r11, %r9
xorl %eax, %eax
movq %r9, %r10
jmp 0x83f7
andq %rax, %r10
orq %r11, %r10
jmp 0x7f95
leaq 0xdff7(%rip), %rdi      # 0x16506
leaq 0xdffb(%rip), %rsi      # 0x16511
leaq 0xe1ac(%rip), %rcx      # 0x166c9
movl $0xc9, %edx
callq 0x1080