SDL: audio: Prebake the resampler's kaiser table instead of doing it at runtime.

From de019568dc948a01a3789b487a896c5e0d495b94 Mon Sep 17 00:00:00 2001
From: "Ryan C. Gordon" <[EMAIL REDACTED]>
Date: Sat, 9 Apr 2022 23:43:57 -0400
Subject: [PATCH] audio: Prebake the resampler's kaiser table instead of doing
 it at runtime.

---
 build-scripts/gen_audio_resampler_filter.c | 162 ++++
 src/audio/SDL_audio.c                      |   2 -
 src/audio/SDL_audio_c.h                    |   5 -
 src/audio/SDL_audio_resampler_filter.h     | 890 +++++++++++++++++++++
 src/audio/SDL_audiocvt.c                   | 105 +--
 5 files changed, 1054 insertions(+), 110 deletions(-)
 create mode 100644 build-scripts/gen_audio_resampler_filter.c
 create mode 100644 src/audio/SDL_audio_resampler_filter.h

diff --git a/build-scripts/gen_audio_resampler_filter.c b/build-scripts/gen_audio_resampler_filter.c
new file mode 100644
index 00000000000..fbc5c905d39
--- /dev/null
+++ b/build-scripts/gen_audio_resampler_filter.c
@@ -0,0 +1,162 @@
+/*
+  Simple DirectMedia Layer
+  Copyright (C) 1997-2022 Sam Lantinga <slouken@libsdl.org>
+
+  This software is provided 'as-is', without any express or implied
+  warranty.  In no event will the authors be held liable for any damages
+  arising from the use of this software.
+
+  Permission is granted to anyone to use this software for any purpose,
+  including commercial applications, and to alter it and redistribute it
+  freely, subject to the following restrictions:
+
+  1. The origin of this software must not be misrepresented; you must not
+     claim that you wrote the original software. If you use this software
+     in a product, an acknowledgment in the product documentation would be
+     appreciated but is not required.
+  2. Altered source versions must be plainly marked as such, and must not be
+     misrepresented as being the original software.
+  3. This notice may not be removed or altered from any source distribution.
+*/
+
+/*
+
+Built with:
+
+gcc -o genfilter build-scripts/gen_audio_resampler_filter.c -lm && ./genfilter > src/audio/SDL_audio_resampler_filter.h
+
+ */
+
+/*
+   SDL's resampler uses a "bandlimited interpolation" algorithm:
+     https://ccrma.stanford.edu/~jos/resample/
+
+   This code pre-generates the kaiser tables so we don't have to do this at
+   run time, at a cost of about 20 kilobytes of static data in SDL. This code
+   used to be part of SDL itself and generated the tables on the first use,
+   but that was expensive to produce on platforms without floating point
+   hardware.
+*/
+
+#include <stdio.h>
+#include <math.h>
+
+#define RESAMPLER_ZERO_CROSSINGS 5
+#define RESAMPLER_BITS_PER_SAMPLE 16
+#define RESAMPLER_SAMPLES_PER_ZERO_CROSSING  (1 << ((RESAMPLER_BITS_PER_SAMPLE / 2) + 1))
+#define RESAMPLER_FILTER_SIZE ((RESAMPLER_SAMPLES_PER_ZERO_CROSSING * RESAMPLER_ZERO_CROSSINGS) + 1)
+
+/* This is a "modified" bessel function, so you can't use POSIX j0() */
+static double
+bessel(const double x)
+{
+    const double xdiv2 = x / 2.0;
+    double i0 = 1.0f;
+    double f = 1.0f;
+    int i = 1;
+
+    while (1) {
+        const double diff = pow(xdiv2, i * 2) / pow(f, 2);
+        if (diff < 1.0e-21f) {
+            break;
+        }
+        i0 += diff;
+        i++;
+        f *= (double) i;
+    }
+
+    return i0;
+}
+
+/* build kaiser table with cardinal sine applied to it, and array of differences between elements. */
+static void
+kaiser_and_sinc(float *table, float *diffs, const int tablelen, const double beta)
+{
+    const int lenm1 = tablelen - 1;
+    const int lenm1div2 = lenm1 / 2;
+    int i;
+
+    table[0] = 1.0f;
+    for (i = 1; i < tablelen; i++) {
+        const double kaiser = bessel(beta * sqrt(1.0 - pow(((i - lenm1) / 2.0) / lenm1div2, 2.0))) / bessel(beta);
+        table[tablelen - i] = (float) kaiser;
+    }
+
+    for (i = 1; i < tablelen; i++) {
+        const float x = (((float) i) / ((float) RESAMPLER_SAMPLES_PER_ZERO_CROSSING)) * ((float) M_PI);
+        table[i] *= sinf(x) / x;
+        diffs[i - 1] = table[i] - table[i - 1];
+    }
+    diffs[lenm1] = 0.0f;
+}
+
+
+static float ResamplerFilter[RESAMPLER_FILTER_SIZE];
+static float ResamplerFilterDifference[RESAMPLER_FILTER_SIZE];
+
+static void
+PrepareResampleFilter(void)
+{
+    /* if dB > 50, beta=(0.1102 * (dB - 8.7)), according to Matlab. */
+    const double dB = 80.0;
+    const double beta = 0.1102 * (dB - 8.7);
+    kaiser_and_sinc(ResamplerFilter, ResamplerFilterDifference, RESAMPLER_FILTER_SIZE, beta);
+}
+
+int main(void)
+{
+    int i;
+
+    PrepareResampleFilter();
+
+    printf(
+        "/*\n"
+        "  Simple DirectMedia Layer\n"
+        "  Copyright (C) 1997-2022 Sam Lantinga <slouken@libsdl.org>\n"
+        "\n"
+        "  This software is provided 'as-is', without any express or implied\n"
+        "  warranty.  In no event will the authors be held liable for any damages\n"
+        "  arising from the use of this software.\n"
+        "\n"
+        "  Permission is granted to anyone to use this software for any purpose,\n"
+        "  including commercial applications, and to alter it and redistribute it\n"
+        "  freely, subject to the following restrictions:\n"
+        "\n"
+        "  1. The origin of this software must not be misrepresented; you must not\n"
+        "     claim that you wrote the original software. If you use this software\n"
+        "     in a product, an acknowledgment in the product documentation would be\n"
+        "     appreciated but is not required.\n"
+        "  2. Altered source versions must be plainly marked as such, and must not be\n"
+        "     misrepresented as being the original software.\n"
+        "  3. This notice may not be removed or altered from any source distribution.\n"
+        "*/\n"
+        "\n"
+        "/* DO NOT EDIT, THIS FILE WAS GENERATED BY build-scripts/gen_audio_resampler_filter.c */\n"
+        "\n"
+        "#define RESAMPLER_ZERO_CROSSINGS %d\n"
+        "#define RESAMPLER_BITS_PER_SAMPLE %d\n"
+        "#define RESAMPLER_SAMPLES_PER_ZERO_CROSSING (1 << ((RESAMPLER_BITS_PER_SAMPLE / 2) + 1))\n"
+        "#define RESAMPLER_FILTER_SIZE ((RESAMPLER_SAMPLES_PER_ZERO_CROSSING * RESAMPLER_ZERO_CROSSINGS) + 1)\n"
+        "\n", RESAMPLER_ZERO_CROSSINGS, RESAMPLER_BITS_PER_SAMPLE
+    );
+
+    printf("static const float ResamplerFilter[RESAMPLER_FILTER_SIZE] = {\n");
+    printf("    %ff", ResamplerFilter[0]);
+    for (i = 0; i < RESAMPLER_FILTER_SIZE-1; i++) {
+        printf("%s%ff", ((i % 6) == 5) ? ",\n    " : ", ", ResamplerFilter[i+1]);
+    }
+    printf("\n};\n\n");
+
+    printf("static const float ResamplerFilterDifference[RESAMPLER_FILTER_SIZE] = {\n");
+    printf("    %ff", ResamplerFilterDifference[0]);
+    for (i = 0; i < RESAMPLER_FILTER_SIZE-1; i++) {
+        printf("%s%ff", ((i % 6) == 5) ? ",\n    " : ", ", ResamplerFilterDifference[i+1]);
+    }
+    printf("\n};\n\n");
+    printf("/* vi: set ts=4 sw=4 expandtab: */\n\n");
+
+    return 0;
+}
+
+/* vi: set ts=4 sw=4 expandtab: */
+
diff --git a/src/audio/SDL_audio.c b/src/audio/SDL_audio.c
index fb363f77141..ac3ac1fc2c8 100644
--- a/src/audio/SDL_audio.c
+++ b/src/audio/SDL_audio.c
@@ -1649,8 +1649,6 @@ SDL_AudioQuit(void)
 #ifdef HAVE_LIBSAMPLERATE_H
     UnloadLibSampleRate();
 #endif
-
-    SDL_FreeResampleFilter();
 }
 
 #define NUM_FORMATS 10
diff --git a/src/audio/SDL_audio_c.h b/src/audio/SDL_audio_c.h
index cddaecef03f..bfa0760de59 100644
--- a/src/audio/SDL_audio_c.h
+++ b/src/audio/SDL_audio_c.h
@@ -70,11 +70,6 @@ extern SDL_AudioFilter SDL_Convert_F32_to_S16;
 extern SDL_AudioFilter SDL_Convert_F32_to_U16;
 extern SDL_AudioFilter SDL_Convert_F32_to_S32;
 
-/* You need to call SDL_PrepareResampleFilter() before using the internal resampler.
-   SDL_AudioQuit() calls SDL_FreeResamplerFilter(), you should never call it yourself. */
-extern int SDL_PrepareResampleFilter(void);
-extern void SDL_FreeResampleFilter(void);
-
 #endif /* SDL_audio_c_h_ */
 
 /* vi: set ts=4 sw=4 expandtab: */
diff --git a/src/audio/SDL_audio_resampler_filter.h b/src/audio/SDL_audio_resampler_filter.h
new file mode 100644
index 00000000000..7725d6499e9
--- /dev/null
+++ b/src/audio/SDL_audio_resampler_filter.h
@@ -0,0 +1,890 @@
+/*
+  Simple DirectMedia Layer
+  Copyright (C) 1997-2022 Sam Lantinga <slouken@libsdl.org>
+
+  This software is provided 'as-is', without any express or implied
+  warranty.  In no event will the authors be held liable for any damages
+  arising from the use of this software.
+
+  Permission is granted to anyone to use this software for any purpose,
+  including commercial applications, and to alter it and redistribute it
+  freely, subject to the following restrictions:
+
+  1. The origin of this software must not be misrepresented; you must not
+     claim that you wrote the original software. If you use this software
+     in a product, an acknowledgment in the product documentation would be
+     appreciated but is not required.
+  2. Altered source versions must be plainly marked as such, and must not be
+     misrepresented as being the original software.
+  3. This notice may not be removed or altered from any source distribution.
+*/
+
+/* DO NOT EDIT, THIS FILE WAS GENERATED BY build-scripts/gen_audio_resampler_filter.c */
+
+#define RESAMPLER_ZERO_CROSSINGS 5
+#define RESAMPLER_BITS_PER_SAMPLE 16
+#define RESAMPLER_SAMPLES_PER_ZERO_CROSSING (1 << ((RESAMPLER_BITS_PER_SAMPLE / 2) + 1))
+#define RESAMPLER_FILTER_SIZE ((RESAMPLER_SAMPLES_PER_ZERO_CROSSING * RESAMPLER_ZERO_CROSSINGS) + 1)
+
+static const float ResamplerFilter[RESAMPLER_FILTER_SIZE] = {
+    1.000000f, 0.999994f, 0.999974f, 0.999941f, 0.999895f, 0.999834f,
+    0.999760f, 0.999672f, 0.999571f, 0.999456f, 0.999327f, 0.999185f,
+    0.999029f, 0.998859f, 0.998676f, 0.998479f, 0.998269f, 0.998044f,
+    0.997807f, 0.997555f, 0.997290f, 0.997012f, 0.996720f, 0.996414f,
+    0.996094f, 0.995762f, 0.995415f, 0.995055f, 0.994682f, 0.994295f,
+    0.993894f, 0.993480f, 0.993052f, 0.992611f, 0.992157f, 0.991689f,
+    0.991207f, 0.990713f, 0.990204f, 0.989683f, 0.989148f, 0.988599f,
+    0.988037f, 0.987462f, 0.986874f, 0.986272f, 0.985657f, 0.985028f,
+    0.984387f, 0.983732f, 0.983064f, 0.982382f, 0.981688f, 0.980980f,
+    0.980259f, 0.979525f, 0.978778f, 0.978018f, 0.977245f, 0.976458f,
+    0.975659f, 0.974847f, 0.974021f, 0.973183f, 0.972332f, 0.971468f,
+    0.970591f, 0.969701f, 0.968798f, 0.967882f, 0.966954f, 0.966013f,
+    0.965059f, 0.964092f, 0.963113f, 0.962120f, 0.961116f, 0.960098f,
+    0.959068f, 0.958026f, 0.956971f, 0.955903f, 0.954823f, 0.953731f,
+    0.952626f, 0.951509f, 0.950379f, 0.949237f, 0.948083f, 0.946917f,
+    0.945738f, 0.944547f, 0.943344f, 0.942128f, 0.940901f, 0.939661f,
+    0.938410f, 0.937146f, 0.935871f, 0.934583f, 0.933284f, 0.931973f,
+    0.930650f, 0.929315f, 0.927968f, 0.926610f, 0.925240f, 0.923858f,
+    0.922465f, 0.921060f, 0.919644f, 0.918216f, 0.916776f, 0.915325f,
+    0.913863f, 0.912390f, 0.910905f, 0.909408f, 0.907901f, 0.906382f,
+    0.904853f, 0.903312f, 0.901760f, 0.900197f, 0.898623f, 0.897038f,
+    0.895442f, 0.893835f, 0.892218f, 0.890590f, 0.888951f, 0.887301f,
+    0.885641f, 0.883970f, 0.882288f, 0.880596f, 0.878894f, 0.877181f,
+    0.875457f, 0.873724f, 0.871980f, 0.870226f, 0.868461f, 0.866687f,
+    0.864902f, 0.863107f, 0.861303f, 0.859488f, 0.857664f, 0.855829f,
+    0.853985f, 0.852131f, 0.850267f, 0.848394f, 0.846511f, 0.844618f,
+    0.842716f, 0.840805f, 0.838884f, 0.836953f, 0.835014f, 0.833065f,
+    0.831107f, 0.829139f, 0.827163f, 0.825177f, 0.823183f, 0.821179f,
+    0.819167f, 0.817146f, 0.815116f, 0.813077f, 0.811029f, 0.808973f,
+    0.806909f, 0.804835f, 0.802754f, 0.800664f, 0.798565f, 0.796458f,
+    0.794343f, 0.792220f, 0.790088f, 0.787949f, 0.785801f, 0.783645f,
+    0.781482f, 0.779310f, 0.777131f, 0.774944f, 0.772750f, 0.770547f,
+    0.768337f, 0.766120f, 0.763895f, 0.761662f, 0.759423f, 0.757176f,
+    0.754921f, 0.752660f, 0.750391f, 0.748115f, 0.745833f, 0.743543f,
+    0.741246f, 0.738943f, 0.736633f, 0.734316f, 0.731992f, 0.729662f,
+    0.727325f, 0.724982f, 0.722632f, 0.720276f, 0.717914f, 0.715545f,
+    0.713171f, 0.710790f, 0.708403f, 0.706010f, 0.703611f, 0.701206f,
+    0.698795f, 0.696379f, 0.693957f, 0.691529f, 0.689096f, 0.686657f,
+    0.684213f, 0.681763f, 0.679308f, 0.676847f, 0.674382f, 0.671911f,
+    0.669436f, 0.666955f, 0.664469f, 0.661978f, 0.659483f, 0.656983f,
+    0.654477f, 0.651968f, 0.649454f, 0.646935f, 0.644412f, 0.641884f,
+    0.639352f, 0.636816f, 0.634275f, 0.631731f, 0.629182f, 0.626629f,
+    0.624072f, 0.621512f, 0.618947f, 0.616379f, 0.613807f, 0.611232f,
+    0.608652f, 0.606070f, 0.603484f, 0.600894f, 0.598301f, 0.595705f,
+    0.593106f, 0.590503f, 0.587898f, 0.585289f, 0.582677f, 0.580063f,
+    0.577446f, 0.574826f, 0.572203f, 0.569578f, 0.566950f, 0.564319f,
+    0.561686f, 0.559051f, 0.556414f, 0.553774f, 0.551132f, 0.548488f,
+    0.545841f, 0.543193f, 0.540543f, 0.537891f, 0.535237f, 0.532582f,
+    0.529924f, 0.527265f, 0.524605f, 0.521943f, 0.519280f, 0.516615f,
+    0.513949f, 0.511281f, 0.508613f, 0.505943f, 0.503273f, 0.500601f,
+    0.497928f, 0.495255f, 0.492581f, 0.489906f, 0.487230f, 0.484554f,
+    0.481877f, 0.479199f, 0.476522f, 0.473843f, 0.471165f, 0.468486f,
+    0.465807f, 0.463128f, 0.460449f, 0.457770f, 0.455091f, 0.452412f,
+    0.449733f, 0.447055f, 0.444377f, 0.441699f, 0.439022f, 0.436345f,
+    0.433668f, 0.430993f, 0.428318f, 0.425643f, 0.422970f, 0.420297f,
+    0.417625f, 0.414955f, 0.412285f, 0.409616f, 0.406949f, 0.404282f,
+    0.401617f, 0.398954f, 0.396291f, 0.393631f, 0.390971f, 0.388314f,
+    0.385657f, 0.383003f, 0.380350f, 0.377699f, 0.375050f, 0.372403f,
+    0.369758f, 0.367115f, 0.364474f, 0.361835f, 0.359198f, 0.356564f,
+    0.353932f, 0.351302f, 0.348675f, 0.346050f, 0.343428f, 0.340808f,
+    0.338191f, 0.335577f, 0.332965f, 0.330357f, 0.327751f, 0.325148f,
+    0.322548f, 0.319951f, 0.317358f, 0.314767f, 0.312180f, 0.309596f,
+    0.307015f, 0.304437f, 0.301863f, 0.299293f, 0.296726f, 0.294162f,
+    0.291603f, 0.289047f, 0.286494f, 0.283946f, 0.281401f, 0.278860f,
+    0.276323f, 0.273791f, 0.271262f, 0.268737f, 0.266217f, 0.263700f,
+    0.261188f, 0.258680f, 0.256177f, 0.253678f, 0.251183f, 0.248693f,
+    0.246208f, 0.243727f, 0.241251f, 0.238779f, 0.236312f, 0.233850f,
+    0.231393f, 0.228941f, 0.226494f, 0.224051f, 0.221614f, 0.219182f,
+    0.216755f, 0.214333f, 0.211916f, 0.209505f, 0.207099f, 0.204698f,
+    0.202302f, 0.199913f, 0.197528f, 0.195149f, 0.192776f, 0.190408f,
+    0.188046f, 0.185690f, 0.183339f, 0.180995f, 0.178656f, 0.176323f,
+    0.173995f, 0.171674f, 0.169359f, 0.167050f, 0.164747f, 0.162450f,
+    0.160159f, 0.157875f, 0.155597f, 0.153325f, 0.151059f, 0.148800f,
+    0.146547f, 0.144300f, 0.142060f, 0.139827f, 0.137600f, 0.135380f,
+    0.133166f, 0.130959f, 0.128759f, 0.126566f, 0.124379f, 0.122199f,
+    0.120026f, 0.117860f, 0.115701f, 0.113549f, 0.111404f, 0.109265f,
+    0.107134f, 0.105010f, 0.102893f, 0.100784f, 0.098681f, 0.096586f,
+    0.094498f, 0.092417f, 0.090344f, 0.088278f, 0.086219f, 0.084168f,
+    0.082124f, 0.080088f, 0.078059f, 0.076038f, 0.074025f, 0.072019f,
+    0.070020f, 0.068029f, 0.066046f, 0.064071f, 0.062104f, 0.060144f,
+    0.058192f, 0.056248f, 0.054312f, 0.052383f, 0.050463f, 0.048550f,
+    0.046646f, 0.044749f, 0.042861f, 0.040980f, 0.039108f, 0.037243f,
+    0.035387f, 0.033539f, 0.031699f, 0.029867f, 0.028044f, 0.026228f,
+    0.024421f, 0.022622f, 0.020832f, 0.019050f, 0.017276f, 0.015510f,
+    0.013753f, 0.012004f, 0.010264f, 0.008532f, 0.006809f, 0.005094f,
+    0.003387f, 0.001689f, -0.000000f, -0.001681f, -0.003353f, -0.005017f,
+    -0.006672f, -0.008319f, -0.009956f, -0.011586f, -0.013206f, -0.014818f,
+    -0.016421f, -0.018016f, -0.019602f, -0.021179f, -0.022747f, -0.024306f,
+    -0.025857f, -0.027399f, -0.028932f, -0.030456f, -0.031972f, -0.033479f,
+    -0.034976f, -0.036465f, -0.037945f, -0.039416f, -0.040879f, -0.042332f,
+    -0.043777f, -0.045212f, -0.046639f, -0.048056f, -0.049465f, -0.050865f,
+    -0.052255f, -0.053637f, -0.055010f, -0.056374f, -0.057729f, -0.059074f,
+    -0.060411f, -0.061739f, -0.063058f, -0.064368f, -0.065668f, -0.066960f,
+    -0.068243f, -0.069516f, -0.070781f, -0.072036f, -0.073282f, -0.074520f,
+    -0.075748f, -0.076967f, -0.078177f, -0.079379f, -0.080571f, -0.081754f,
+    -0.082927f, -0.084092f, -0.085248f, -0.086395f, -0.087532f, -0.088661f,
+    -0.089780f, -0.090890f, -0.091992f, -0.093084f, -0.094167f, -0.095241f,
+    -0.096306f, -0.097362f, -0.098409f, -0.099446f, -0.100475f, -0.101495f,
+    -0.102506f, -0.103507f, -0.104500f, -0.105483f, -0.106458f, -0.107423f,
+    -0.108380f, -0.109327f, -0.110266f, -0.111195f, -0.112116f, -0.113027f,
+    -0.113929f, -0.114823f, -0.115708f, -0.116583f, -0.117450f, -0.118307f,
+    -0.119156f, -0.119996f, -0.120827f, -0.121649f, -0.122462f, -0.123266f,
+    -0.124062f, -0.124848f, -0.125626f, -0.126395f, -0.127155f, -0.127906f,
+    -0.128648f, -0.129382f, -0.130107f, -0.130823f, -0.131530f, -0.132228f,
+    -0.132918f, -0.133599f, -0.134271f, -0.134935f, -0.135590f, -0.136236f,
+    -0.136874f, -0.137503f, -0.138123f, -0.138735f, -0.139338f, -0.139933f,
+    -0.140519f, -0.141096f, -0.141665f, -0.142226f, -0.142778f, -0.143321f,
+    -0.143856f, -0.144383f, -0.144901f, -0.145411f, -0.145912f, -0.146405f,
+    -0.146890f, -0.147366f, -0.147834f, -0.148294f, -0.148745f, -0.149189f,
+    -0.149623f, -0.150050f, -0.150469f, -0.150879f, -0.151281f, -0.151675f,
+    -0.152061f, -0.152439f, -0.152809f, -0.153171f, -0.153525f, -0.153870f,
+    -0.154208f, -0.154538f, -0.154860f, -0.155174f, -0.155480f, -0.155778f,
+    -0.156068f, -0.156351f, -0.156626f, -0.156892f, -0.157152f, -0.157403f,
+    -0.157647f, -0.157883f, -0.158111f, -0.158332f, -0.158546f, -0.158751f,
+    -0.158949f, -0.159140f, -0.159323f, -0.159498f, -0.159667f, -0.159827f,
+    -0.159981f, -0.160127f, -0.160265f, -0.160397f, -0.160521f, -0.160637f,
+    -0.160747f, -0.160849f, -0.160944f, -0.161032f, -0.161113f, -0.161187f,
+    -0.161254f, -0.161314f, -0.161366f, -0.161412f, -0.161451f, -0.161483f,
+    -0.161507f, -0.161526f, -0.161537f, -0.161541f, -0.161539f, -0.161530f,
+    -0.161514f, -0.161492f, -0.161463f, -0.161427f, -0.161384f, -0.161336f,
+    -0.161280f, -0.161218f, -0.161150f, -0.161075f, -0.160994f, -0.160906f,
+    -0.160812f, -0.160712f, -0.160605f, -0.160492f, -0.160373f, -0.160248f,
+    -0.160117f, -0.159979f, -0.159836f, -0.159686f, -0.159530f, -0.159369f,
+    -0.159201f, -0.159028f, -0.158848f, -0.158663f, -0.158472f, -0.158275f,
+    -0.158072f, -0.157864f, -0.157649f, -0.157430f, -0.157204f, -0.156973f,
+    -0.156737f, -0.156495f, -0.156247f, -0.155994f, -0.155735f, -0.155472f,
+    -0.155202f, -0.154928f, -0.154648f, -0.154363f, -0.154072f, -0.153777f,
+    -0.153476f, -0.153171f, -0.152860f, -0.152544f, -0.152223f, -0.151897f,
+    -0.151566f, -0.151230f, -0.150890f, -0.150544f, -0.150194f, -0.149839f,
+    -0.149479f, -0.149115f, -0.148745f, -0.148372f, -0.147993f, -0.147610f,
+    -0.147223f, -0.146831f, -0.146435f, -0.146034f, -0.145629f, -0.145219f,
+    -0.144805f, -0.144387f, -0.143965f, -0.143538f, -0.143107f, -0.142672f,
+    -0.142233f, -0.141790f, -0.141343f, -0.140892f, -0.140437f, -0.139978f,
+    -0.139516f, -0.139049f, -0.138578f, -0.138104f, -0.137626f, -0.137145f,
+    -0.136659f, -0.136170f, -0.135678f, -0.135181f, -0.134682f, -0.134179f,
+    -0.133672f, -0.133162f, -0.132649f, -0.132132f, -0.131612f, -0.131088f,
+    -0.130562f, -0.130032f, -0.129499f, -0.128963f, -0.128424f, -0.127881f,
+    -0.127336f, -0.126788f, -0.126237f, -0.125682f, -0.125125f, -0.124566f,
+    -0.124003f, -0.123437f, -0.122869f, -0.122298f, -0.121725f, -0.121148f,
+    -0.120569f, -0.119988f, -0.119404f, -0.118818f, -0.118229f, -0.117637f,
+    -0.117044f, -0.116448f, -0.115849f, -0.115249f, -0.114646f, -0.114041f,
+    -0.113433f, -0.112824f, -0.112212f, -0.111598f, -0.110983f, -0.110365f,
+    -0.109745f, -0.109124f, -0.108500f, -0.107875f, -0.107247f, -0.106618f,
+    -0.105988f, -0.105355f, -0.104721f, -0.104085f, -0.103447f, -0.102808f,
+    -0.102167f, -0.101525f, -0.100881f, -0.100236f, -0.099589f, -0.098941f,
+    -0.098292f, -0.097641f, -0.096989f, -0.096336f, -0.095681f, -0.095025f,
+    -0.094368f, -0.093710f, -0.093051f, -0.092391f, -0.091729f, -0.091067f,
+    -0.090404f, -0.089740f, -0.089074f, -0.088408f, -0.087741f, -0.087074f,
+    -0.086405f, -0.085736f, -0.085066f, -0.084395f, -0.083724f, -0.083052f,
+    -0.082380f, -0.081706f, -0.081033f, -0.080359f, -0.079684f, -0.079009f,
+    -0.078334f, -0.077658f, -0.076981f, -0.076305f, -0.075628f, -0.074951f,
+    -0.074274f, -0.073596f, -0.072918f, -0.072241f, -0.071563f, -0.070884f,
+    -0.070206f, -0.069528f, -0.068850f, -0.068172f, -0.067494f, -0.066816f,
+    -0.066138f, -0.065460f, -0.064783f, -0.064106f, -0.063428f, -0.062752f,
+    -0.062075f, -0.061399f, -0.060723f, -0.060047f, -0.059372f, -0.058697f,
+    -0.058023f, -0.057349f, -0.056676f, -0.056003f, -0.055331f, -0.054659f,
+    -0.053988f, -0.053318f, -0.052648f, -0.051979f, -0.051310f, -0.050643f,
+    -0.049976f, -0.049310f, -0.048644f, -0.047980f, -0.047316f, -0.046654f,
+    -0.045992f, -0.045331f, -0.044671f, -0.044012f, -0.043354f, -0.042697f,
+    -0.042041f, -0.041387f, -0.040733f, -0.040080f, -0.039429f, -0.038779f,
+    -0.038130f, -0.037482f, -0.036835f, -0.036190f, -0.035546f, -0.034903f,
+    -0.034262f, -0.033621f, -0.032983f, -0.032345f, -0.031709f, -0.031075f,
+    -0.030442f, -0.029810f, -0.029180f, -0.028552f, -0.027925f, -0.027299f,
+    -0.026675f, -0.026053f, -0.025433f, -0.024813f, -0.024196f, -0.023580f,
+    -0.022966f, -0.022354f, -0.021744f, -0.021135f, -0.020528f, -0.019923f,
+    -0.019319f, -0.018718f, -0.018118f, -0.017520f, -0.016924f, -0.016330f,
+    -0.015738f, -0.015147f, -0.014559f, -0.013973f, -0.013388f, -0.012806f,
+    -0.012226f, -0.011647f, -0.011071f, -0.010497f, -0.009925f, -0.009355f,
+    -0.008787f, -0.008221f, -0.007657f, -0.007096f, -0.006537f, -0.005980f,
+    -0.005425f, -0.004872f, -0.004322f, -0.003773f, -0.003227f, -0.002684f,
+    -0.002142f, -0.001603f, -0.001067f, -0.000532f, 0.000000f, 0.000530f,
+    0.001057f, 0.001582f, 0.002105f, 0.002625f, 0.003143f, 0.003658f,
+    0.004171f, 0.004681f, 0.005189f, 0.005695f, 0.006198f, 0.006698f,
+    0.007196f, 0.007692f, 0.008185f, 0.008675f, 0.009163f, 0.009648f,
+    0.010131f, 0.010611f, 0.011089f, 0.011564f, 0.012036f, 0.012506f,
+    0.012973f, 0.013438f, 0.013899f, 0.014358f, 0.014815f, 0.015269f,
+    0.015720f, 0.016168f, 0.016614f, 0.017057f, 0.017498f, 0.017935f,
+    0.018370f, 0.018802f, 0.019232f, 0.019658f, 0.020082f, 0.020503f,
+    0.020922f, 0.021337f, 0.021750f, 0.022160f, 0.022567f, 0.022972f,
+    0.023374f, 0.023772f, 0.024168f, 0.024562f, 0.024952f, 0.025340f,
+    0.025724f, 0.026106f, 0.026485f, 0.026861f, 0.027235f, 0.027605f,
+    0.027973f, 0.028338f, 0.028700f, 0.029059f, 0.029415f, 0.029768f,
+    0.030119f, 0.030466f, 0.030811f, 0.031152f, 0.031491f, 0.031827f,
+    0.032160f, 0.032491f, 0.032818f, 0.033142f, 0.033464f, 0.033782f,
+    0.034098f, 0.034411f, 0.034721f, 0.035028f, 0.035332f, 0.035633f,
+    0.035931f, 0.036227f, 0.036519f, 0.036809f, 0.037095f, 0.037379f,
+    0.037660f, 0.037938f, 0.038213f, 0.038485f, 0.038754f, 0.039020f,
+    0.039284f, 0.039544f, 0.039802f, 0.040056f, 0.040308f, 0.040557f,
+    0.040803f, 0.041046f, 0.041286f, 0.041524f, 0.041758f, 0.041990f,
+    0.042218f, 0.042444f, 0.042667f, 0.042887f, 0.043104f, 0.043318f,
+    0.043530f, 0.043738f, 0.043944f, 0.044147f, 0.044347f, 0.044544f,
+    0.044738f, 0.044930f, 0.045118f, 0.045304f, 0.045487f, 0.045667f,
+    0.045845f, 0.046019f, 0.046191f, 0.046360f, 0.046526f, 0.046689f,
+    0.046850f, 0.047008f, 0.047163f, 0.047315f, 0.047464f, 0.047611f,
+    0.047755f, 0.047896f, 0.048035f, 0.048170f, 0.048303f, 0.048434f,
+    0.048561f, 0.048686f, 0.048808f, 0.048927f, 0.049044f, 0.049158f,
+    0.049270f, 0.049378f, 0.049484f, 0.049588f, 0.049688f, 0.049786f,
+    0.049882f, 0.049975f, 0.050065f, 0.050152f, 0.050237f, 0.050320f,
+    0.050400f, 0.050477f, 0.050552f, 0.050624f, 0.050693f, 0.050760f,
+    0.050825f, 0.050887f, 0.050946f, 0.051003f, 0.051057f, 0.051109f,
+    0.051159f, 0.051206f, 0.051250f, 0.051292f, 0.051332f, 0.051369f,
+    0.051403f, 0.051436f, 0.051465f, 0.051493f, 0.051518f, 0.051541f,
+    0.051561f, 0.051579f, 0.051595f, 0.051608f, 0.051619f, 0.051627f,
+    0.051634f, 0.051638f, 0.051639f, 0.051639f, 0.051636f, 0.051631f,
+    0.051623f, 0.051614f, 0.051602f, 0.051588f, 0.051572f, 0.051553f,
+    0.051533f, 0.051510f, 0.051485f, 0.051458f, 0.051428f, 0.051397f,
+    0.051363f, 0.051328f, 0.051290f, 0.051250f, 0.051208f, 0.051164f,
+    0.051118f, 0.051070f, 0.051020f, 0.050968f, 0.050914f, 0.050858f,
+    0.050800f, 0.050740f, 0.050678f, 0.050614f, 0.050548f, 0.050480f,
+    0.050411f, 0.050339f, 0.050265f, 0.050190f, 0.050113f, 0.050034f,
+    0.049953f, 0.049870f, 0.049786f, 0.049699f, 0.049611f, 0.049521f,
+    0.049429f, 0.049336f, 0.049241f, 0.049144f, 0.049045f, 0.048945f,
+    0.048843f, 0.048739f, 0.048634f, 0.048527f, 0.048418f, 0.048308f,
+    0.048196f, 0.048083f, 0.047967f, 0.047851f, 0.047733f, 0.047613f,
+    0.047492f, 0.047369f, 0.047244f, 0.047118f, 0.046991f, 0.046862f,
+    0.046732f, 0.046600f, 0.046467f, 0.046333f, 0.046197f, 0.046059f,
+    0.045920f, 0.045780f, 0.045639f, 0.045496f, 0.045352f, 0.045206f,
+    0.045059f, 0.044911f, 0.044762f, 0.044611f, 0.044459f, 0.044306f,
+    0.044152f, 0.043996f, 0.043839f, 0.043681f, 0.043522f, 0.043362f,
+    0.043200f, 0.043038f, 0.042874f, 0.042709f, 0.042543f, 0.042376f,
+    0.042208f, 0.042038f, 0.041868f, 0.041697f, 0.041525f, 0.041351f,
+    0.041177f, 0.041002f, 0.040825f, 0.040648f, 0.040470f, 0.040291f,
+    0.040111f, 0.039930f, 0.039748f, 0.039565f, 0.039381f, 0.039197f,
+    0.039012f, 0.038825f, 0.038638f, 0.038451f, 0.038262f, 0.038073f,
+    0.037883f, 0.037692f, 0.037500f, 0.037308f, 0.037115f, 0.036921f,
+    0.036726f, 0.036531f, 0.036335f, 0.036139f, 0.035942f, 0.035744f,
+    0.035545f, 0.035346f, 0.035147f, 0.034947f, 0.034746f, 0.034544f,
+    0.034342f, 0.034140f, 0.033937f, 0.033734f, 0.033530f, 0.033325f,
+    0.033120f, 0.032915f, 0.032709f, 0.032503f, 0.032296f, 0.032089f,
+    0.031881f, 0.031673f, 0.031465f, 0.031256f, 0.031047f, 0.030838f,
+    0.030628f, 0.030418f, 0.030208f, 0.029997f, 0.029786f, 0.029575f,
+    0.029363f, 0.029151f, 0.028939f, 0.028727f, 0.028515f, 0.028302f,
+    0.028089f, 0.027876f, 0.027663f, 0.027449f, 0.027236f, 0.027022f,
+    0.026808f, 0.026594f, 0.026380f, 0.026166f, 0.025951f, 0.025737f,
+    0.025522f, 0.025308f, 0.025093f, 0.024879f, 0.024664f, 0.024449f,
+    0.024235f, 0.024020f, 0.023805f, 0.023590f, 0.023376f, 0.023161f,
+    0.022947f, 0.022732f, 0.022518f, 0.022303f, 0.022089f, 0.021875f,
+    0.021661f, 0.021447f, 0.021233f, 0.021019f, 0.020806f, 0.020593f,
+    0.020379f, 0.020166f, 0.019953f, 0.019741f, 0.019528f, 0.019316f,
+    0.019104f, 0.018892f, 0.018681f, 0.018469f, 0.018258f, 0.018047f,
+    0.017837f, 0.017627f, 0.017417f, 0.017207f, 0.016998f, 0.016789f,
+    0.016580f, 0.016371f, 0.016163f, 0.015956f, 0.015748f, 0.015541f,
+    0.015335f, 0.015129f, 0.014923f, 0.014717f, 0.014512f, 0.014308f,
+    0.014103f, 0.013900f, 0.013696f, 0.013493f, 0.013291f, 0.013089f,
+    0.012887f, 0.012686f, 0.012486f, 0.012286f, 0.012086f, 0.011887f,
+    0.011688f, 0.011490f, 0.011293f, 0.011096f, 0.010899f, 0.010703f,
+    0.010508f, 0.010313f, 0.010118f, 0.009925f, 0.009732f, 0.009539f,
+    0.009347f, 0.009156f, 0.008965f, 0.008775f, 0.008585f, 0.008396f,
+    0.008208f, 0.008020f, 0.007833f, 0.007646f, 0.007461f, 0.007275f,
+    0.007091f, 0.006907f, 0.006724f, 0.006541f, 0.006360f, 0.006178f,
+    0.005998f, 0.005818f, 0.005639f, 0.005461f, 0.005283f, 0.005106f,
+    0.004930f, 0.004755f, 0.004580f, 0.004406f, 0.004233f, 0.004060f,
+    0.003888f, 0.003717f, 0.003547f, 0.003377f, 0.003209f, 0.003041f,
+    0.002873f, 0.002707f, 0.002541f, 0.002376f, 0.002212f, 0.002049f,
+    0.001887f, 0.001725f, 0.001564f, 0.001404f, 0.001245f, 0.001086f,
+    0.000929f, 0.000772f, 0.000616f, 0.000461f, 0.000306f, 0.000153f,
+    -0.000000f, -0.000152f, -0.000303f, -0.000453f, -0.000602f, -0.000751f,
+    -0.000898f, -0.001045f, -0.001191f, -0.001336f, -0.001480f, -0.001623f,
+    -0.001766f, -0.001907f, -0.002048f, -0.002188f, -0.002327f, -0.002465f,
+    -0.002602f, -0.002738f, -0.002873f, -0.003008f, -0.003141f, -0.003274f,
+    -0.003406f, -0.003537f, -0.003667f, -0.003796f, -0.003924f, -0.004052f,
+    -0.004178f, -0.004303f, -0.004428f, -0.004552f, -0.004674f, -0.004796f,
+    -0.004917f, -0.005037f, -0.005156f, -0.005275f, -0.005392f, -0.005508f,
+    -0.005624f, -0.005738f, -0.005852f, -0.005965f, -0.006076f, -0.006187f,
+    -0.006297f, -0.006406f, -0.006514f, -0.006622f, -0.006728f, -0.006833f,
+    -0.006938f, -0.007041f, -0.007144f, -0.007245f, -0.007346f, -0.007446f,
+    -0.007545f, -0.007643f, -0.007740f, -0.007836f, -0.007931f, -0.008025f,
+    -0.008119f, -0.008211f, -0.008303f, -0.008393f, -0.008483f, -0.008572f,
+    -0.008659f, -0.008746f, -0.008832f, -0.008917f, -0.009001f, -0.009085f,
+    -0.009167f, -0.009248f, -0.009329f, -0.009409f, -0.009487f, -0.009565f,
+    -0.009642f, -0.009718f, -0.009793f, -0.009867f, -0.009940f, -0.010013f,
+    -0.010084f, -0.010155f, -0.010224f, -0.010293f, -0.010361f, -0.010428f,
+    -0.010494f, -0.010559f, -0.010623f, -0.010687f, -0.010749f, -0.010811f,
+    -0.010872f, -0.010931f, -0.010990f, -0.011049f, -0.011106f, -0.011162f,
+    -0.011218f, -0.011272f, -0.011326f, -0.011379f, -0.011431f, -0.011482f,
+    -0.011533f, -0.011582f, -0.011631f, -0.011679f, -0.011725f, -0.011772f,
+    -0.011817f, -0.011861f, -0.011905f, -0.011948f, -0.011989f, -0.012031f,
+    -0.012071f, -0.012110f, -0.012149f, -0.012187f, -0.012224f, -0.012260f,
+    -0.012295f, -0.012330f, -0.012363f, -0.012396f, -0.012428f, -0.012460f,
+    -0.012490f, -0.012520f, -0.012549f, -0.012577f, -0.012604f, -0.012631f,
+    -0.012657f, -0.012682f, -0.012706f, -0.012730f, -0.012752f, -0.012774f,
+    -0.012796f, -0.012816f, -0.012836f, -0.012855f, -0.012873f, -0.012891f,
+    -0.012907f, -0.012924f, -0.012939f, -0.012953f, -0.012967f, -0.012980f,
+    -0.012993f, -0.013005f, -0.013016f, -0.013026f, -0.013035f, -0.013044f,
+    -0.013053f, -0.013060f, -0.013067f, -0.013073f, -0.013078f, -0.013083f,
+    -0.013087f, -0.013091f, -0.013094f, -0.013096f, -0.013097f, -0.013098f,
+    -0.013098f, -0.013098f, -0.013096f, -0.013095f, -0.013092f, -0.013089f,
+    -0.013085f, -0.013081f, -0.013076f, -0.013071f, -0.013065f, -0.013058f,
+    -0.013050f, -0.013042f, -0.013034f, -0.013025f, -0.013015f, -0.013005f,
+    -0.012994f, -0.012982f, -0.012970f, -0.012958f, -0.012944f, -0.012931f,
+    -0.012916f, -0.012902f, -0.012886f, -0.012870f, -0.012854f, -0.012837f,
+    -0.012819f, -0.012801f, -0.012782f, -0.012763f, -0.012744f, -0.012723f,
+    -0.012703f, -0.012682f, -0.012660f, -0.012638f, -0.012615f, -0.012592f,
+    -0.012568f, -0.012544f, -0.012520f, -0.012495f, -0.012469f, -0.012443f,
+    -0.012417f, -0.012390f, -0.012362f, -0.012335f, -0.012306f, -0.012278f,
+    -0.012249f, -0.012219f, -0.012189f, -0.012159f, -0.012128f, -0.012097f,
+    -0.012065f, -0.012033f, -0.012001f, -0.011968f, -0.011935f, -0.011901f,
+    -0.011867f, -0.011833f, -0.011798f, -0.011763f, -0.011728f, -0.011692f,
+    -0.011656f, -0.011619f, -0.011582f, -0.011545f, -0.011507f, -0.011469f,
+    -0.011431f, -0.011393f, -0.011354f, -0.011314f, -0.011275f, -0.011235f,
+    -0.011195f, -0.011154f, -0.011114f, -0.011073f, -0.011031f, -0.010990f,
+    -0.01

(Patch may be truncated, please check the link at the top of this post.)