#define NULL ((void *)0)
typedef unsigned long size_t; // Customize by platform.
typedef long intptr_t;
typedef unsigned long uintptr_t;
typedef long scalar_t__; // Either arithmetic or pointer type.
/* By default, we understand bool (as a convenience). */
typedef int bool;
#define false 0
#define true 1

/* Forward declarations */

/* Type definitions */

/* Variables and functions */
short SHRT_MAX;
short SHRT_MIN;
int ffr4fi2(float *input, long ntodo, double scale, double zero, short *output,
            int *status) {
  long ii;
  double dvalue;
  if (scale == 1. && zero == 0.) {
    for (ii = 0; ii < ntodo; ii++) {
      if (input[ii] < -32768.49) {
        *status = -11;
        output[ii] = SHRT_MIN;
      } else if (input[ii] > 32767.49) {
        *status = -11;
        output[ii] = SHRT_MAX;
      } else
        output[ii] = (short)input[ii];
    }
  } else {
    for (ii = 0; ii < ntodo; ii++) {
      dvalue = (input[ii] - zero) / scale;
      if (dvalue < -32768.49) {
        *status = -11;
        output[ii] = SHRT_MIN;
      } else if (dvalue > 32767.49) {
        *status = -11;
        output[ii] = SHRT_MAX;
      } else {
        if (dvalue >= 0)
          output[ii] = (short)(dvalue + .5);
        else
          output[ii] = (short)(dvalue - .5);
      }
    }
  }
  return (*status);
}


x86 assembly (clang, -O0):
<ffr4fi2>:
push   %rbp
mov    %rsp,%rbp
mov    %rdi,-0x8(%rbp)
mov    %rsi,-0x10(%rbp)
movsd  %xmm0,-0x18(%rbp)
movsd  %xmm1,-0x20(%rbp)
mov    %rdx,-0x28(%rbp)
mov    %rcx,-0x30(%rbp)
movsd  -0x18(%rbp),%xmm0
movsd  0xed5(%rip),%xmm1
ucomisd %xmm1,%xmm0
jne    1239 <ffr4fi2+0x139>
jp     1239 <ffr4fi2+0x139>
movsd  -0x20(%rbp),%xmm0
xorps  %xmm1,%xmm1
ucomisd %xmm1,%xmm0
jne    1239 <ffr4fi2+0x139>
jp     1239 <ffr4fi2+0x139>
movq   $0x0,-0x38(%rbp)
mov    -0x38(%rbp),%rax
cmp    -0x10(%rbp),%rax
jge    1234 <ffr4fi2+0x134>
mov    -0x8(%rbp),%rax
mov    -0x38(%rbp),%rcx
movss  (%rax,%rcx,4),%xmm0
cvtss2sd %xmm0,%xmm1
movsd  0xe86(%rip),%xmm0
ucomisd %xmm1,%xmm0
jbe    11b1 <ffr4fi2+0xb1>
mov    -0x30(%rbp),%rax
movl   $0xfffffff5,(%rax)
mov    0x2e43(%rip),%rax
mov    (%rax),%dx
mov    -0x28(%rbp),%rax
mov    -0x38(%rbp),%rcx
mov    %dx,(%rax,%rcx,2)
jmp    121e <ffr4fi2+0x11e>
mov    -0x8(%rbp),%rax
mov    -0x38(%rbp),%rcx
movss  (%rax,%rcx,4),%xmm0
cvtss2sd %xmm0,%xmm0
movsd  0xe46(%rip),%xmm1
ucomisd %xmm1,%xmm0
jbe    11f9 <ffr4fi2+0xf9>
mov    -0x30(%rbp),%rax
movl   $0xfffffff5,(%rax)
mov    0x2df3(%rip),%rax
mov    (%rax),%dx
mov    -0x28(%rbp),%rax
mov    -0x38(%rbp),%rcx
mov    %dx,(%rax,%rcx,2)
jmp    1219 <ffr4fi2+0x119>
mov    -0x8(%rbp),%rax
mov    -0x38(%rbp),%rcx
movss  (%rax,%rcx,4),%xmm0
cvttss2si %xmm0,%eax
mov    %ax,%dx
mov    -0x28(%rbp),%rax
mov    -0x38(%rbp),%rcx
mov    %dx,(%rax,%rcx,2)
jmp    121e <ffr4fi2+0x11e>
jmp    1223 <ffr4fi2+0x123>
mov    -0x38(%rbp),%rax
add    $0x1,%rax
mov    %rax,-0x38(%rbp)
jmp    115b <ffr4fi2+0x5b>
jmp    1367 <ffr4fi2+0x267>
movq   $0x0,-0x38(%rbp)
mov    -0x38(%rbp),%rax
cmp    -0x10(%rbp),%rax
jge    1362 <ffr4fi2+0x262>
mov    -0x8(%rbp),%rax
mov    -0x38(%rbp),%rcx
movss  (%rax,%rcx,4),%xmm0
cvtss2sd %xmm0,%xmm0
subsd  -0x20(%rbp),%xmm0
divsd  -0x18(%rbp),%xmm0
movsd  %xmm0,-0x40(%rbp)
movsd  0xd91(%rip),%xmm0
ucomisd -0x40(%rbp),%xmm0
jbe    12a7 <ffr4fi2+0x1a7>
mov    -0x30(%rbp),%rax
movl   $0xfffffff5,(%rax)
mov    0x2d4d(%rip),%rax
mov    (%rax),%dx
mov    -0x28(%rbp),%rax
mov    -0x38(%rbp),%rcx
mov    %dx,(%rax,%rcx,2)
jmp    134c <ffr4fi2+0x24c>
movsd  -0x40(%rbp),%xmm0
movsd  0xd5c(%rip),%xmm1
ucomisd %xmm1,%xmm0
jbe    12e3 <ffr4fi2+0x1e3>
mov    -0x30(%rbp),%rax
movl   $0xfffffff5,(%rax)
mov    0x2d09(%rip),%rax
mov    (%rax),%dx
mov    -0x28(%rbp),%rax
mov    -0x38(%rbp),%rcx
mov    %dx,(%rax,%rcx,2)
jmp    1347 <ffr4fi2+0x247>
movsd  -0x40(%rbp),%xmm0
xorps  %xmm1,%xmm1
ucomisd %xmm1,%xmm0
jb     131e <ffr4fi2+0x21e>
movsd  -0x40(%rbp),%xmm0
movsd  0xd1e(%rip),%xmm1
addsd  %xmm1,%xmm0
cvttsd2si %xmm0,%eax
mov    %ax,%dx
mov    -0x28(%rbp),%rax
mov    -0x38(%rbp),%rcx
mov    %dx,(%rax,%rcx,2)
jmp    1342 <ffr4fi2+0x242>
movsd  -0x40(%rbp),%xmm0
movsd  0xced(%rip),%xmm1
addsd  %xmm1,%xmm0
cvttsd2si %xmm0,%eax
mov    %ax,%dx
mov    -0x28(%rbp),%rax
mov    -0x38(%rbp),%rcx
mov    %dx,(%rax,%rcx,2)
jmp    1347 <ffr4fi2+0x247>
jmp    134c <ffr4fi2+0x24c>
jmp    1351 <ffr4fi2+0x251>
mov    -0x38(%rbp),%rax
add    $0x1,%rax
mov    %rax,-0x38(%rbp)
jmp    1241 <ffr4fi2+0x141>
jmp    1367 <ffr4fi2+0x267>
mov    -0x30(%rbp),%rax
mov    (%rax),%eax
pop    %rbp
ret

x86 assembly (clang, -O2):
<ffr4fi2>:
ucomisd 0xef8(%rip),%xmm0
jne    1197 <ffr4fi2+0x97>
jp     1197 <ffr4fi2+0x97>
xorpd  %xmm2,%xmm2
ucomisd %xmm2,%xmm1
jne    1197 <ffr4fi2+0x97>
jp     1197 <ffr4fi2+0x97>
test   %rsi,%rsi
jle    1247 <ffr4fi2+0x147>
xor    %eax,%eax
movsd  0xed1(%rip),%xmm0
mov    0x2ea2(%rip),%r8
movsd  0xeca(%rip),%xmm1
mov    0x2e8b(%rip),%r9
jmp    116c <ffr4fi2+0x6c>
nop
movl   $0xfffffff5,(%rcx)
movzwl (%r8),%r10d
mov    %r10w,(%rdx,%rax,2)
add    $0x1,%rax
cmp    %rax,%rsi
je     1247 <ffr4fi2+0x147>
movss  (%rdi,%rax,4),%xmm2
xorps  %xmm3,%xmm3
cvtss2sd %xmm2,%xmm3
ucomisd %xmm3,%xmm0
ja     1150 <ffr4fi2+0x50>
ucomisd %xmm1,%xmm3
jbe    1190 <ffr4fi2+0x90>
movl   $0xfffffff5,(%rcx)
movzwl (%r9),%r10d
jmp    115a <ffr4fi2+0x5a>
cvttss2si %xmm2,%r10d
jmp    115a <ffr4fi2+0x5a>
test   %rsi,%rsi
jle    1247 <ffr4fi2+0x147>
xor    %eax,%eax
movsd  0xe5e(%rip),%xmm2
mov    0x2e2f(%rip),%r8
movsd  0xe57(%rip),%xmm3
mov    0x2e18(%rip),%r9
xorpd  %xmm4,%xmm4
movsd  0xe54(%rip),%xmm5
movsd  0xe44(%rip),%xmm6
jmp    11f8 <ffr4fi2+0xf8>
cs nopw 0x0(%rax,%rax,1)
movl   $0xfffffff5,(%rcx)
movzwl (%r8),%r10d
mov    %r10w,(%rdx,%rax,2)
add    $0x1,%rax
cmp    %rax,%rsi
je     1247 <ffr4fi2+0x147>
movss  (%rdi,%rax,4),%xmm7
cvtss2sd %xmm7,%xmm7
subsd  %xmm1,%xmm7
divsd  %xmm0,%xmm7
ucomisd %xmm7,%xmm2
ja     11e0 <ffr4fi2+0xe0>
ucomisd %xmm3,%xmm7
jbe    1230 <ffr4fi2+0x130>
movl   $0xfffffff5,(%rcx)
movzwl (%r9),%r10d
jmp    11ea <ffr4fi2+0xea>
cs nopw 0x0(%rax,%rax,1)
nopl   0x0(%rax,%rax,1)
ucomisd %xmm4,%xmm7
jae    123c <ffr4fi2+0x13c>
addsd  %xmm5,%xmm7
jmp    1240 <ffr4fi2+0x140>
addsd  %xmm6,%xmm7
cvttsd2si %xmm7,%r10d
jmp    11ea <ffr4fi2+0xea>
mov    (%rcx),%eax
ret

LLVM IR (-O0):
@SHRT_MIN = global i16 0
@SHRT_MAX = global i16 0
define i32 @ffr4fi2(float* %0, i64 %1, double %2, double %3, i16* %4, i32* %5) {
%7 = alloca float*
%8 = alloca i64
%9 = alloca double
%10 = alloca double
%11 = alloca i16*
%12 = alloca i32*
%13 = alloca i64
%14 = alloca double
store float* %0, float** %7
store i64 %1, i64* %8
store double %2, double* %9
store double %3, double* %10
store i16* %4, i16** %11
store i32* %5, i32** %12
%15 = load double, double* %9
%16 = fcmp oeq double %15, 1.000000e+00
br i1 %16, label %17, label %66
17: ; preds = %6
%18 = load double, double* %10
%19 = fcmp oeq double %18, 0.000000e+00
br i1 %19, label %20, label %66
20: ; preds = %17
store i64 0, i64* %13
br label %21
21: ; preds = %62, %20
%22 = load i64, i64* %13
%23 = load i64, i64* %8
%24 = icmp slt i64 %22, %23
br i1 %24, label %25, label %65
25: ; preds = %21
%26 = load float*, float** %7
%27 = load i64, i64* %13
%28 = getelementptr inbounds float, float* %26, i64 %27
%29 = load float, float* %28
%30 = fpext float %29 to double
%31 = fcmp olt double %30, 0xC0E0000FAE147AE1
br i1 %31, label %32, label %38
32: ; preds = %25
%33 = load i32*, i32** %12
store i32 -11, i32* %33
%34 = load i16, i16* @SHRT_MIN
%35 = load i16*, i16** %11
%36 = load i64, i64* %13
%37 = getelementptr inbounds i16, i16* %35, i64 %36
store i16 %34, i16* %37
br label %61
38: ; preds = %25
%39 = load float*, float** %7
%40 = load i64, i64* %13
%41 = getelementptr inbounds float, float* %39, i64 %40
%42 = load float, float* %41
%43 = fpext float %42 to double
%44 = fcmp ogt double %43, 0x40DFFFDF5C28F5C3
br i1 %44, label %45, label %51
45: ; preds = %38
%46 = load i32*, i32** %12
store i32 -11, i32* %46
%47 = load i16, i16* @SHRT_MAX
%48 = load i16*, i16** %11
%49 = load i64, i64* %13
%50 = getelementptr inbounds i16, i16* %48, i64 %49
store i16 %47, i16* %50
br label %60
51: ; preds = %38
%52 = load float*, float** %7
%53 = load i64, i64* %13
%54 = getelementptr inbounds float, float* %52, i64 %53
%55 = load float, float* %54
%56 = fptosi float %55 to i16
%57 = load i16*, i16** %11
%58 = load i64, i64* %13
%59 = getelementptr inbounds i16, i16* %57, i64 %58
store i16 %56, i16* %59
br label %60
60: ; preds = %51, %45
br label %61
61: ; preds = %60, %32
br label %62
62: ; preds = %61
%63 = load i64, i64* %13
%64 = add nsw i64 %63, 1
store i64 %64, i64* %13
br label %21
65: ; preds = %21
br label %122
66: ; preds = %17, %6
store i64 0, i64* %13
br label %67
67: ; preds = %118, %66
%68 = load i64, i64* %13
%69 = load i64, i64* %8
%70 = icmp slt i64 %68, %69
br i1 %70, label %71, label %121
71: ; preds = %67
%72 = load float*, float** %7
%73 = load i64, i64* %13
%74 = getelementptr inbounds float, float* %72, i64 %73
%75 = load float, float* %74
%76 = fpext float %75 to double
%77 = load double, double* %10
%78 = fsub double %76, %77
%79 = load double, double* %9
%80 = fdiv double %78, %79
store double %80, double* %14
%81 = load double, double* %14
%82 = fcmp olt double %81, 0xC0E0000FAE147AE1
br i1 %82, label %83, label %89
83: ; preds = %71
%84 = load i32*, i32** %12
store i32 -11, i32* %84
%85 = load i16, i16* @SHRT_MIN
%86 = load i16*, i16** %11
%87 = load i64, i64* %13
%88 = getelementptr inbounds i16, i16* %86, i64 %87
store i16 %85, i16* %88
br label %117
89: ; preds = %71
%90 = load double, double* %14
%91 = fcmp ogt double %90, 0x40DFFFDF5C28F5C3
br i1 %91, label %92, label %98
92: ; preds = %89
%93 = load i32*, i32** %12
store i32 -11, i32* %93
%94 = load i16, i16* @SHRT_MAX
%95 = load i16*, i16** %11
%96 = load i64, i64* %13
%97 = getelementptr inbounds i16, i16* %95, i64 %96
store i16 %94, i16* %97
br label %116
98: ; preds = %89
%99 = load double, double* %14
%100 = fcmp oge double %99, 0.000000e+00
br i1 %100, label %101, label %108
101: ; preds = %98
%102 = load double, double* %14
%103 = fadd double %102, 5.000000e-01
%104 = fptosi double %103 to i16
%105 = load i16*, i16** %11
%106 = load i64, i64* %13
%107 = getelementptr inbounds i16, i16* %105, i64 %106
store i16 %104, i16* %107
br label %115
108: ; preds = %98
%109 = load double, double* %14
%110 = fsub double %109, 5.000000e-01
%111 = fptosi double %110 to i16
%112 = load i16*, i16** %11
%113 = load i64, i64* %13
%114 = getelementptr inbounds i16, i16* %112, i64 %113
store i16 %111, i16* %114
br label %115
115: ; preds = %108, %101
br label %116
116: ; preds = %115, %92
br label %117
117: ; preds = %116, %83
br label %118
118: ; preds = %117
%119 = load i64, i64* %13
%120 = add nsw i64 %119, 1
store i64 %120, i64* %13
br label %67
121: ; preds = %67
br label %122
122: ; preds = %121, %65
%123 = load i32*, i32** %12
%124 = load i32, i32* %123
ret i32 %124
}

LLVM IR (-O2):
@SHRT_MIN = global i16 0
@SHRT_MAX = global i16 0
define i32 @ffr4fi2(float* nocapture %0, i64 %1, double %2, double %3, i16* nocapture writeonly %4, i32* nocapture %5) {
%7 = fcmp oeq double %2, 1.000000e+00
%8 = fcmp oeq double %3, 0.000000e+00
%9 = and i1 %7, %8
%10 = icmp sgt i64 %1, 0
br i1 %9, label %12, label %11
11: ; preds = %6
br i1 %10, label %32, label %59
12: ; preds = %6
br i1 %10, label %13, label %59
13: ; preds = %12, %27
%14 = phi i64 [ %30, %27 ], [ 0, %12 ]
%15 = getelementptr inbounds float, float* %0, i64 %14
%16 = load float, float* %15
%17 = fpext float %16 to double
%18 = fcmp olt double %17, 0xC0E0000FAE147AE1
br i1 %18, label %19, label %21
19: ; preds = %13
store i32 -11, i32* %5
%20 = load i16, i16* @SHRT_MIN
br label %27
21: ; preds = %13
%22 = fcmp ogt double %17, 0x40DFFFDF5C28F5C3
br i1 %22, label %23, label %25
23: ; preds = %21
store i32 -11, i32* %5
%24 = load i16, i16* @SHRT_MAX
br label %27
25: ; preds = %21
%26 = fptosi float %16 to i16
br label %27
27: ; preds = %19, %25, %23
%28 = phi i16 [ %20, %19 ], [ %26, %25 ], [ %24, %23 ]
%29 = getelementptr inbounds i16, i16* %4, i64 %14
store i16 %28, i16* %29
%30 = add nuw nsw i64 %14, 1
%31 = icmp eq i64 %30, %1
br i1 %31, label %59, label %13
32: ; preds = %11, %54
%33 = phi i64 [ %57, %54 ], [ 0, %11 ]
%34 = getelementptr inbounds float, float* %0, i64 %33
%35 = load float, float* %34
%36 = fpext float %35 to double
%37 = fsub double %36, %3
%38 = fdiv double %37, %2
%39 = fcmp olt double %38, 0xC0E0000FAE147AE1
br i1 %39, label %40, label %42
40: ; preds = %32
store i32 -11, i32* %5
%41 = load i16, i16* @SHRT_MIN
br label %54
42: ; preds = %32
%43 = fcmp ogt double %38, 0x40DFFFDF5C28F5C3
br i1 %43, label %44, label %46
44: ; preds = %42
store i32 -11, i32* %5
%45 = load i16, i16* @SHRT_MAX
br label %54
46: ; preds = %42
%47 = fcmp ult double %38, 0.000000e+00
br i1 %47, label %51, label %48
48: ; preds = %46
%49 = fadd double %38, 5.000000e-01
%50 = fptosi double %49 to i16
br label %54
51: ; preds = %46
%52 = fadd double %38, -5.000000e-01
%53 = fptosi double %52 to i16
br label %54
54: ; preds = %40, %48, %51, %44
%55 = phi i16 [ %41, %40 ], [ %50, %48 ], [ %53, %51 ], [ %45, %44 ]
%56 = getelementptr inbounds i16, i16* %4, i64 %33
store i16 %55, i16* %56
%57 = add nuw nsw i64 %33, 1
%58 = icmp eq i64 %57, %1
br i1 %58, label %59, label %32
59: ; preds = %54, %27, %11, %12
%60 = load i32, i32* %5
ret i32 %60
}