diff --git a/cmake_targets/CMakeLists.txt b/cmake_targets/CMakeLists.txt index 5f5f09dfab550c8f63b04d96a48f139f8c3fcc2b..46fd189952e8b975a3526761aaabb0d70eb8ba94 100644 --- a/cmake_targets/CMakeLists.txt +++ b/cmake_targets/CMakeLists.txt @@ -494,7 +494,7 @@ include_directories ("${OPENAIR_TARGETS}/ARCH/EXMIMO/DEFS/") #set (option_HWEXMIMOLIB_lib "-l ") set(HWLIB_EXMIMO_SOURCE ${OPENAIR_TARGETS}/ARCH/EXMIMO/USERSPACE/LIB/openair0_lib.c - ${OPENAIR_TARGETS}/ARCH/EXMIMO/USERSPACE/LIB/gain_control.c +# ${OPENAIR_TARGETS}/ARCH/EXMIMO/USERSPACE/LIB/gain_control.c ) add_library(oai_exmimodevif MODULE ${HWLIB_EXMIMO_SOURCE} ) @@ -535,8 +535,8 @@ if (${RF_BOARD} STREQUAL "EXMIMO") include_directories ("${OPENAIR_TARGETS}/ARCH/EXMIMO/USERSPACE/LIB/") include_directories ("${OPENAIR_TARGETS}/ARCH/EXMIMO/DEFS/") set(HW_SOURCE ${HW_SOURCE} - ${OPENAIR_TARGETS}/ARCH/EXMIMO/USERSPACE/LIB/openair0_lib.c - ${OPENAIR_TARGETS}/ARCH/EXMIMO/USERSPACE/LIB/gain_control.c) + ${OPENAIR_TARGETS}/ARCH/EXMIMO/USERSPACE/LIB/openair0_lib.c) +# ${OPENAIR_TARGETS}/ARCH/EXMIMO/USERSPACE/LIB/gain_control.c) set(option_HW_lib "-rdynamic -ldl") elseif (${RF_BOARD} STREQUAL "OAI_USRP") @@ -1478,9 +1478,9 @@ add_boolean_option(OAI_NW_DRIVER_USE_NETLINK True "????") ${OPENAIR1_DIR}/SIMULATION/ETH_TRANSPORT/pgm_link.c ) - add_library(OPENAIR0_LIB - ${OPENAIR_TARGETS}/ARCH/EXMIMO/USERSPACE/LIB/openair0_lib.c - ) +# add_library(OPENAIR0_LIB +# ${OPENAIR_TARGETS}/ARCH/EXMIMO/USERSPACE/LIB/openair0_lib.c +# ) # System packages that are required # We use either the cmake buildin, in ubuntu are in: /usr/share/cmake*/Modules/ diff --git a/cmake_targets/build_oai b/cmake_targets/build_oai index 96adfa004099a85db33d7be6a9b967dabb362a72..a289677373610259b045eca24fbf1904ae6e225d 100755 --- a/cmake_targets/build_oai +++ b/cmake_targets/build_oai @@ -692,7 +692,9 @@ function main() { #add exmimo compilation #TODO EXMIMO library support - + compilations \ + $build_dir oai_exmimodevif \ + liboai_exmimodevif.so $dbin/liboai_exmimodevif.so.$REL echo_info "liboai_device.so is linked to EXMIMO device library" elif [ "$HW" == "OAI_USRP" ] ; then if [ -d "/usr/include/uhd" ] ; then diff --git a/openair1/PHY/LTE_ESTIMATION/adjust_gain.c b/openair1/PHY/LTE_ESTIMATION/adjust_gain.c index 48339de4cdbb28d8bda02b0f97da2654c389481f..da07687a9e987de03b6e93df652b747839b5fdb3 100644 --- a/openair1/PHY/LTE_ESTIMATION/adjust_gain.c +++ b/openair1/PHY/LTE_ESTIMATION/adjust_gain.c @@ -30,20 +30,10 @@ #include "PHY/defs.h" #include "PHY/extern.h" -#ifdef EXMIMO -#include "openair0_lib.h" -extern int card; -#endif - void phy_adjust_gain (PHY_VARS_UE *ue, uint32_t rx_power_fil_dB, uint8_t eNB_id) { -#ifdef EXMIMO - exmimo_config_t *p_exmimo_config = openair0_exmimo_pci[card].exmimo_config_ptr; - uint16_t i; -#endif - LOG_D(PHY,"Gain control: rssi %d (%d,%d)\n", rx_power_fil_dB, ue->measurements.rssi, @@ -80,77 +70,6 @@ phy_adjust_gain (PHY_VARS_UE *ue, uint32_t rx_power_fil_dB, uint8_t eNB_id) LOG_D(PHY,"Gain control: rx_total_gain_dB = %d (max %d,rxpf %d)\n",ue->rx_total_gain_dB,MAX_RF_GAIN,rx_power_fil_dB); -#ifdef EXMIMO - - if (ue->rx_total_gain_dB>ue->rx_gain_max[0]) { - ue->rx_total_gain_dB = ue->rx_gain_max[0]; - - for (i=0; i<ue->frame_parms.nb_antennas_rx; i++) { - p_exmimo_config->rf.rx_gain[i][0] = 30; - } - - } else if (ue->rx_total_gain_dB<(ue->rx_gain_max[0]-30)) { - // for the moment we stay in max gain mode - ue->rx_total_gain_dB = ue->rx_gain_max[0] - 30; - - for (i=0; i<ue->frame_parms.nb_antennas_rx; i++) { - p_exmimo_config->rf.rx_gain[i][0] = 0; - } - - /* - ue->rx_gain_mode[0] = byp; - ue->rx_gain_mode[1] = byp; - exmimo_pci_interface->rf.rf_mode0 = 22991; //bypass - exmimo_pci_interface->rf.rf_mode1 = 22991; //bypass - - if (ue->rx_total_gain_dB<(ue->rx_gain_byp[0]-50)) { - exmimo_pci_interface->rf.rx_gain00 = 0; - exmimo_pci_interface->rf.rx_gain10 = 0; - } - */ - } else { - - for (i=0; i<ue->frame_parms.nb_antennas_rx; i++) { - p_exmimo_config->rf.rx_gain[i][0] = 30 - ue->rx_gain_max[0] + ue->rx_total_gain_dB; - } - } - - /* - break; - case med_gain: - case byp_gain: - if (ue->rx_total_gain_dB>ue->rx_gain_byp[0]) { - ue->rx_gain_mode[0] = max_gain; - ue->rx_gain_mode[1] = max_gain; - exmimo_pci_interface->rf.rf_mode0 = 55759; //max gain - exmimo_pci_interface->rf.rf_mode1 = 55759; //max gain - - if (ue->rx_total_gain_dB>ue->rx_gain_max[0]) { - exmimo_pci_interface->rf.rx_gain00 = 50; - exmimo_pci_interface->rf.rx_gain10 = 50; - } - else { - exmimo_pci_interface->rf.rx_gain00 = 50 - ue->rx_gain_max[0] + ue->rx_total_gain_dB; - exmimo_pci_interface->rf.rx_gain10 = 50 - ue->rx_gain_max[1] + ue->rx_total_gain_dB; - } - } - else if (ue->rx_total_gain_dB<(ue->rx_gain_byp[0]-50)) { - exmimo_pci_interface->rf.rx_gain00 = 0; - exmimo_pci_interface->rf.rx_gain10 = 0; - } - else { - exmimo_pci_interface->rf.rx_gain00 = 50 - ue->rx_gain_byp[0] + ue->rx_total_gain_dB; - exmimo_pci_interface->rf.rx_gain10 = 50 - ue->rx_gain_byp[1] + ue->rx_total_gain_dB; - } - break; - default: - exmimo_pci_interface->rf.rx_gain00 = 50; - exmimo_pci_interface->rf.rx_gain10 = 50; - break; - } - */ -#endif - #ifdef DEBUG_PHY /* if ((ue->frame%100==0) || (ue->frame < 10)) msg("[PHY][ADJUST_GAIN] frame %d, rx_power = %d, rx_power_fil = %d, rx_power_fil_dB = %d, coef=%d, ncoef=%d, rx_total_gain_dB = %d (%d,%d,%d)\n", diff --git a/openair1/PHY/TOOLS/lte_dfts.c b/openair1/PHY/TOOLS/lte_dfts.c index 375ea418d72e00389ebec52e092b540a6368d852..4fc332704bae044eab5a2d38372f1c2f2381bafd 100644 --- a/openair1/PHY/TOOLS/lte_dfts.c +++ b/openair1/PHY/TOOLS/lte_dfts.c @@ -6817,6 +6817,7 @@ void dft60(int16_t *x,int16_t *y,unsigned char scale) for (i=0; i<60; i++) { y128[i] = mulhi_int16(y128[i],norm128); + printf("y[%d] = (%d,%d)\n",i,((int16_t*)&y128[i])[0],((int16_t*)&y128[i])[1]); } } @@ -18553,6 +18554,7 @@ int main(int argc, char**argv) simd_q15_t x[4096],y[4096],tw0,tw1,tw2,tw3; #endif int i; + simd_q15_t *x128=x,*y128=y; set_taus_seed(0); opp_enabled = 1; @@ -18592,17 +18594,22 @@ int main(int argc, char**argv) ((int16_t *)&tw3)[5] = 0; ((int16_t *)&tw3)[6] = 32767; ((int16_t *)&tw3)[7] = 0; - + */ for (i=0;i<300;i++) { #if defined(__x86_64__) || defined(__i386__) +#ifndef __AVX2__ x[i] = _mm_set1_epi32(taus()); x[i] = _mm_srai_epi16(x[i],4); +#else + x[i] = _mm256_set1_epi32(taus()); + x[i] = _mm256_srai_epi16(x[i],4); +#endif #elif defined(__arm__) x[i] = (int16x8_t)vdupq_n_s32(taus()); x[i] = vshrq_n_s16(x[i],4); #endif } - + /* bfly2_tw1(x,x+1,y,y+1); printf("(%d,%d) (%d,%d) => (%d,%d) (%d,%d)\n",((int16_t*)&x[0])[0],((int16_t*)&x[0])[1],((int16_t*)&x[1])[0],((int16_t*)&x[1])[1],((int16_t*)&y[0])[0],((int16_t*)&y[0])[1],((int16_t*)&y[1])[0],((int16_t*)&y[1])[1]); printf("(%d,%d) (%d,%d) => (%d,%d) (%d,%d)\n",((int16_t*)&x[0])[0],((int16_t*)&x[0])[1],((int16_t*)&x[1])[0],((int16_t*)&x[1])[1],((int16_t*)&y[0])[2],((int16_t*)&y[0])[3],((int16_t*)&y[1])[2],((int16_t*)&y[1])[3]); @@ -18743,27 +18750,27 @@ int main(int argc, char**argv) for (i=0;i<48;i++) printf("%d,%d,",((int16_t*)(&y[i]))[0],((int16_t *)(&y[i]))[1]); printf("\n"); - + */ dft60((int16_t *)x,(int16_t *)y,1); printf("\n\n60-point\n"); printf("X: "); for (i=0;i<60;i++) - printf("%d,%d,",((int16_t*)(&x[i]))[0],((int16_t *)(&x[i]))[1]); + printf("%d,%d,",((int16_t*)(&x128[i]))[0],((int16_t *)(&x128[i]))[1]); printf("\nY:"); for (i=0;i<60;i++) - printf("%d,%d,",((int16_t*)(&y[i]))[0],((int16_t *)(&y[i]))[1]); + printf("%d,%d,",((int16_t*)(&y128[i]))[0],((int16_t *)(&y128[i]))[1]); printf("\n"); - + dft72((int16_t *)x,(int16_t *)y,1); printf("\n\n72-point\n"); printf("X: "); for (i=0;i<72;i++) - printf("%d,%d,",((int16_t*)(&x[i]))[0],((int16_t *)(&x[i]))[1]); + printf("%d,%d,",((int16_t*)(&x128[i]))[0],((int16_t *)(&x128[i]))[1]); printf("\nY:"); for (i=0;i<72;i++) - printf("%d: %d,%d\n",i,((int16_t*)(&y[i]))[0],((int16_t *)(&y[i]))[1]); + printf("%d: %d,%d\n",i,((int16_t*)(&y128[i]))[0],((int16_t *)(&y128[i]))[1]); printf("\n"); - + /* dft96((int16_t *)x,(int16_t *)y,1); printf("\n\n96-point\n"); printf("X: "); @@ -18783,17 +18790,17 @@ int main(int argc, char**argv) for (i=0;i<108;i++) printf("%d: %d,%d\n",i,((int16_t*)(&y[i]))[0],((int16_t *)(&y[i]))[1]); printf("\n"); - + */ dft120((int16_t *)x,(int16_t *)y,1); printf("\n\n120-point\n"); printf("X: "); for (i=0;i<120;i++) - printf("%d,%d,",((int16_t*)(&x[i]))[0],((int16_t *)(&x[i]))[1]); + printf("%d,%d,",((int16_t*)(&x128[i]))[0],((int16_t *)(&x128[i]))[1]); printf("\nY:"); for (i=0;i<120;i++) - printf("%d: %d,%d\n",i,((int16_t*)(&y[i]))[0],((int16_t *)(&y[i]))[1]); + printf("%d: %d,%d\n",i,((int16_t*)(&y128[i]))[0],((int16_t *)(&y128[i]))[1]); printf("\n"); - + /* dft144((int16_t *)x,(int16_t *)y,1); printf("\n\n144-point\n"); printf("X: "); diff --git a/targets/ARCH/COMMON/common_lib.h b/targets/ARCH/COMMON/common_lib.h index dc0b31af58c0b974c4597f2d6b540a98c718b591..f8ec3f8e58961584db2149ff0aa6147f7c9fd334 100644 --- a/targets/ARCH/COMMON/common_lib.h +++ b/targets/ARCH/COMMON/common_lib.h @@ -51,6 +51,9 @@ #define BBU_LOCAL_RADIO_HEAD 0 #define BBU_REMOTE_RADIO_HEAD 1 +#define MAX_CARDS 8 + + typedef int64_t openair0_timestamp; typedef volatile int64_t openair0_vtimestamp; @@ -59,9 +62,9 @@ typedef volatile int64_t openair0_vtimestamp; typedef struct openair0_device_t openair0_device; -#ifndef EXMIMO -#define MAX_CARDS 1 -#endif + + + //#define USRP_GAIN_OFFSET (56.0) // 86 calibrated for USRP B210 @ 2.6 GHz to get equivalent RS EPRE in OAI to SMBV100 output @@ -145,16 +148,12 @@ typedef struct { unsigned int samples_per_frame; //! the sample rate for both transmit and receive. double sample_rate; - //! number of samples per RX/TX packet (USRP + Ethernet) - unsigned int samples_per_packet; - //! delay in sending samples (write) due to hardware access, softmodem processing and fronthaul delay if exist - int tx_scheduling_advance; + //! flag to indicate that the device is doing mmapped DMA transfers + int mmapped_dma; //! offset in samples between TX and RX paths int tx_sample_advance; - //! configurable tx thread lauch delay - int txlaunch_wait; /* 1 or 0 */ - //! configurable tx thread lauch delay - int txlaunch_wait_slotcount; + int samples_per_packet; + int tx_scheduling_advance; //! number of RX channels (=RX antennas) int rx_num_channels; //! number of TX channels (=TX antennas) @@ -165,7 +164,7 @@ typedef struct { //! \brief Center frequency in Hz for TX. //! index: [0..rx_num_channels[ !!! see lte-ue.c:427 FIXME iterates over rx_num_channels double tx_freq[4]; - + //! \brief memory //! \brief Pointer to Calibration table for RX gains rx_gain_calib_table_t *rx_gain_calib_table; diff --git a/targets/ARCH/EXMIMO/USERSPACE/LIB/openair0_lib.c b/targets/ARCH/EXMIMO/USERSPACE/LIB/openair0_lib.c index 427cd47be831bd4f266789d1d1af1ebf34176f46..a8b5f3e21b508c539bcfb1595a92b4da4d529d54 100644 --- a/targets/ARCH/EXMIMO/USERSPACE/LIB/openair0_lib.c +++ b/targets/ARCH/EXMIMO/USERSPACE/LIB/openair0_lib.c @@ -36,17 +36,34 @@ * 28.01.2013: Initial version */ -#include <fcntl.h> -#include <sys/ioctl.h> -#include <sys/mman.h> -#include <string.h> -#include <unistd.h> +#define _GNU_SOURCE #include <stdio.h> #include <stdlib.h> +#include <errno.h> +#include <fcntl.h> +#include <getopt.h> +#include <unistd.h> +#include <string.h> +#include <sys/ioctl.h> +#include <sys/types.h> +#include <sys/mman.h> +#include <sched.h> +#include <linux/sched.h> +#include <signal.h> +#include <execinfo.h> +#include <getopt.h> +#include <sys/sysinfo.h> +#include <sys/ioctl.h> +#include <linux/kernel.h> +#include <linux/types.h> +#include <syscall.h> #include "openair0_lib.h" #include "openair_device.h" #include "common_lib.h" + +#include <pthread.h> + #define max(a,b) ((a)>(b) ? (a) : (b)) exmimo_pci_interface_bot_virtual_t openair0_exmimo_pci[MAX_CARDS]; // contains userspace pointers for each card @@ -66,6 +83,14 @@ static uint32_t rf_vcocal[4] = {910,910,910,910}; static uint32_t rf_vcocal_850[4] = {2015, 2015, 2015, 2015}; static uint32_t rf_rxdc[4] = {32896,32896,32896,32896}; + + +extern volatile int oai_exit; + + +void kill_watchdog(openair0_device *); +void create_watchdog(openair0_device *); + unsigned int log2_int( unsigned int x ) { unsigned int ans = 0 ; @@ -247,16 +272,279 @@ int openair0_stop_without_reset(int card) #define MY_RF_MODE (RXEN + TXEN + TXLPFNORM + TXLPFEN + TXLPF25 + RXLPFNORM + RXLPFEN + RXLPF25 + LNA1ON +LNAMax + RFBBNORM + DMAMODE_RX + DMAMODE_TX) #define RF_MODE_BASE (LNA1ON + RFBBNORM) +static void *watchdog_thread(void *arg) { + + int policy, s, j; + struct sched_param sparam; + char cpu_affinity[1024]; + cpu_set_t cpuset; + exmimo_state_t *exm=((openair0_device *)arg)->priv; + openair0_config_t *cfg=&((openair0_device *)arg)->openair0_cfg[0]; + + volatile unsigned int *daq_mbox = openair0_daq_cnt(); + unsigned int mbox,diff; + + + /* Set affinity mask to include CPUs 1 to MAX_CPUS */ + /* CPU 0 is reserved for UHD threads */ + /* CPU 1 is reserved for all TX threads */ + /* Enable CPU Affinity only if number of CPUs >2 */ + CPU_ZERO(&cpuset); + +#ifdef CPU_AFFINITY + if (get_nprocs() > 2) + { + for (j = 1; j < get_nprocs(); j++) + CPU_SET(j, &cpuset); + s = pthread_setaffinity_np(pthread_self(), sizeof(cpu_set_t), &cpuset); + if (s != 0) + { + perror( "pthread_setaffinity_np"); + printf("Error setting processor affinity"); + } + } +#endif //CPU_AFFINITY + + /* Check the actual affinity mask assigned to the thread */ + + s = pthread_getaffinity_np(pthread_self(), sizeof(cpu_set_t), &cpuset); + if (s != 0) + { + perror( "pthread_getaffinity_np"); + printf("Error getting processor affinity "); + } + memset(cpu_affinity,0,sizeof(cpu_affinity)); + for (j = 0; j < CPU_SETSIZE; j++) + if (CPU_ISSET(j, &cpuset)) + { + char temp[1024]; + sprintf (temp, " CPU_%d", j); + strcat(cpu_affinity, temp); + } + + memset(&sparam, 0 , sizeof (sparam)); + sparam.sched_priority = sched_get_priority_max(SCHED_FIFO); + policy = SCHED_FIFO ; + + s = pthread_setschedparam(pthread_self(), policy, &sparam); + if (s != 0) + { + perror("pthread_setschedparam : "); + printf("Error setting thread priority"); + } + s = pthread_getschedparam(pthread_self(), &policy, &sparam); + if (s != 0) + { + perror("pthread_getschedparam : "); + printf("Error getting thread priority"); + + } + + printf("EXMIMO2 Watchdog TX thread started on CPU %d TID %ld, sched_policy = %s , priority = %d, CPU Affinity=%s \n", + sched_getcpu(), + syscall(__NR_gettid), + (policy == SCHED_FIFO) ? "SCHED_FIFO" : + (policy == SCHED_RR) ? "SCHED_RR" : + (policy == SCHED_OTHER) ? "SCHED_OTHER" : + "???", + sparam.sched_priority, + cpu_affinity ); + + + + + mlockall(MCL_CURRENT | MCL_FUTURE); + + exm->watchdog_exit = 0; + exm->ts = 0; + exm->last_mbox = 0; + + if (cfg->sample_rate==30.72e6) { + exm->samples_per_tick = 15360; + exm->samples_per_frame = 307200; + } + else if (cfg->sample_rate==23.04e6) { + exm->samples_per_tick = 11520; + exm->samples_per_frame = 230400; + } + else if (cfg->sample_rate==15.36e6) { + exm->samples_per_tick = 7680; + exm->samples_per_frame = 153600; + } + else if (cfg->sample_rate==7.68e6) { + exm->samples_per_tick = 3840; + exm->samples_per_frame = 76800; + } + else if (cfg->sample_rate==3.84e6) { + exm->samples_per_tick = 1920; + exm->samples_per_frame = 38400; + } + else if (cfg->sample_rate==1.92e6) { + exm->samples_per_tick = 960; + exm->samples_per_frame = 19200; + } + else { + printf("Unknown sampling rate %f, exiting \n",cfg->sample_rate); + exm->watchdog_exit=1; + } + // main loop to keep up with DMA transfers from exmimo2 + while ((!oai_exit) && (!exm->watchdog_exit)) { + + if (exm->daq_state == running) { + + // grab time from MBOX + mbox = daq_mbox[0]; + if (mbox<exm->last_mbox) { // wrap-around + diff = 150 + mbox - exm->last_mbox; + } + else { + diff = mbox - exm->last_mbox; + } + exm->last_mbox = mbox; + + pthread_mutex_lock(&exm->watchdog_mutex); + exm->ts += (diff*exm->samples_per_frame/150) ; + + if (diff > 10) // we're too late so exit + exm->watchdog_exit = 1; + + if (exm->ts - exm->last_ts_rx > exm->samples_per_frame) { + exm->watchdog_exit = 1; + printf("RX Overflow, exiting\n"); + } + pthread_mutex_unlock(&exm->watchdog_mutex); + } + + + usleep(500); // sleep for 500us + } + + oai_exit=1; + return NULL; +} + +void create_watchdog(openair0_device *dev) { + + exmimo_state_t *priv = dev->priv; + priv->watchdog_exit=0; +#ifndef DEADLINE_SCHEDULER + priv->watchdog_sched_param.sched_priority = sched_get_priority_max(SCHED_FIFO); + pthread_attr_setschedparam(&priv->watchdog_attr,&priv->watchdog_sched_param); + pthread_attr_setschedpolicy(&priv->watchdog_attr,SCHED_FIFO); + pthread_create(&priv->watchdog,&priv->watchdog_attr,watchdog_thread,dev); +#else + pthread_create(&priv->watchdog,NULL,watchdog_thread,devv); +#endif + pthread_mutex_init(&priv->watchdog_mutex,NULL); + + +} + +int trx_exmimo_start(openair0_device *device) { + + exmimo_state_t *exm=device->priv; + + openair0_start_rt_acquisition(0); + exm->daq_state = running; + + return(0); +} + +int trx_exmimo_write(openair0_device *device,openair0_timestamp ptimestamp, void **buff, int nsamps, int cc, int flags) { + + return(0); +} + +int trx_exmimo_read(openair0_device *device, openair0_timestamp *ptimestamp, void **buff, int nsamps, int cc) { + + exmimo_state_t *exm=device->priv; + openair0_config_t *cfg=&device->openair0_cfg[0]; + openair0_timestamp ts,diff; + int i; + + pthread_mutex_lock(&exm->watchdog_mutex); + ts = exm->ts; + pthread_mutex_unlock(&exm->watchdog_mutex); + while (ts < exm->last_ts_rx + nsamps) { + + diff = exm->last_ts_rx+nsamps - ts; // difference in samples between current timestamp and last RX received sample + // go to sleep until we should have enough samples (1024 for a bit more) + usleep((unsigned int)((double)(diff+1024)*1e6/cfg->sample_rate)); + // get new timestamp, in case we have to sleep again + pthread_mutex_lock(&exm->watchdog_mutex); + ts = exm->ts; + pthread_mutex_unlock(&exm->watchdog_mutex); + } + + if (cfg->mmapped_dma == 0) { // if buff is not the dma buffer, do a memcpy, otherwise do nothing + for (i=0;i<cc;i++) { + memcpy(buff[i], + openair0_exmimo_pci[0].adc_head[i]+(exm->last_ts_rx % exm->samples_per_frame), + nsamps*sizeof(int)); + } + } + + *ptimestamp=exm->last_ts_rx; + exm->last_ts_rx += nsamps; + + return(0); +} + +void trx_exmimo_end(openair0_device *device) { + + exmimo_state_t *exm=device->priv; + + exm->daq_state = idle; + openair0_stop(0); + +} + +int trx_exmimo_get_stats(openair0_device* device) { + + return(0); + +} + +int trx_exmimo_reset_stats(openair0_device* device) { + + return(0); + +} + +int trx_exmimo_stop(int card) { + + return(0); + +} + +int trx_exmimo_set_freq(openair0_device* device, openair0_config_t *openair0_cfg1,int exmimo_dump_config) { + + return(0); +} + +int trx_exmimo_set_gains(openair0_device* device, openair0_config_t *openair0_cfg) { + + return(0); + +} + +void kill_watchdog(openair0_device *device) { + + exmimo_state_t *exm=(exmimo_state_t *)device->priv; + exm->watchdog_exit=1; + +} + int device_init(openair0_device *device, openair0_config_t *openair0_cfg) { // Initialize card // exmimo_config_t *p_exmimo_config; exmimo_id_t *p_exmimo_id; int ret; + exmimo_state_t *exm = (exmimo_state_t *)malloc(sizeof(exmimo_state_t)); ret = openair0_open(); - - + if ( ret != 0 ) { if (ret == -1) printf("Error opening /dev/openair0"); @@ -289,6 +577,23 @@ int device_init(openair0_device *device, openair0_config_t *openair0_cfg) { device->type = EXMIMO_DEV; + // Add stuff that was in lte-softmodem here + + // + device->trx_start_func = trx_exmimo_start; + device->trx_end_func = trx_exmimo_end; + device->trx_read_func = trx_exmimo_read; + device->trx_write_func = trx_exmimo_write; + device->trx_get_stats_func = trx_exmimo_get_stats; + device->trx_reset_stats_func = trx_exmimo_reset_stats; + device->trx_stop_func = trx_exmimo_stop; + device->trx_set_freq_func = trx_exmimo_set_freq; + device->trx_set_gains_func = trx_exmimo_set_gains; + device->openair0_cfg = openair0_cfg; + device->priv = (void *)exm; + + create_watchdog(device); + return(0); } @@ -326,8 +631,6 @@ int openair0_config(openair0_config_t *openair0_cfg, int UE_flag) p_exmimo_config->framing.multicard_syncmode=SYNCMODE_SLAVE; /* device specific */ - openair0_cfg[card].txlaunch_wait = 1;//manage when TX processing is triggered - openair0_cfg[card].txlaunch_wait_slotcount = 1; //manage when TX processing is triggered openair0_cfg[card].iq_txshift = 4;//shift openair0_cfg[card].iq_rxrescale = 15;//rescale iqs diff --git a/targets/ARCH/EXMIMO/USERSPACE/LIB/openair0_lib.h b/targets/ARCH/EXMIMO/USERSPACE/LIB/openair0_lib.h index 0abb27dee281c50aca2e280fd18358ae631513ca..a2f37b09dcf0a0a6bd7400db35976e96f5e3604d 100644 --- a/targets/ARCH/EXMIMO/USERSPACE/LIB/openair0_lib.h +++ b/targets/ARCH/EXMIMO/USERSPACE/LIB/openair0_lib.h @@ -42,6 +42,29 @@ #include "pcie_interface.h" #include "openair_device.h" #include "common_lib.h" +#include <pthread.h> +#include <sched.h> +#include <linux/sched.h> + +typedef enum { + idle=0, + waiting_for_synch, + running +} exmimo_daq_state_t; + +typedef struct { + pthread_t watchdog; + pthread_attr_t watchdog_attr; + struct sched_param watchdog_sched_param; + pthread_mutex_t watchdog_mutex; + int watchdog_exit; + exmimo_daq_state_t daq_state; + openair0_timestamp ts; + openair0_timestamp last_ts_rx; + int samples_per_tick; + int samples_per_frame; + int last_mbox; +} exmimo_state_t; // Use this to access shared memory (configuration structures, adc/dac data buffers, ...) // contains userspace pointers diff --git a/targets/RT/USER/lte-enb.c b/targets/RT/USER/lte-enb.c index 5275bb43bd41a647cfdcae3fef411cf876f5bb80..f59ec9ba646fc5481262225278b8013beeb872d1 100644 --- a/targets/RT/USER/lte-enb.c +++ b/targets/RT/USER/lte-enb.c @@ -129,7 +129,7 @@ extern volatile int start_UE; #endif extern volatile int oai_exit; -extern openair0_config_t openair0_cfg[MAX_CARDS]; +extern openair0_config_t *openair0_cfg; extern pthread_cond_t sync_cond; extern pthread_mutex_t sync_mutex; @@ -1174,11 +1174,9 @@ int setup_eNB_buffers(PHY_VARS_eNB **phy_vars_eNB, openair0_config_t *openair0_c { int i, CC_id; -#ifndef EXMIMO + uint16_t N_TA_offset = 0; -#else - int j; -#endif + LTE_DL_FRAME_PARMS *frame_parms; @@ -1191,8 +1189,6 @@ int setup_eNB_buffers(PHY_VARS_eNB **phy_vars_eNB, openair0_config_t *openair0_c return(-1); } -#ifndef EXMIMO - if (frame_parms->frame_type == TDD) { if (frame_parms->N_RB_DL == 100) N_TA_offset = 624; @@ -1202,8 +1198,9 @@ int setup_eNB_buffers(PHY_VARS_eNB **phy_vars_eNB, openair0_config_t *openair0_c N_TA_offset = 624/4; } -#endif + + /* // replace RX signal buffers with mmaped HW versions #ifdef EXMIMO openair0_cfg[CC_id].tx_num_channels = 0; @@ -1253,7 +1250,9 @@ int setup_eNB_buffers(PHY_VARS_eNB **phy_vars_eNB, openair0_config_t *openair0_c } } -#else // not EXMIMO +#else // not EXMIMO + */ + rxdata = (int32_t**)malloc16(frame_parms->nb_antennas_rx*sizeof(int32_t*)); txdata = (int32_t**)malloc16(frame_parms->nb_antennas_tx*sizeof(int32_t*)); @@ -1275,7 +1274,7 @@ int setup_eNB_buffers(PHY_VARS_eNB **phy_vars_eNB, openair0_config_t *openair0_c } -#endif + } return(0); diff --git a/targets/RT/USER/lte-ue.c b/targets/RT/USER/lte-ue.c index 991438d4d5cb2e24fe6446d2bb441d52f0f8f2db..66c60056b358554ed96e230b9d57815d1f423aff 100644 --- a/targets/RT/USER/lte-ue.c +++ b/targets/RT/USER/lte-ue.c @@ -100,6 +100,7 @@ extern pthread_cond_t sync_cond; extern pthread_mutex_t sync_mutex; extern int sync_var; + extern openair0_config_t openair0_cfg[MAX_CARDS]; extern uint32_t downlink_frequency[MAX_NUM_CCs][4]; extern int32_t uplink_frequency_offset[MAX_NUM_CCs][4];