float interpolate(float freq, double filter_curve_db[][2],
                  int number_of_points) {
  double result;
  int i;
  double freqLow, freqHigh;
  double curveLow, curveHigh;
  if (freq <= filter_curve_db[0][0]) {
    freqLow = filter_curve_db[0][0];
    curveLow = filter_curve_db[0][1];
    freqHigh = filter_curve_db[1][0];
    curveHigh = filter_curve_db[1][1];
    result = ((freq - freqLow) * curveHigh + (freqHigh - freq) * curveLow) /
             (freqHigh - freqLow);
    return (float)result;
  }
  if (freq >= filter_curve_db[number_of_points - 1][0]) {
    freqLow = filter_curve_db[number_of_points - 2][0];
    curveLow = filter_curve_db[number_of_points - 2][1];
    freqHigh = filter_curve_db[number_of_points - 1][0];
    curveHigh = filter_curve_db[number_of_points - 1][1];
    result = ((freq - freqLow) * curveHigh + (freqHigh - freq) * curveLow) /
             (freqHigh - freqLow);
    return (float)result;
  }
  i = 1;
  freqHigh = filter_curve_db[i][0];
  while (freqHigh < freq) {
    i++;
    freqHigh = filter_curve_db[i][0];
  }
  curveHigh = filter_curve_db[i][1];
  freqLow = filter_curve_db[i - 1][0];
  curveLow = filter_curve_db[i - 1][1];
  result = ((freq - freqLow) * curveHigh + (freqHigh - freq) * curveLow) /
           (freqHigh - freqLow);
  return (float)result;
}


x86 assembly (clang, -O0):
<interpolate>:
push   %rbp
mov    %rsp,%rbp
movss  %xmm0,-0x8(%rbp)
mov    %rdi,-0x10(%rbp)
mov    %esi,-0x14(%rbp)
movss  -0x8(%rbp),%xmm0
cvtss2sd %xmm0,%xmm1
mov    -0x10(%rbp),%rax
movsd  (%rax),%xmm0
ucomisd %xmm1,%xmm0
jb     11ba <interpolate+0xba>
mov    -0x10(%rbp),%rax
movsd  (%rax),%xmm0
movsd  %xmm0,-0x30(%rbp)
mov    -0x10(%rbp),%rax
movsd  0x8(%rax),%xmm0
movsd  %xmm0,-0x40(%rbp)
mov    -0x10(%rbp),%rax
movsd  0x10(%rax),%xmm0
movsd  %xmm0,-0x38(%rbp)
mov    -0x10(%rbp),%rax
movsd  0x18(%rax),%xmm0
movsd  %xmm0,-0x48(%rbp)
movss  -0x8(%rbp),%xmm0
cvtss2sd %xmm0,%xmm0
subsd  -0x30(%rbp),%xmm0
movsd  -0x48(%rbp),%xmm2
movsd  -0x38(%rbp),%xmm1
movss  -0x8(%rbp),%xmm3
cvtss2sd %xmm3,%xmm3
subsd  %xmm3,%xmm1
mulsd  -0x40(%rbp),%xmm1
mulsd  %xmm2,%xmm0
addsd  %xmm1,%xmm0
movsd  -0x38(%rbp),%xmm1
subsd  -0x30(%rbp),%xmm1
divsd  %xmm1,%xmm0
movsd  %xmm0,-0x20(%rbp)
movsd  -0x20(%rbp),%xmm0
cvtsd2ss %xmm0,%xmm0
movss  %xmm0,-0x4(%rbp)
jmp    13b3 <interpolate+0x2b3>
movss  -0x8(%rbp),%xmm0
cvtss2sd %xmm0,%xmm0
mov    -0x10(%rbp),%rax
mov    -0x14(%rbp),%ecx
sub    $0x1,%ecx
movslq %ecx,%rcx
shl    $0x4,%rcx
add    %rcx,%rax
ucomisd (%rax),%xmm0
jb     12af <interpolate+0x1af>
mov    -0x10(%rbp),%rax
mov    -0x14(%rbp),%ecx
sub    $0x2,%ecx
movslq %ecx,%rcx
shl    $0x4,%rcx
add    %rcx,%rax
movsd  (%rax),%xmm0
movsd  %xmm0,-0x30(%rbp)
mov    -0x10(%rbp),%rax
mov    -0x14(%rbp),%ecx
sub    $0x2,%ecx
movslq %ecx,%rcx
shl    $0x4,%rcx
add    %rcx,%rax
movsd  0x8(%rax),%xmm0
movsd  %xmm0,-0x40(%rbp)
mov    -0x10(%rbp),%rax
mov    -0x14(%rbp),%ecx
sub    $0x1,%ecx
movslq %ecx,%rcx
shl    $0x4,%rcx
add    %rcx,%rax
movsd  (%rax),%xmm0
movsd  %xmm0,-0x38(%rbp)
mov    -0x10(%rbp),%rax
mov    -0x14(%rbp),%ecx
sub    $0x1,%ecx
movslq %ecx,%rcx
shl    $0x4,%rcx
add    %rcx,%rax
movsd  0x8(%rax),%xmm0
movsd  %xmm0,-0x48(%rbp)
movss  -0x8(%rbp),%xmm0
cvtss2sd %xmm0,%xmm0
subsd  -0x30(%rbp),%xmm0
movsd  -0x48(%rbp),%xmm2
movsd  -0x38(%rbp),%xmm1
movss  -0x8(%rbp),%xmm3
cvtss2sd %xmm3,%xmm3
subsd  %xmm3,%xmm1
mulsd  -0x40(%rbp),%xmm1
mulsd  %xmm2,%xmm0
addsd  %xmm1,%xmm0
movsd  -0x38(%rbp),%xmm1
subsd  -0x30(%rbp),%xmm1
divsd  %xmm1,%xmm0
movsd  %xmm0,-0x20(%rbp)
movsd  -0x20(%rbp),%xmm0
cvtsd2ss %xmm0,%xmm0
movss  %xmm0,-0x4(%rbp)
jmp    13b3 <interpolate+0x2b3>
movl   $0x1,-0x24(%rbp)
mov    -0x10(%rbp),%rax
movslq -0x24(%rbp),%rcx
shl    $0x4,%rcx
add    %rcx,%rax
movsd  (%rax),%xmm0
movsd  %xmm0,-0x38(%rbp)
movsd  -0x38(%rbp),%xmm1
movss  -0x8(%rbp),%xmm0
cvtss2sd %xmm0,%xmm0
ucomisd %xmm1,%xmm0
jbe    130c <interpolate+0x20c>
mov    -0x24(%rbp),%eax
add    $0x1,%eax
mov    %eax,-0x24(%rbp)
mov    -0x10(%rbp),%rax
movslq -0x24(%rbp),%rcx
shl    $0x4,%rcx
add    %rcx,%rax
movsd  (%rax),%xmm0
movsd  %xmm0,-0x38(%rbp)
jmp    12ce <interpolate+0x1ce>
mov    -0x10(%rbp),%rax
movslq -0x24(%rbp),%rcx
shl    $0x4,%rcx
add    %rcx,%rax
movsd  0x8(%rax),%xmm0
movsd  %xmm0,-0x48(%rbp)
mov    -0x10(%rbp),%rax
mov    -0x24(%rbp),%ecx
sub    $0x1,%ecx
movslq %ecx,%rcx
shl    $0x4,%rcx
add    %rcx,%rax
movsd  (%rax),%xmm0
movsd  %xmm0,-0x30(%rbp)
mov    -0x10(%rbp),%rax
mov    -0x24(%rbp),%ecx
sub    $0x1,%ecx
movslq %ecx,%rcx
shl    $0x4,%rcx
add    %rcx,%rax
movsd  0x8(%rax),%xmm0
movsd  %xmm0,-0x40(%rbp)
movss  -0x8(%rbp),%xmm0
cvtss2sd %xmm0,%xmm0
subsd  -0x30(%rbp),%xmm0
movsd  -0x48(%rbp),%xmm2
movsd  -0x38(%rbp),%xmm1
movss  -0x8(%rbp),%xmm3
cvtss2sd %xmm3,%xmm3
subsd  %xmm3,%xmm1
mulsd  -0x40(%rbp),%xmm1
mulsd  %xmm2,%xmm0
addsd  %xmm1,%xmm0
movsd  -0x38(%rbp),%xmm1
subsd  -0x30(%rbp),%xmm1
divsd  %xmm1,%xmm0
movsd  %xmm0,-0x20(%rbp)
movsd  -0x20(%rbp),%xmm0
cvtsd2ss %xmm0,%xmm0
movss  %xmm0,-0x4(%rbp)
movss  -0x4(%rbp),%xmm0
pop    %rbp
ret

x86 assembly (clang, -O2):
<interpolate>:
cvtss2sd %xmm0,%xmm0
movsd  (%rdi),%xmm1
ucomisd %xmm0,%xmm1
jae    118d <interpolate+0x8d>
movslq %esi,%rcx
lea    -0x1(%rcx),%rax
shl    $0x4,%rax
movsd  (%rdi,%rax,1),%xmm1
ucomisd %xmm1,%xmm0
jae    11b9 <interpolate+0xb9>
movsd  0x10(%rdi),%xmm1
mov    $0x1,%eax
ucomisd %xmm1,%xmm0
jbe    1161 <interpolate+0x61>
lea    0x20(%rdi),%rcx
mov    $0x1,%eax
cs nopw 0x0(%rax,%rax,1)
nopl   0x0(%rax,%rax,1)
movsd  (%rcx),%xmm1
add    $0x1,%eax
add    $0x10,%rcx
ucomisd %xmm1,%xmm0
ja     1150 <interpolate+0x50>
mov    %eax,%ecx
shl    $0x4,%rcx
cltq
shl    $0x4,%rax
movsd  -0x10(%rax,%rdi,1),%xmm2
movapd %xmm1,%xmm3
subsd  %xmm0,%xmm3
subsd  %xmm2,%xmm0
mulsd  -0x8(%rax,%rdi,1),%xmm3
mulsd  0x8(%rdi,%rcx,1),%xmm0
jmp    11db <interpolate+0xdb>
movsd  0x10(%rdi),%xmm2
movapd %xmm2,%xmm3
subsd  %xmm0,%xmm3
subsd  %xmm1,%xmm0
mulsd  0x8(%rdi),%xmm3
mulsd  0x18(%rdi),%xmm0
addsd  %xmm3,%xmm0
subsd  %xmm1,%xmm2
divsd  %xmm2,%xmm0
cvtsd2ss %xmm0,%xmm0
ret
shl    $0x4,%rcx
movsd  -0x20(%rcx,%rdi,1),%xmm2
movapd %xmm1,%xmm3
subsd  %xmm0,%xmm3
subsd  %xmm2,%xmm0
mulsd  -0x18(%rcx,%rdi,1),%xmm3
mulsd  0x8(%rdi,%rax,1),%xmm0
addsd  %xmm3,%xmm0
subsd  %xmm2,%xmm1
divsd  %xmm1,%xmm0
cvtsd2ss %xmm0,%xmm0
ret

LLVM IR (-O0):
define float @interpolate(float %0, [2 x double]* %1, i32 %2) {
%4 = alloca float
%5 = alloca float
%6 = alloca [2 x double]*
%7 = alloca i32
%8 = alloca double
%9 = alloca i32
%10 = alloca double
%11 = alloca double
%12 = alloca double
%13 = alloca double
store float %0, float* %5
store [2 x double]* %1, [2 x double]** %6
store i32 %2, i32* %7
%14 = load float, float* %5
%15 = fpext float %14 to double
%16 = load [2 x double]*, [2 x double]** %6
%17 = getelementptr inbounds [2 x double], [2 x double]* %16, i64 0
%18 = getelementptr inbounds [2 x double], [2 x double]* %17, i64 0, i64 0
%19 = load double, double* %18
%20 = fcmp ole double %15, %19
br i1 %20, label %21, label %56
21: ; preds = %3
%22 = load [2 x double]*, [2 x double]** %6
%23 = getelementptr inbounds [2 x double], [2 x double]* %22, i64 0
%24 = getelementptr inbounds [2 x double], [2 x double]* %23, i64 0, i64 0
%25 = load double, double* %24
store double %25, double* %10
%26 = load [2 x double]*, [2 x double]** %6
%27 = getelementptr inbounds [2 x double], [2 x double]* %26, i64 0
%28 = getelementptr inbounds [2 x double], [2 x double]* %27, i64 0, i64 1
%29 = load double, double* %28
store double %29, double* %12
%30 = load [2 x double]*, [2 x double]** %6
%31 = getelementptr inbounds [2 x double], [2 x double]* %30, i64 1
%32 = getelementptr inbounds [2 x double], [2 x double]* %31, i64 0, i64 0
%33 = load double, double* %32
store double %33, double* %11
%34 = load [2 x double]*, [2 x double]** %6
%35 = getelementptr inbounds [2 x double], [2 x double]* %34, i64 1
%36 = getelementptr inbounds [2 x double], [2 x double]* %35, i64 0, i64 1
%37 = load double, double* %36
store double %37, double* %13
%38 = load float, float* %5
%39 = fpext float %38 to double
%40 = load double, double* %10
%41 = fsub double %39, %40
%42 = load double, double* %13
%43 = load double, double* %11
%44 = load float, float* %5
%45 = fpext float %44 to double
%46 = fsub double %43, %45
%47 = load double, double* %12
%48 = fmul double %46, %47
%49 = call double @llvm.fmuladd.f64(double %41, double %42, double %48)
%50 = load double, double* %11
%51 = load double, double* %10
%52 = fsub double %50, %51
%53 = fdiv double %49, %52
store double %53, double* %8
%54 = load double, double* %8
%55 = fptrunc double %54 to float
store float %55, float* %4
br label %174
56: ; preds = %3
%57 = load float, float* %5
%58 = fpext float %57 to double
%59 = load [2 x double]*, [2 x double]** %6
%60 = load i32, i32* %7
%61 = sub nsw i32 %60, 1
%62 = sext i32 %61 to i64
%63 = getelementptr inbounds [2 x double], [2 x double]* %59, i64 %62
%64 = getelementptr inbounds [2 x double], [2 x double]* %63, i64 0, i64 0
%65 = load double, double* %64
%66 = fcmp oge double %58, %65
br i1 %66, label %67, label %114
67: ; preds = %56
%68 = load [2 x double]*, [2 x double]** %6
%69 = load i32, i32* %7
%70 = sub nsw i32 %69, 2
%71 = sext i32 %70 to i64
%72 = getelementptr inbounds [2 x double], [2 x double]* %68, i64 %71
%73 = getelementptr inbounds [2 x double], [2 x double]* %72, i64 0, i64 0
%74 = load double, double* %73
store double %74, double* %10
%75 = load [2 x double]*, [2 x double]** %6
%76 = load i32, i32* %7
%77 = sub nsw i32 %76, 2
%78 = sext i32 %77 to i64
%79 = getelementptr inbounds [2 x double], [2 x double]* %75, i64 %78
%80 = getelementptr inbounds [2 x double], [2 x double]* %79, i64 0, i64 1
%81 = load double, double* %80
store double %81, double* %12
%82 = load [2 x double]*, [2 x double]** %6
%83 = load i32, i32* %7
%84 = sub nsw i32 %83, 1
%85 = sext i32 %84 to i64
%86 = getelementptr inbounds [2 x double], [2 x double]* %82, i64 %85
%87 = getelementptr inbounds [2 x double], [2 x double]* %86, i64 0, i64 0
%88 = load double, double* %87
store double %88, double* %11
%89 = load [2 x double]*, [2 x double]** %6
%90 = load i32, i32* %7
%91 = sub nsw i32 %90, 1
%92 = sext i32 %91 to i64
%93 = getelementptr inbounds [2 x double], [2 x double]* %89, i64 %92
%94 = getelementptr inbounds [2 x double], [2 x double]* %93, i64 0, i64 1
%95 = load double, double* %94
store double %95, double* %13
%96 = load float, float* %5
%97 = fpext float %96 to double
%98 = load double, double* %10
%99 = fsub double %97, %98
%100 = load double, double* %13
%101 = load double, double* %11
%102 = load float, float* %5
%103 = fpext float %102 to double
%104 = fsub double %101, %103
%105 = load double, double* %12
%106 = fmul double %104, %105
%107 = call double @llvm.fmuladd.f64(double %99, double %100, double %106)
%108 = load double, double* %11
%109 = load double, double* %10
%110 = fsub double %108, %109
%111 = fdiv double %107, %110
store double %111, double* %8
%112 = load double, double* %8
%113 = fptrunc double %112 to float
store float %113, float* %4
br label %174
114: ; preds = %56
store i32 1, i32* %9
%115 = load [2 x double]*, [2 x double]** %6
%116 = load i32, i32* %9
%117 = sext i32 %116 to i64
%118 = getelementptr inbounds [2 x double], [2 x double]* %115, i64 %117
%119 = getelementptr inbounds [2 x double], [2 x double]* %118, i64 0, i64 0
%120 = load double, double* %119
store double %120, double* %11
br label %121
121: ; preds = %126, %114
%122 = load double, double* %11
%123 = load float, float* %5
%124 = fpext float %123 to double
%125 = fcmp olt double %122, %124
br i1 %125, label %126, label %135
126: ; preds = %121
%127 = load i32, i32* %9
%128 = add nsw i32 %127, 1
store i32 %128, i32* %9
%129 = load [2 x double]*, [2 x double]** %6
%130 = load i32, i32* %9
%131 = sext i32 %130 to i64
%132 = getelementptr inbounds [2 x double], [2 x double]* %129, i64 %131
%133 = getelementptr inbounds [2 x double], [2 x double]* %132, i64 0, i64 0
%134 = load double, double* %133
store double %134, double* %11
br label %121
135: ; preds = %121
%136 = load [2 x double]*, [2 x double]** %6
%137 = load i32, i32* %9
%138 = sext i32 %137 to i64
%139 = getelementptr inbounds [2 x double], [2 x double]* %136, i64 %138
%140 = getelementptr inbounds [2 x double], [2 x double]* %139, i64 0, i64 1
%141 = load double, double* %140
store double %141, double* %13
%142 = load [2 x double]*, [2 x double]** %6
%143 = load i32, i32* %9
%144 = sub nsw i32 %143, 1
%145 = sext i32 %144 to i64
%146 = getelementptr inbounds [2 x double], [2 x double]* %142, i64 %145
%147 = getelementptr inbounds [2 x double], [2 x double]* %146, i64 0, i64 0
%148 = load double, double* %147
store double %148, double* %10
%149 = load [2 x double]*, [2 x double]** %6
%150 = load i32, i32* %9
%151 = sub nsw i32 %150, 1
%152 = sext i32 %151 to i64
%153 = getelementptr inbounds [2 x double], [2 x double]* %149, i64 %152
%154 = getelementptr inbounds [2 x double], [2 x double]* %153, i64 0, i64 1
%155 = load double, double* %154
store double %155, double* %12
%156 = load float, float* %5
%157 = fpext float %156 to double
%158 = load double, double* %10
%159 = fsub double %157, %158
%160 = load double, double* %13
%161 = load double, double* %11
%162 = load float, float* %5
%163 = fpext float %162 to double
%164 = fsub double %161, %163
%165 = load double, double* %12
%166 = fmul double %164, %165
%167 = call double @llvm.fmuladd.f64(double %159, double %160, double %166)
%168 = load double, double* %11
%169 = load double, double* %10
%170 = fsub double %168, %169
%171 = fdiv double %167, %170
store double %171, double* %8
%172 = load double, double* %8
%173 = fptrunc double %172 to float
store float %173, float* %4
br label %174
174: ; preds = %135, %67, %21
%175 = load float, float* %4
ret float %175
}

LLVM IR (-O2):
define float @interpolate(float %0, [2 x double]* nocapture %1, i32 %2) {
%4 = fpext float %0 to double
%5 = getelementptr inbounds [2 x double], [2 x double]* %1, i64 0, i64 0
%6 = load double, double* %5
%7 = fcmp ult double %6, %4
br i1 %7, label %21, label %8
8: ; preds = %3
%9 = getelementptr inbounds [2 x double], [2 x double]* %1, i64 0, i64 1
%10 = load double, double* %9
%11 = getelementptr inbounds [2 x double], [2 x double]* %1, i64 1, i64 0
%12 = load double, double* %11
%13 = getelementptr inbounds [2 x double], [2 x double]* %1, i64 1, i64 1
%14 = load double, double* %13
%15 = fsub double %4, %6
%16 = fsub double %12, %4
%17 = fmul double %10, %16
%18 = tail call double @llvm.fmuladd.f64(double %15, double %14, double %17)
%19 = fsub double %12, %6
%20 = fdiv double %18, %19
br label %72
21: ; preds = %3
%22 = add nsw i32 %2, -1
%23 = sext i32 %22 to i64
%24 = getelementptr inbounds [2 x double], [2 x double]* %1, i64 %23, i64 0
%25 = load double, double* %24
%26 = fcmp ugt double %25, %4
br i1 %26, label %42, label %27
27: ; preds = %21
%28 = add nsw i32 %2, -2
%29 = sext i32 %28 to i64
%30 = getelementptr inbounds [2 x double], [2 x double]* %1, i64 %29, i64 0
%31 = load double, double* %30
%32 = getelementptr inbounds [2 x double], [2 x double]* %1, i64 %29, i64 1
%33 = load double, double* %32
%34 = getelementptr inbounds [2 x double], [2 x double]* %1, i64 %23, i64 1
%35 = load double, double* %34
%36 = fsub double %4, %31
%37 = fsub double %25, %4
%38 = fmul double %37, %33
%39 = tail call double @llvm.fmuladd.f64(double %36, double %35, double %38)
%40 = fsub double %25, %31
%41 = fdiv double %39, %40
br label %72
42: ; preds = %21
%43 = getelementptr inbounds [2 x double], [2 x double]* %1, i64 1, i64 0
%44 = load double, double* %43
%45 = fcmp olt double %44, %4
br i1 %45, label %46, label %54
46: ; preds = %42, %46
%47 = phi i64 [ %48, %46 ], [ 1, %42 ]
%48 = add nuw nsw i64 %47, 1
%49 = getelementptr inbounds [2 x double], [2 x double]* %1, i64 %48, i64 0
%50 = load double, double* %49
%51 = fcmp olt double %50, %4
br i1 %51, label %46, label %52
52: ; preds = %46
%53 = trunc i64 %48 to i32
br label %54
54: ; preds = %52, %42
%55 = phi i32 [ 1, %42 ], [ %53, %52 ]
%56 = phi double [ %44, %42 ], [ %50, %52 ]
%57 = zext i32 %55 to i64
%58 = getelementptr inbounds [2 x double], [2 x double]* %1, i64 %57, i64 1
%59 = load double, double* %58
%60 = add nsw i32 %55, -1
%61 = sext i32 %60 to i64
%62 = getelementptr inbounds [2 x double], [2 x double]* %1, i64 %61, i64 0
%63 = load double, double* %62
%64 = getelementptr inbounds [2 x double], [2 x double]* %1, i64 %61, i64 1
%65 = load double, double* %64
%66 = fsub double %4, %63
%67 = fsub double %56, %4
%68 = fmul double %67, %65
%69 = tail call double @llvm.fmuladd.f64(double %66, double %59, double %68)
%70 = fsub double %56, %63
%71 = fdiv double %69, %70
br label %72
72: ; preds = %54, %27, %8
%73 = phi double [ %20, %8 ], [ %41, %27 ], [ %71, %54 ]
%74 = fptrunc double %73 to float
ret float %74
}