|
|
@ -53,6 +53,21 @@ |
|
|
|
#define PPM_DURATION 10 |
|
|
|
#define PPM_DURATION 10 |
|
|
|
#define PPM_DUMP_TIME 5 |
|
|
|
#define PPM_DUMP_TIME 5 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
struct time_generic |
|
|
|
|
|
|
|
/* holds all the platform specific values */ |
|
|
|
|
|
|
|
{ |
|
|
|
|
|
|
|
#ifndef _WIN32 |
|
|
|
|
|
|
|
time_t tv_sec; |
|
|
|
|
|
|
|
long tv_nsec; |
|
|
|
|
|
|
|
#else |
|
|
|
|
|
|
|
long tv_sec; |
|
|
|
|
|
|
|
long tv_nsec; |
|
|
|
|
|
|
|
int init; |
|
|
|
|
|
|
|
LARGE_INTEGER frequency; |
|
|
|
|
|
|
|
LARGE_INTEGER ticks; |
|
|
|
|
|
|
|
#endif |
|
|
|
|
|
|
|
}; |
|
|
|
|
|
|
|
|
|
|
|
static enum { |
|
|
|
static enum { |
|
|
|
NO_BENCHMARK, |
|
|
|
NO_BENCHMARK, |
|
|
|
TUNER_BENCHMARK, |
|
|
|
TUNER_BENCHMARK, |
|
|
@ -134,12 +149,15 @@ static void underrun_test(unsigned char *buf, uint32_t len, int mute) |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
#ifndef _WIN32 |
|
|
|
#ifndef _WIN32 |
|
|
|
static int ppm_gettime(struct timespec *ts) |
|
|
|
static int ppm_gettime(struct time_generic *tg) |
|
|
|
{ |
|
|
|
{ |
|
|
|
int rv = ENOSYS; |
|
|
|
int rv = ENOSYS; |
|
|
|
|
|
|
|
struct timespec ts; |
|
|
|
|
|
|
|
|
|
|
|
#ifdef __unix__ |
|
|
|
#ifdef __unix__ |
|
|
|
rv = clock_gettime(CLOCK_MONOTONIC, ts); |
|
|
|
rv = clock_gettime(CLOCK_MONOTONIC, &ts); |
|
|
|
|
|
|
|
tg->tv_sec = ts.tv_sec; |
|
|
|
|
|
|
|
tg->tv_nsec = ts.tv_nsec; |
|
|
|
#elif __APPLE__ |
|
|
|
#elif __APPLE__ |
|
|
|
struct timeval tv; |
|
|
|
struct timeval tv; |
|
|
|
|
|
|
|
|
|
|
@ -149,6 +167,24 @@ static int ppm_gettime(struct timespec *ts) |
|
|
|
#endif |
|
|
|
#endif |
|
|
|
return rv; |
|
|
|
return rv; |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
#endif |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
#ifdef _WIN32 |
|
|
|
|
|
|
|
static int ppm_gettime(struct time_generic *tg) |
|
|
|
|
|
|
|
{ |
|
|
|
|
|
|
|
int rv; |
|
|
|
|
|
|
|
int64_t frac; |
|
|
|
|
|
|
|
if (!tg->init) { |
|
|
|
|
|
|
|
QueryPerformanceFrequency(&tg->frequency); |
|
|
|
|
|
|
|
tg->init = 1; |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
rv = QueryPerformanceCounter(&tg->ticks); |
|
|
|
|
|
|
|
tg->tv_sec = tg->ticks.QuadPart / tg->frequency.QuadPart; |
|
|
|
|
|
|
|
frac = (int64_t)(tg->ticks.QuadPart - (tg->tv_sec * tg->frequency.QuadPart)); |
|
|
|
|
|
|
|
tg->tv_nsec = (long)(frac * 1000000000L / (int64_t)tg->frequency.QuadPart); |
|
|
|
|
|
|
|
return !rv; |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
#endif |
|
|
|
|
|
|
|
|
|
|
|
static int ppm_report(uint64_t nsamples, uint64_t interval) |
|
|
|
static int ppm_report(uint64_t nsamples, uint64_t interval) |
|
|
|
{ |
|
|
|
{ |
|
|
@ -165,8 +201,8 @@ static void ppm_test(uint32_t len) |
|
|
|
static uint64_t interval = 0; |
|
|
|
static uint64_t interval = 0; |
|
|
|
static uint64_t nsamples_total = 0; |
|
|
|
static uint64_t nsamples_total = 0; |
|
|
|
static uint64_t interval_total = 0; |
|
|
|
static uint64_t interval_total = 0; |
|
|
|
struct timespec ppm_now; |
|
|
|
struct time_generic ppm_now; |
|
|
|
static struct timespec ppm_recent; |
|
|
|
static struct time_generic ppm_recent; |
|
|
|
static enum { |
|
|
|
static enum { |
|
|
|
PPM_INIT_NO, |
|
|
|
PPM_INIT_NO, |
|
|
|
PPM_INIT_DUMP, |
|
|
|
PPM_INIT_DUMP, |
|
|
@ -174,6 +210,7 @@ static void ppm_test(uint32_t len) |
|
|
|
} ppm_init = PPM_INIT_NO; |
|
|
|
} ppm_init = PPM_INIT_NO; |
|
|
|
|
|
|
|
|
|
|
|
ppm_gettime(&ppm_now); |
|
|
|
ppm_gettime(&ppm_now); |
|
|
|
|
|
|
|
|
|
|
|
if (ppm_init != PPM_INIT_RUN) { |
|
|
|
if (ppm_init != PPM_INIT_RUN) { |
|
|
|
/*
|
|
|
|
/*
|
|
|
|
* Kyle Keen wrote: |
|
|
|
* Kyle Keen wrote: |
|
|
@ -189,11 +226,11 @@ static void ppm_test(uint32_t len) |
|
|
|
} |
|
|
|
} |
|
|
|
if (ppm_init == PPM_INIT_DUMP && ppm_recent.tv_sec < ppm_now.tv_sec) |
|
|
|
if (ppm_init == PPM_INIT_DUMP && ppm_recent.tv_sec < ppm_now.tv_sec) |
|
|
|
return; |
|
|
|
return; |
|
|
|
ppm_recent.tv_sec = ppm_now.tv_sec; |
|
|
|
ppm_recent = ppm_now; |
|
|
|
ppm_recent.tv_nsec = ppm_now.tv_nsec; |
|
|
|
|
|
|
|
ppm_init = PPM_INIT_RUN; |
|
|
|
ppm_init = PPM_INIT_RUN; |
|
|
|
return; |
|
|
|
return; |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
nsamples += (uint64_t)(len / 2UL); |
|
|
|
nsamples += (uint64_t)(len / 2UL); |
|
|
|
interval = (uint64_t)(ppm_now.tv_sec - ppm_recent.tv_sec); |
|
|
|
interval = (uint64_t)(ppm_now.tv_sec - ppm_recent.tv_sec); |
|
|
|
if (interval < ppm_duration) |
|
|
|
if (interval < ppm_duration) |
|
|
@ -206,19 +243,16 @@ static void ppm_test(uint32_t len) |
|
|
|
(int)((1000000000UL * nsamples) / interval), |
|
|
|
(int)((1000000000UL * nsamples) / interval), |
|
|
|
ppm_report(nsamples, interval), |
|
|
|
ppm_report(nsamples, interval), |
|
|
|
ppm_report(nsamples_total, interval_total)); |
|
|
|
ppm_report(nsamples_total, interval_total)); |
|
|
|
ppm_recent.tv_sec = ppm_now.tv_sec; |
|
|
|
ppm_recent = ppm_now; |
|
|
|
ppm_recent.tv_nsec = ppm_now.tv_nsec; |
|
|
|
|
|
|
|
nsamples = 0; |
|
|
|
nsamples = 0; |
|
|
|
} |
|
|
|
} |
|
|
|
#endif |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
static void rtlsdr_callback(unsigned char *buf, uint32_t len, void *ctx) |
|
|
|
static void rtlsdr_callback(unsigned char *buf, uint32_t len, void *ctx) |
|
|
|
{ |
|
|
|
{ |
|
|
|
underrun_test(buf, len, 0); |
|
|
|
underrun_test(buf, len, 0); |
|
|
|
#ifndef _WIN32 |
|
|
|
|
|
|
|
if (test_mode == PPM_BENCHMARK) |
|
|
|
if (test_mode == PPM_BENCHMARK) |
|
|
|
ppm_test(len); |
|
|
|
ppm_test(len); |
|
|
|
#endif |
|
|
|
|
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
void e4k_benchmark(void) |
|
|
|
void e4k_benchmark(void) |
|
|
@ -375,7 +409,7 @@ int main(int argc, char **argv) |
|
|
|
verbose_reset_buffer(dev); |
|
|
|
verbose_reset_buffer(dev); |
|
|
|
|
|
|
|
|
|
|
|
if ((test_mode == PPM_BENCHMARK) && !sync_mode) { |
|
|
|
if ((test_mode == PPM_BENCHMARK) && !sync_mode) { |
|
|
|
fprintf(stderr, "Reporting PPM error measurement every %i seconds...\n", ppm_duration); |
|
|
|
fprintf(stderr, "Reporting PPM error measurement every %u seconds...\n", ppm_duration); |
|
|
|
fprintf(stderr, "Press ^C after a few minutes.\n"); |
|
|
|
fprintf(stderr, "Press ^C after a few minutes.\n"); |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|