#include "common.h"
int check_storage_number(calculated_number n, int debug) {
char buffer[100];
uint32_t flags = SN_EXISTS;
storage_number s = pack_storage_number(n, flags);
calculated_number d = unpack_storage_number(s);
if(!does_storage_number_exist(s)) {
fprintf(stderr, "Exists flags missing for number " CALCULATED_NUMBER_FORMAT "!\n", n);
return 5;
}
calculated_number ddiff = d - n;
calculated_number dcdiff = ddiff * 100.0 / n;
if(dcdiff < 0) dcdiff = -dcdiff;
size_t len = print_calculated_number(buffer, d);
calculated_number p = strtold(buffer, NULL);
calculated_number pdiff = n - p;
calculated_number pcdiff = pdiff * 100.0 / n;
if(pcdiff < 0) pcdiff = -pcdiff;
if(debug) {
fprintf(stderr,
CALCULATED_NUMBER_FORMAT " original\n"
CALCULATED_NUMBER_FORMAT " packed and unpacked, (stored as 0x%08X, diff " CALCULATED_NUMBER_FORMAT ", " CALCULATED_NUMBER_FORMAT "%%)\n"
"%s printed after unpacked (%zu bytes)\n"
CALCULATED_NUMBER_FORMAT " re-parsed from printed (diff " CALCULATED_NUMBER_FORMAT ", " CALCULATED_NUMBER_FORMAT "%%)\n\n",
n,
d, s, ddiff, dcdiff,
buffer,
len, p, pdiff, pcdiff
);
if(len != strlen(buffer)) fprintf(stderr, "ERROR: printed number %s is reported to have length %zu but it has %zu\n", buffer, len, strlen(buffer));
if(dcdiff > ACCURACY_LOSS) fprintf(stderr, "WARNING: packing number " CALCULATED_NUMBER_FORMAT " has accuracy loss %0.7Lf %%\n", n, dcdiff);
if(pcdiff > ACCURACY_LOSS) fprintf(stderr, "WARNING: re-parsing the packed, unpacked and printed number " CALCULATED_NUMBER_FORMAT " has accuracy loss %0.7Lf %%\n", n, pcdiff);
}
if(len != strlen(buffer)) return 1;
if(dcdiff > ACCURACY_LOSS) return 3;
if(pcdiff > ACCURACY_LOSS) return 4;
return 0;
}
void benchmark_storage_number(int loop, int multiplier) {
int i, j;
calculated_number n, d;
storage_number s;
unsigned long long user, system, total, mine, their;
char buffer[100];
struct rusage now, last;
fprintf(stderr, "\n\nBenchmarking %d numbers, please wait...\n\n", loop);
// ------------------------------------------------------------------------
fprintf(stderr, "SYSTEM LONG DOUBLE SIZE: %zu bytes\n", sizeof(calculated_number));
fprintf(stderr, "NETDATA FLOATING POINT SIZE: %zu bytes\n", sizeof(storage_number));
mine = (calculated_number)sizeof(storage_number) * (calculated_number)loop;
their = (calculated_number)sizeof(calculated_number) * (calculated_number)loop;
if(mine > their) {
fprintf(stderr, "\nNETDATA NEEDS %0.2Lf TIMES MORE MEMORY. Sorry!\n", (long double)(mine / their));
}
else {
fprintf(stderr, "\nNETDATA INTERNAL FLOATING POINT ARITHMETICS NEEDS %0.2Lf TIMES LESS MEMORY.\n", (long double)(their / mine));
}
fprintf(stderr, "\nNETDATA FLOATING POINT\n");
fprintf(stderr, "MIN POSITIVE VALUE " CALCULATED_NUMBER_FORMAT "\n", (calculated_number)STORAGE_NUMBER_POSITIVE_MIN);
fprintf(stderr, "MAX POSITIVE VALUE " CALCULATED_NUMBER_FORMAT "\n", (calculated_number)STORAGE_NUMBER_POSITIVE_MAX);
fprintf(stderr, "MIN NEGATIVE VALUE " CALCULATED_NUMBER_FORMAT "\n", (calculated_number)STORAGE_NUMBER_NEGATIVE_MIN);
fprintf(stderr, "MAX NEGATIVE VALUE " CALCULATED_NUMBER_FORMAT "\n", (calculated_number)STORAGE_NUMBER_NEGATIVE_MAX);
fprintf(stderr, "Maximum accuracy loss: " CALCULATED_NUMBER_FORMAT "%%\n\n\n", (calculated_numb