Commit a1aae829 authored by alblf's avatar alblf

Fix duplicated memory allocation when replaying using mmap,

add use_mmap parameter for the record player device
fix assertion when replaying without using mmap
parent af6836d9
......@@ -58,10 +58,9 @@ int read_recplayconfig(recplay_conf_t **recplay_conf, recplay_state_t **recplay_
// Use mmap for IQ files for systems with less than 6GB total RAM
sysinfo(&systeminfo);
if (systeminfo.totalram < 6144000000) {
(*recplay_state)->use_mmap = 0;
} else {
(*recplay_state)->use_mmap = 1;
if (systeminfo.totalram < 6144000000 && ((*recplay_conf)->use_mmap == 1)) {
LOG_W(HW,"System with %f GB of mem (<6GB), mmap usage disabled\n",systeminfo.totalram/10E9);
(*recplay_conf)->use_mmap = 0;
}
} else { /* record player enabled */
free(*recplay_conf);
......
......@@ -78,7 +78,7 @@ typedef struct {
#define CONFIG_HLP_SF_LOOPS "Number of loops to replay of the entire subframes file"
#define CONFIG_HLP_SF_RDELAY "Delay in microseconds to read a subframe in replay mode"
#define CONFIG_HLP_SF_WDELAY "Delay in microseconds to write a subframe in replay mode"
#define CONFIG_HLP_USE_MMAP "In replay mode, map iq file in memory before replaying"
/* keyword strings for config options, used in CMDLINE_XXX_DESC macros and printed when -h option is used */
#define CONFIG_OPT_SF_FILE "subframes-file"
#define CONFIG_OPT_SF_REC "subframes-record"
......@@ -87,7 +87,7 @@ typedef struct {
#define CONFIG_OPT_SF_LOOPS "subframes-loops"
#define CONFIG_OPT_SF_RDELAY "subframes-read-delay"
#define CONFIG_OPT_SF_WDELAY "subframes-write-delay"
#define CONFIG_OPT_USE_MMAP "use-mmap"
#define DEVICE_RECPLAY_SECTION "device.recplay"
/* For information only - the macro is not usable in C++ */
/*---------------------------------------------------------------------------------------------------------------------------------------------------------------------------*/
......@@ -95,13 +95,14 @@ typedef struct {
/* optname helpstr paramflags XXXptr defXXXval type numelt */
/*---------------------------------------------------------------------------------------------------------------------------------------------------------------------------*/
#define DEVICE_RECPLAY_PARAMS_DESC { \
{CONFIG_OPT_SF_FILE, CONFIG_HLP_SF_FILE, 0, strptr:(char **)((*recplay_conf)->u_sf_filename), defstrval:DEF_SF_FILE, TYPE_STRING, 1024}, \
{CONFIG_OPT_SF_REC, CONFIG_HLP_SF_REC, PARAMFLAG_BOOL, uptr:&(u_sf_record), defuintval:0, TYPE_UINT, 0}, \
{CONFIG_OPT_SF_REP, CONFIG_HLP_SF_REP, PARAMFLAG_BOOL, uptr:&(u_sf_replay), defuintval:0, TYPE_UINT, 0}, \
{CONFIG_OPT_SF_FILE, CONFIG_HLP_SF_FILE, 0, strptr:(char **)((*recplay_conf)->u_sf_filename), defstrval:DEF_SF_FILE, TYPE_STRING, 1024}, \
{CONFIG_OPT_SF_REC, CONFIG_HLP_SF_REC, PARAMFLAG_BOOL, uptr:&(u_sf_record), defuintval:0, TYPE_UINT, 0}, \
{CONFIG_OPT_SF_REP, CONFIG_HLP_SF_REP, PARAMFLAG_BOOL, uptr:&(u_sf_replay), defuintval:0, TYPE_UINT, 0}, \
{CONFIG_OPT_SF_MAX, CONFIG_HLP_SF_MAX, 0, uptr:&((*recplay_conf)->u_sf_max), defintval:DEF_NB_SF, TYPE_UINT, 0}, \
{CONFIG_OPT_SF_LOOPS, CONFIG_HLP_SF_LOOPS, 0, uptr:&((*recplay_conf)->u_sf_loops), defintval:DEF_SF_NB_LOOP, TYPE_UINT, 0}, \
{CONFIG_OPT_SF_RDELAY, CONFIG_HLP_SF_RDELAY, 0, uptr:&((*recplay_conf)->u_sf_read_delay), defintval:DEF_SF_DELAY_READ, TYPE_UINT, 0}, \
{CONFIG_OPT_SF_WDELAY, CONFIG_HLP_SF_WDELAY, 0, uptr:&((*recplay_conf)->u_sf_write_delay), defintval:DEF_SF_DELAY_WRITE, TYPE_UINT, 0}, \
{CONFIG_OPT_USE_MMAP, CONFIG_HLP_USE_MMAP, PARAMFLAG_BOOL, uptr:&((*recplay_conf)->use_mmap), defuintval:1, TYPE_UINT, 0}, \
}/*! \brief Record Player Configuration and state */
typedef struct {
char u_sf_filename[1024]; // subframes file path
......@@ -109,10 +110,10 @@ typedef struct {
unsigned int u_sf_loops ; // number of loops in replay mode
unsigned int u_sf_read_delay; // read delay in replay mode
unsigned int u_sf_write_delay ; // write delay in replay mode
unsigned int use_mmap; // default is to use mmap
} recplay_conf_t;
typedef struct {
int use_mmap; // default is to use mmap
size_t mapsize;
FILE *pFile;
int fd;
......
......@@ -68,19 +68,18 @@ static int iqplayer_loadfile(openair0_device *device, openair0_config_t *openair
exit(-1);
}
if (s->use_mmap) {
if (c->use_mmap) {
// use mmap
s->mapsize=sb.st_size;
LOG_I(HW,"Loading subframes using mmap() from %s size=%lu bytes ...\n",c->u_sf_filename, (uint64_t)sb.st_size );
void *mptr = mmap(NULL, sb.st_size, PROT_WRITE, MAP_PRIVATE, s->fd, 0) ;
s->ms_sample = (iqrec_t *) ( mmap(NULL, sb.st_size, PROT_WRITE, MAP_PRIVATE, s->fd, 0) + sizeof(iqfile_header_t));
if (mptr != MAP_FAILED) {
s->ms_sample = (iqrec_t *) ( mptr + sizeof(iqfile_header_t));
parse_iqfile_header(device, (iqfile_header_t *)mptr);
s->ms_sample = (iqrec_t *)((char *)mptr + sizeof(iqfile_header_t));
LOG_I(HW,"Loaded %u subframes.\n",s->nbSamplesBlocks );
} else {
LOG_E(HW,"Cannot mmap file, exiting.\n");
LOG_E(HW,"Cannot mmap file, exiting, errnor %s\n",strerror(errno));
close(s->fd);
exit(-1);
}
......@@ -108,7 +107,7 @@ static int iqplayer_loadfile(openair0_device *device, openair0_config_t *openair
if (lseek(s->fd,sizeof(iqfile_header_t), SEEK_SET) == 0) {
LOG_I(HW,"Initial seek at beginning of the file\n" );
} else {
LOG_I(HW,"Problem initial seek at beginning of the file\n");
LOG_I(HW,"Problem initial seek at beginning of the file, %s\n",strerror(errno));
}
} else {
LOG_E(HW,"Cannot read header in %s exiting.\n",c->u_sf_filename );
......@@ -134,11 +133,10 @@ static int trx_iqplayer_start(openair0_device *device) {
static void trx_iqplayer_end(openair0_device *device) {
if (device == NULL)
return;
if (device->recplay_state == NULL)
return;
if (device->recplay_state->use_mmap) {
if (device->openair0_cfg->recplay_conf->use_mmap) {
if (device->recplay_state->ms_sample != MAP_FAILED) {
munmap(device->recplay_state->ms_sample, device->recplay_state->mapsize);
}
......@@ -201,21 +199,22 @@ static int trx_iqplayer_read(openair0_device *device, openair0_timestamp *ptimes
LOG_I(HW,"go back at the beginning of IQ file");
device->recplay_state->currentPtr=(uint8_t *)device->recplay_state->ms_sample;
if (!s->use_mmap) {
if (lseek(device->recplay_state->fd, 0, SEEK_SET) != 0) {
LOG_E(HW, "Problem seeking at the beginning of IQ file");
}
if (!(device->openair0_cfg->recplay_conf->use_mmap) ) {
close(device->recplay_state->fd);
iqplayer_loadfile(device, device->openair0_cfg);
// LOG_E(HW, "Problem seeking at the beginning of IQ file %s\n",strerror(errno));
}
}
if (!s->use_mmap) {
if (!(device->openair0_cfg->recplay_conf->use_mmap)) {
// read sample from file
if (read(s->fd, s->ms_sample, sizeof(iqrec_t)) != sizeof(iqrec_t)) {
LOG_E(HW,"pb reading iqfile at index %lu\n",sizeof(iqrec_t)*s->curSamplesBlock );
LOG_E(HW,"pb reading iqfile at index %lu %s\n",sizeof(iqrec_t)*s->curSamplesBlock, strerror(errno) );
exit(-1);
} else {
if (read(s->fd, s->ms_sample+1, s->ms_sample->nbBytes) != s->ms_sample->nbBytes) {
LOG_E(HW,"pb reading iqfile at index %lu\n",sizeof(iqrec_t)*s->curSamplesBlock );
LOG_E(HW,"pb reading iqfile at index %lu %s\n",sizeof(iqrec_t)*s->curSamplesBlock, strerror(errno) );
exit(-1);
}
}
......@@ -225,7 +224,9 @@ static int trx_iqplayer_read(openair0_device *device, openair0_timestamp *ptimes
AssertFatal(curHeader->header==BELL_LABS_IQ_HEADER,"" );
// the current timestamp is the stored timestamp until we wrap on input
// USRP shifts 1 sample time to time
AssertFatal(s->wrap_count !=0 || abs(curHeader->ts-s->currentTs) < 5 ,"");
if (s->wrap_count !=0 && device->openair0_cfg->recplay_conf->use_mmap)
AssertFatal( abs(curHeader->ts-s->currentTs) < 5 ,
"wrap_count=%li, ts %lu %lu",s->wrap_count,curHeader->ts,s->currentTs);
AssertFatal(nsamps*4==curHeader->nbBytes,"");
*ptimestamp = s->currentTs;
memcpy(buff[0], curHeader+1, nsamps*4);
......@@ -233,7 +234,7 @@ static int trx_iqplayer_read(openair0_device *device, openair0_timestamp *ptimes
// Prepare for next read
s->currentTs+=nsamps;
if (s->use_mmap)
if (device->openair0_cfg->recplay_conf->use_mmap)
s->currentPtr+=sizeof(iqrec_t)+s->ms_sample->nbBytes;
struct timespec req;
......
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