sointu/tests/test_renderer.c
Veikko Sariola 1b1dabafb8 fix(asm): Change the scaling to 29 in the speed unti (29 increments = double speed).
The old speed scaling of 24 was ill-chosen so that triplets resulted in a minor buffer overflow error. This was never caught by anyone until Visual Studio 2019 in debug mode. Presumably all compilers allocate some extra space so this didn't matter. Now 29 increments = double speed and speeds with alternating 52 and 81 result in triplets that are just slightly faster then ordinary bpm i.e. the buffer will be slightly underrun, which probably is unnoticable to the user.
2020-11-12 19:46:37 +02:00

167 lines
3.6 KiB
C

#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <stdbool.h>
#if defined (_WIN32)
#include <windows.h>
#else
#include <sys/types.h>
#include <sys/stat.h>
#endif
#include <math.h>
#include <stdint.h>
#if UINTPTR_MAX == 0xffffffff // are we 32-bit?
#if defined(__clang__) || defined(__GNUC__)
#define CALLCONV __attribute__ ((stdcall))
#elif defined(_WIN32)
#define CALLCONV __stdcall // on 32-bit platforms, we just use stdcall, as all know it
#endif
#else // 64-bit
#define CALLCONV // the asm will use honor honor correct x64 ABI on all 64-bit platforms
#endif
extern void CALLCONV su_render_song(void *);
#ifdef INCLUDE_GMDLS
extern void CALLCONV su_load_gmdls(void);
#endif
extern int su_max_samples;
int main(int argc, char* argv[]) {
FILE* f;
char filename[256];
int n;
int retval;
char test_name[] = TEST_NAME;
char expected_output_folder[] = "expected_output/";
char actual_output_folder[] = "actual_output/";
long fsize;
long bufsize;
float max_diff;
float diff;
#ifndef SU_USE_16BIT_OUTPUT
float* buf = NULL;
float* filebuf = NULL;
float v;
bufsize = su_max_samples * 2 * sizeof(float);
buf = (float*)malloc(bufsize);
memset(buf, 0, bufsize);
#else
short* buf = NULL;
short* filebuf = NULL;
short v;
bufsize = su_max_samples * 2 * sizeof(short);
buf = (short*)malloc(bufsize);
memset(buf, 0, bufsize);
#endif
if (buf == NULL) {
printf("Could not allocate buffer for 4klang rendering\n");
return 1;
}
#ifdef INCLUDE_GMDLS
su_load_gmdls();
#endif
su_render_song(buf);
snprintf(filename, sizeof filename, "%s%s%s", expected_output_folder, test_name, ".raw");
f = fopen(filename, "rb");
if (f == NULL) {
printf("No expected waveform found!\n");
goto fail;
}
fseek(f, 0, SEEK_END);
fsize = ftell(f);
fseek(f, 0, SEEK_SET);
if (bufsize < fsize) {
printf("4klang rendered shorter wave than expected\n");
goto fail;
}
if (bufsize > fsize) {
printf("4klang rendered longer wave than expected\n");
goto fail;
}
#ifndef SU_USE_16BIT_OUTPUT
filebuf = (float*)malloc(bufsize);
#else
filebuf = (short*)malloc(bufsize);
#endif
if (filebuf == NULL) {
printf("Could not allocate buffer for file contents\n");
goto fail;
}
fread((void*)filebuf, su_max_samples * 2, sizeof(*filebuf), f);
max_diff = 0.0f;
for (n = 0; n < su_max_samples * 2; n++) {
diff = buf[n] - filebuf[n];
#ifdef SU_USE_16BIT_OUTPUT
diff = diff / 32768.0f;
#endif
diff = fabs(diff);
if (diff > 1e-3f || isnan(diff)) {
printf("4klang rendered different wave than expected\n");
goto fail;
}
if (diff > max_diff) {
max_diff = diff;
}
}
if (max_diff > 1e-6) {
printf("4klang rendered almost correct wave, but a small maximum error of %f\n",max_diff);
goto fail;
}
success:
retval = 0;
goto end;
fail:
retval = 1;
end:
if (f != 0) {
fclose(f);
f = 0;
}
#if defined (_WIN32)
CreateDirectory(actual_output_folder, NULL);
#else
mkdir(actual_output_folder, 0777);
#endif
snprintf(filename, sizeof filename, "%s%s%s", actual_output_folder, test_name, ".raw");
f = fopen(filename, "wb");
fwrite((void*)buf, sizeof(*buf), 2 * su_max_samples, f);
fclose(f);
if (buf != 0) {
free(buf);
buf = 0;
}
if (filebuf != 0) {
free(filebuf);
filebuf = 0;
}
return retval;
}