Fix #334

parent 20d76a90
...@@ -43,6 +43,8 @@ ...@@ -43,6 +43,8 @@
#include "UTIL/LOG/log_extern.h" #include "UTIL/LOG/log_extern.h"
#include "common_lib.h" #include "common_lib.h"
#include "assertions.h" #include "assertions.h"
#include <sys/sysinfo.h>
#include <sys/resource.h>
#ifdef __SSE4_1__ #ifdef __SSE4_1__
# include <smmintrin.h> # include <smmintrin.h>
...@@ -274,6 +276,8 @@ static int sync_to_gps(openair0_device *device) ...@@ -274,6 +276,8 @@ static int sync_to_gps(openair0_device *device)
#include "usrp_lib.h" #include "usrp_lib.h"
static FILE *pFile = NULL; static FILE *pFile = NULL;
int mmapfd = 0; int mmapfd = 0;
int iqfd = 0;
int use_mmap = 1; // default is to use mmap
struct stat sb; struct stat sb;
iqrec_t *ms_sample = NULL; // memory for all subframes iqrec_t *ms_sample = NULL; // memory for all subframes
unsigned int nb_samples = 0; unsigned int nb_samples = 0;
...@@ -406,13 +410,24 @@ static void trx_usrp_end(openair0_device *device) { ...@@ -406,13 +410,24 @@ static void trx_usrp_end(openair0_device *device) {
} }
} }
if (u_sf_mode == 2) { // replay if (u_sf_mode == 2) { // replay
if (ms_sample != MAP_FAILED) { if (use_mmap) {
munmap(ms_sample, sb.st_size); if (ms_sample != MAP_FAILED) {
ms_sample = NULL; munmap(ms_sample, sb.st_size);
} ms_sample = NULL;
if (mmapfd != 0) { }
close(mmapfd); if (mmapfd != 0) {
mmapfd = 0; close(mmapfd);
mmapfd = 0;
}
} else {
if (ms_sample != NULL) {
free(ms_sample);
ms_sample = NULL;
}
if (iqfd != 0) {
close(iqfd);
iqfd = 0;
}
} }
} }
#endif #endif
...@@ -619,15 +634,50 @@ static int trx_usrp_read(openair0_device *device, openair0_timestamp *ptimestamp ...@@ -619,15 +634,50 @@ static int trx_usrp_read(openair0_device *device, openair0_timestamp *ptimestamp
return 0; // should make calling process exit return 0; // should make calling process exit
} }
wrap_ts = wrap_count * (nb_samples * (((int)(device->openair0_cfg[0].sample_rate)) / 1000)); wrap_ts = wrap_count * (nb_samples * (((int)(device->openair0_cfg[0].sample_rate)) / 1000));
if (!use_mmap) {
if (lseek(iqfd, 0, SEEK_SET) == 0) {
std::cerr << "Seeking at the beginning of IQ file" << std::endl;
} else {
std::cerr << "Problem seeking at the beginning of IQ file" << std::endl;
}
}
} }
if (cur_samples < nb_samples) { if (use_mmap) {
*ptimestamp = (ms_sample[0].ts + (cur_samples * (((int)(device->openair0_cfg[0].sample_rate)) / 1000))) + wrap_ts; if (cur_samples < nb_samples) {
if (cur_samples == 0) { *ptimestamp = (ms_sample[0].ts + (cur_samples * (((int)(device->openair0_cfg[0].sample_rate)) / 1000))) + wrap_ts;
std::cerr << "starting subframes file with wrap_count=" << wrap_count << " wrap_ts=" << wrap_ts if (cur_samples == 0) {
<< " ts=" << *ptimestamp << std::endl; std::cerr << "starting subframes file with wrap_count=" << wrap_count << " wrap_ts=" << wrap_ts
<< " ts=" << *ptimestamp << std::endl;
}
memcpy(buff[0], &ms_sample[cur_samples].samples[0], nsamps*4);
cur_samples++;
}
} else {
// read sample from file
if (read(iqfd, ms_sample, sizeof(iqrec_t)) != sizeof(iqrec_t)) {
std::cerr << "pb reading iqfile at index " << sizeof(iqrec_t)*cur_samples << std::endl;
close(iqfd);
free(ms_sample);
ms_sample = NULL;
iqfd = 0;
exit(-1);
}
if (cur_samples < nb_samples) {
static int64_t ts0 = 0;
if ((cur_samples == 0) && (wrap_count == 0)) {
ts0 = ms_sample->ts;
}
*ptimestamp = ts0 + (cur_samples * (((int)(device->openair0_cfg[0].sample_rate)) / 1000)) + wrap_ts;
if (cur_samples == 0) {
std::cerr << "starting subframes file with wrap_count=" << wrap_count << " wrap_ts=" << wrap_ts
<< " ts=" << *ptimestamp << std::endl;
}
memcpy(buff[0], &ms_sample->samples[0], nsamps*4);
cur_samples++;
// Prepare for next read
off_t where = lseek(iqfd, cur_samples * sizeof(iqrec_t), SEEK_SET);
} }
memcpy(buff[0], &ms_sample[cur_samples].samples[0], nsamps*4);
cur_samples++;
} }
struct timespec req; struct timespec req;
req.tv_sec = 0; req.tv_sec = 0;
...@@ -907,6 +957,7 @@ extern "C" { ...@@ -907,6 +957,7 @@ extern "C" {
int device_init(openair0_device* device, openair0_config_t *openair0_cfg) { int device_init(openair0_device* device, openair0_config_t *openair0_cfg) {
#if defined(USRP_REC_PLAY) #if defined(USRP_REC_PLAY)
paramdef_t usrp_recplay_params[7]; paramdef_t usrp_recplay_params[7];
struct sysinfo systeminfo;
// to check // to check
static int done = 0; static int done = 0;
if (done == 1) { if (done == 1) {
...@@ -914,6 +965,11 @@ extern "C" { ...@@ -914,6 +965,11 @@ extern "C" {
} // prevent from multiple init } // prevent from multiple init
done = 1; done = 1;
// end to check // end to check
// Use mmap for IQ files for systems with less than 6GB total RAM
sysinfo(&systeminfo);
if (systeminfo.totalram < 6144000000) {
use_mmap = 0;
}
memset(usrp_recplay_params, 0, 7*sizeof(paramdef_t)); memset(usrp_recplay_params, 0, 7*sizeof(paramdef_t));
memset(&u_sf_filename[0], 0, 1024); memset(&u_sf_filename[0], 0, 1024);
if (trx_usrp_recplay_config_init(usrp_recplay_params) != 0) { if (trx_usrp_recplay_config_init(usrp_recplay_params) != 0) {
...@@ -953,7 +1009,8 @@ extern "C" { ...@@ -953,7 +1009,8 @@ extern "C" {
device->trx_set_freq_func = trx_usrp_set_freq; device->trx_set_freq_func = trx_usrp_set_freq;
device->trx_set_gains_func = trx_usrp_set_gains; device->trx_set_gains_func = trx_usrp_set_gains;
device->openair0_cfg = openair0_cfg; device->openair0_cfg = openair0_cfg;
std::cerr << "USRP device initialized in subframes replay mode for " << u_sf_loops << " loops." << std::endl; std::cerr << "USRP device initialized in subframes replay mode for " << u_sf_loops << " loops. Use mmap="
<< use_mmap << std::endl;
} else { } else {
#endif #endif
uhd::set_thread_priority_safe(1.0); uhd::set_thread_priority_safe(1.0);
...@@ -1282,33 +1339,60 @@ extern "C" { ...@@ -1282,33 +1339,60 @@ extern "C" {
memset(ms_sample, 0, u_sf_max * BELL_LABS_IQ_BYTES_PER_SF); memset(ms_sample, 0, u_sf_max * BELL_LABS_IQ_BYTES_PER_SF);
} }
if (u_sf_mode == 2) { if (u_sf_mode == 2) {
// use mmap if (use_mmap) {
mmapfd = open(u_sf_filename, O_RDONLY | O_LARGEFILE); // use mmap
if (mmapfd != 0) { mmapfd = open(u_sf_filename, O_RDONLY | O_LARGEFILE);
fstat(mmapfd, &sb); if (mmapfd != 0) {
std::cerr << "Loading subframes using mmap() from " << u_sf_filename << " size=" << (uint64_t)sb.st_size << " bytes ..." << std::endl; fstat(mmapfd, &sb);
ms_sample = (iqrec_t*) mmap(NULL, sb.st_size, PROT_WRITE, MAP_PRIVATE, mmapfd, 0); std::cerr << "Loading subframes using mmap() from " << u_sf_filename << " size=" << (uint64_t)sb.st_size << " bytes ..." << std::endl;
if (ms_sample != MAP_FAILED) { ms_sample = (iqrec_t*) mmap(NULL, sb.st_size, PROT_WRITE, MAP_PRIVATE, mmapfd, 0);
nb_samples = (sb.st_size / sizeof(iqrec_t)); if (ms_sample != MAP_FAILED) {
int aligned = (((unsigned long)ms_sample & 31) == 0)? 1:0; nb_samples = (sb.st_size / sizeof(iqrec_t));
std::cerr<< "Loaded "<< nb_samples << " subframes." << std::endl; int aligned = (((unsigned long)ms_sample & 31) == 0)? 1:0;
if (aligned == 0) { std::cerr<< "Loaded "<< nb_samples << " subframes." << std::endl;
std::cerr<< "mmap address is not 32 bytes aligned, exiting." << std::endl; if (aligned == 0) {
std::cerr<< "mmap address is not 32 bytes aligned, exiting." << std::endl;
close(mmapfd);
exit(-1);
}
} else {
std::cerr << "Cannot mmap file, exiting." << std::endl;
close(mmapfd); close(mmapfd);
exit(-1); exit(-1);
} }
} else { } else {
std::cerr << "Cannot mmap file, exiting." << std::endl; std::cerr << "Cannot open " << u_sf_filename << " , exiting." << std::endl;
close(mmapfd);
exit(-1); exit(-1);
} }
} else { } else {
iqfd = open(u_sf_filename, O_RDONLY | O_LARGEFILE);
if (iqfd != 0) {
fstat(iqfd, &sb);
nb_samples = (sb.st_size / sizeof(iqrec_t));
std::cerr << "Loading " << nb_samples << " subframes from " << u_sf_filename
<< " size=" << (uint64_t)sb.st_size << " bytes ..." << std::endl;
// allocate buffer for 1 sample at a time
ms_sample = (iqrec_t*) malloc(sizeof(iqrec_t));
if (ms_sample == NULL) {
std::cerr<< "Memory allocation failed for individual subframe replay mode." << std::endl;
close(iqfd);
exit(-1);
}
memset(ms_sample, 0, sizeof(iqrec_t));
// point at beginning of file
if (lseek(iqfd, 0, SEEK_SET) == 0) {
std::cerr << "Initial seek at beginning of the file" << std::endl;
} else {
std::cerr << "Problem initial seek at beginning of the file" << std::endl;
}
} else {
std::cerr << "Cannot open " << u_sf_filename << " , exiting." << std::endl; std::cerr << "Cannot open " << u_sf_filename << " , exiting." << std::endl;
exit(-1); exit(-1);
}
} }
} }
#endif #endif
return 0; return 0;
} }
} }
/*@}*/ /*@}*/
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment