void sincosf(float __x, float *p_sin, float *p_cos) {
  long double c, s;
  __asm__ __volatile__("fsincos\n\t"
                       "fnstsw    %%ax\n\t"
                       "testl     $0x400, %%eax\n\t"
                       "jz        1f\n\t"
                       "fldpi\n\t"
                       "fadd      %%st(0)\n\t"
                       "fxch      %%st(1)\n\t"
                       "2: fprem1\n\t"
                       "fnstsw    %%ax\n\t"
                       "testl     $0x400, %%eax\n\t"
                       "jnz       2b\n\t"
                       "fstp      %%st(1)\n\t"
                       "fsincos\n\t"
                       "1:"
                       : "=t"(c), "=u"(s)
                       : "0"(__x)
                       : "eax");
  *p_sin = (float)s;
  *p_cos = (float)c;
}


x86 assembly (clang, -O0):
<sincosf>:
push   %rbp
mov    %rsp,%rbp
movss  %xmm0,-0x4(%rbp)
mov    %rdi,-0x10(%rbp)
mov    %rsi,-0x18(%rbp)
flds   -0x4(%rbp)
fsincos
fnstsw %ax
test   $0x400,%eax
je     113c <sincosf+0x3c>
fldpi
fadd   %st(0),%st
fxch   %st(1)
fprem1
fnstsw %ax
test   $0x400,%eax
jne    1129 <sincosf+0x29>
fstp   %st(1)
fsincos
fstpt  -0x30(%rbp)
fstpt  -0x40(%rbp)
fldt   -0x40(%rbp)
mov    -0x10(%rbp),%rax
fstps  (%rax)
fldt   -0x30(%rbp)
fstps  -0x44(%rbp)
movss  -0x44(%rbp),%xmm0
mov    -0x18(%rbp),%rax
movss  %xmm0,(%rax)
pop    %rbp
ret

x86 assembly (clang, -O2):
<sincosf>:
movss  %xmm0,-0x4(%rsp)
flds   -0x4(%rsp)
fsincos
fnstsw %ax
test   $0x400,%eax
je     112a <sincosf+0x2a>
fldpi
fadd   %st(0),%st
fxch   %st(1)
fprem1
fnstsw %ax
test   $0x400,%eax
jne    111b <sincosf+0x1b>
fstp   %st(1)
fsincos
fxch   %st(1)
fstps  (%rdi)
fstps  (%rsi)
ret

LLVM IR (-O0):
define void @sincosf(float %0, float* %1, float* %2) {
%4 = alloca float
%5 = alloca float*
%6 = alloca float*
%7 = alloca x86_fp80
%8 = alloca x86_fp80
store float %0, float* %4
store float* %1, float** %5
store float* %2, float** %6
%9 = load float, float* %4
%10 = fpext float %9 to x86_fp80
%11 = call { x86_fp80, x86_fp80 } asm sideeffect "fsincos\0A\09fnstsw %ax\0A\09testl $$0x400, %eax\0A\09jz 1f\0A\09fldpi\0A\09fadd %st(0)\0A\09fxch %st(1)\0A\092: fprem1\0A\09fnstsw %ax\0A\09testl $$0x400, %eax\0A\09jnz 2b\0A\09fstp %st(1)\0A\09fsincos\0A\091:", "={st},={st(1)},0,~{eax},~{dirflag},~{fpsr},~{flags}"(x86_fp80 %10)
%12 = extractvalue { x86_fp80, x86_fp80 } %11, 0
%13 = extractvalue { x86_fp80, x86_fp80 } %11, 1
store x86_fp80 %12, x86_fp80* %7
store x86_fp80 %13, x86_fp80* %8
%14 = load x86_fp80, x86_fp80* %8
%15 = fptrunc x86_fp80 %14 to float
%16 = load float*, float** %5
store float %15, float* %16
%17 = load x86_fp80, x86_fp80* %7
%18 = fptrunc x86_fp80 %17 to float
%19 = load float*, float** %6
store float %18, float* %19
ret void
}

LLVM IR (-O2):
define void @sincosf(float %0, float* nocapture writeonly %1, float* nocapture writeonly %2) {
%4 = fpext float %0 to x86_fp80
%5 = tail call { x86_fp80, x86_fp80 } asm sideeffect "fsincos\0A\09fnstsw %ax\0A\09testl $$0x400, %eax\0A\09jz 1f\0A\09fldpi\0A\09fadd %st(0)\0A\09fxch %st(1)\0A\092: fprem1\0A\09fnstsw %ax\0A\09testl $$0x400, %eax\0A\09jnz 2b\0A\09fstp %st(1)\0A\09fsincos\0A\091:", "={st},={st(1)},0,~{eax},~{dirflag},~{fpsr},~{flags}"(x86_fp80 %4)
%6 = extractvalue { x86_fp80, x86_fp80 } %5, 0
%7 = extractvalue { x86_fp80, x86_fp80 } %5, 1
%8 = fptrunc x86_fp80 %7 to float
store float %8, float* %1
%9 = fptrunc x86_fp80 %6 to float
store float %9, float* %2
ret void
}