dmrs-based OTA synchronization for RU
This commit is contained in:
@@ -92,6 +92,15 @@ int lte_sync_time_eNB_emul(PHY_VARS_eNB *phy_vars_eNb,
|
||||
uint8_t sect_id,
|
||||
int32_t *sync_val);
|
||||
|
||||
|
||||
int ru_sync_time_init(RU_t *ru);
|
||||
|
||||
int ru_sync_time(RU_t *ru,
|
||||
int64_t *lev,
|
||||
int64_t *avg);
|
||||
|
||||
void ru_sync_time_free(RU_t *ru);
|
||||
|
||||
/*!
|
||||
\brief This function performs channel estimation including frequency and temporal interpolation
|
||||
\param phy_vars_ue Pointer to UE PHY variables
|
||||
|
||||
@@ -479,6 +479,65 @@ int lte_sync_time(int **rxdata, ///rx data in time domain
|
||||
|
||||
}
|
||||
|
||||
|
||||
int ru_sync_time_init(RU_t *ru) // LTE_UE_COMMON *common_vars
|
||||
{
|
||||
|
||||
int16_t dmrs[2048];
|
||||
int16_t *dmrsp[2] = {dmrs,NULL};
|
||||
|
||||
ru->dmrssync = (int16_t*)malloc16_clear(ru->frame_parms.N_RB_DL*2*sizeof(int16_t));
|
||||
generate_drs_pusch(NULL,NULL,
|
||||
&ru->frame_parms,
|
||||
(int32_t**)dmrsp,
|
||||
0,
|
||||
AMP,
|
||||
0,
|
||||
0,
|
||||
ru->frame_parms.N_RB_DL,
|
||||
0);
|
||||
|
||||
switch (ru->frame_parms.N_RB_DL) {
|
||||
case 6:
|
||||
idft128(dmrs, /// complex input
|
||||
ru->dmrssync, /// complex output
|
||||
1);
|
||||
break;
|
||||
case 25:
|
||||
idft512(dmrs,
|
||||
ru->dmrssync, /// complex output
|
||||
1);
|
||||
break;
|
||||
case 50:
|
||||
idft1024(dmrs,
|
||||
ru->dmrssync, /// complex output
|
||||
1);
|
||||
break;
|
||||
|
||||
case 75:
|
||||
idft1536(dmrs,
|
||||
ru->dmrssync,
|
||||
1); /// complex output
|
||||
break;
|
||||
case 100:
|
||||
idft2048(dmrs,
|
||||
ru->dmrssync, /// complex output
|
||||
1);
|
||||
break;
|
||||
default:
|
||||
AssertFatal(1==0,"Unsupported N_RB_DL %d\n",ru->frame_parms.N_RB_DL);
|
||||
break;
|
||||
}
|
||||
|
||||
return(0);
|
||||
}
|
||||
|
||||
void ru_sync_time_free(RU_t *ru) {
|
||||
|
||||
AssertFatal(ru->dmrssync!=NULL,"ru->dmrssync is NULL\n");
|
||||
free(ru->dmrssync);
|
||||
}
|
||||
|
||||
//#define DEBUG_PHY
|
||||
|
||||
int lte_sync_time_eNB(int32_t **rxdata, ///rx data in time domain
|
||||
@@ -570,3 +629,62 @@ int lte_sync_time_eNB(int32_t **rxdata, ///rx data in time domain
|
||||
|
||||
}
|
||||
|
||||
int ru_sync_time(RU_t *ru,
|
||||
int64_t *lev,
|
||||
int64_t *avg)
|
||||
{
|
||||
|
||||
|
||||
LTE_DL_FRAME_PARMS *frame_parms = &ru->frame_parms;
|
||||
|
||||
// perform a time domain correlation using the oversampled sync sequence
|
||||
|
||||
int length = LTE_NUMBER_OF_SUBFRAMES_PER_FRAME*frame_parms->samples_per_tti;
|
||||
|
||||
|
||||
// circular copy of beginning to end of rxdata buffer. Note: buffer should be big enough upon calling this function
|
||||
for (int ar=0;ar<ru->nb_rx;ar++) memcpy((void*)&ru->common.rxdata[ar][2*length],
|
||||
(void*)&ru->common.rxdata[ar][0],
|
||||
frame_parms->ofdm_symbol_size);
|
||||
|
||||
int32_t tmp0;
|
||||
int32_t magtmp0,maxlev0=0;
|
||||
int maxpos0=0;
|
||||
int64_t avg0=0;
|
||||
int32_t result;
|
||||
|
||||
|
||||
for (int n=0; n<length; n+=4) {
|
||||
|
||||
tmp0 = 0;
|
||||
|
||||
//calculate dot product of primary_synch0_time and rxdata[ar][n] (ar=0..nb_ant_rx) and store the sum in temp[n];
|
||||
for (int ar=0; ar<ru->nb_rx; ar++) {
|
||||
|
||||
result = dot_product(ru->dmrssync,
|
||||
(int16_t*) &ru->common.rxdata[ar][n],
|
||||
frame_parms->ofdm_symbol_size,
|
||||
11);
|
||||
((int16_t*)&tmp0)[0] += ((int16_t*) &result)[0];
|
||||
((int16_t*)&tmp0)[1] += ((int16_t*) &result)[1];
|
||||
}
|
||||
|
||||
// tmpi holds <synchi,rx0>+<synci,rx1>+...+<synchi,rx_{nbrx-1}>
|
||||
|
||||
magtmp0 = abs32(tmp0);
|
||||
|
||||
// this does max |tmp0(n)|^2 and argmax |tmp0(n)|^2
|
||||
|
||||
if (magtmp0>maxlev0) { maxlev0 = magtmp0; maxpos0 = n; }
|
||||
avg0 += magtmp0;
|
||||
}
|
||||
avg0/=(length/4);
|
||||
|
||||
int dmrsoffset = 2*(frame_parms->ofdm_symbol_size+frame_parms->nb_prefix_samples) + frame_parms->nb_prefix_samples0;
|
||||
|
||||
if ((int64_t)maxlev0 > (5*avg0)) {*lev = maxlev0; *avg=avg0; return((length+maxpos0-dmrsoffset)%length);}
|
||||
|
||||
return(-1);
|
||||
|
||||
|
||||
}
|
||||
|
||||
@@ -36,6 +36,8 @@
|
||||
|
||||
int generate_drs_pusch(PHY_VARS_UE *ue,
|
||||
UE_rxtx_proc_t *proc,
|
||||
LTE_DL_FRAME_PARMS *frame_parms,
|
||||
int32_t **txdataF,
|
||||
uint8_t eNB_id,
|
||||
short amp,
|
||||
unsigned int subframe,
|
||||
@@ -54,29 +56,33 @@ int generate_drs_pusch(PHY_VARS_UE *ue,
|
||||
int16_t alpha_re[12] = {32767, 28377, 16383, 0,-16384, -28378,-32768,-28378,-16384, -1, 16383, 28377};
|
||||
int16_t alpha_im[12] = {0, 16383, 28377, 32767, 28377, 16383, 0,-16384,-28378,-32768,-28378,-16384};
|
||||
|
||||
uint8_t cyclic_shift,cyclic_shift0,cyclic_shift1;
|
||||
LTE_DL_FRAME_PARMS *frame_parms = &ue->frame_parms;
|
||||
int32_t *txdataF = ue->common_vars.txdataF[ant];
|
||||
uint8_t cyclic_shift,cyclic_shift0=0,cyclic_shift1=0;
|
||||
LTE_DL_FRAME_PARMS *fp = (ue==NULL) ? frame_parms : &ue->frame_parms;
|
||||
int32_t *txF = (ue==NULL) ? txdataF[ant] : ue->common_vars.txdataF[ant];
|
||||
uint32_t u,v,alpha_ind;
|
||||
uint32_t u0=frame_parms->pusch_config_common.ul_ReferenceSignalsPUSCH.grouphop[subframe<<1];
|
||||
uint32_t u1=frame_parms->pusch_config_common.ul_ReferenceSignalsPUSCH.grouphop[1+(subframe<<1)];
|
||||
uint32_t v0=frame_parms->pusch_config_common.ul_ReferenceSignalsPUSCH.seqhop[subframe<<1];
|
||||
uint32_t v1=frame_parms->pusch_config_common.ul_ReferenceSignalsPUSCH.seqhop[1+(subframe<<1)];
|
||||
uint32_t u0=0,u1=0,v0=0,v1=0;
|
||||
int32_t ref_re,ref_im;
|
||||
uint8_t harq_pid = subframe2harq_pid(frame_parms,proc->frame_tx,subframe);
|
||||
uint8_t harq_pid = (proc == NULL) ? 0: subframe2harq_pid(fp,proc->frame_tx,subframe);
|
||||
|
||||
cyclic_shift0 = (frame_parms->pusch_config_common.ul_ReferenceSignalsPUSCH.cyclicShift +
|
||||
ue->ulsch[eNB_id]->harq_processes[harq_pid]->n_DMRS2 +
|
||||
frame_parms->pusch_config_common.ul_ReferenceSignalsPUSCH.nPRS[subframe<<1]+
|
||||
((ue->ulsch[0]->cooperation_flag==2)?10:0)+
|
||||
ant*6) % 12;
|
||||
// printf("PUSCH.cyclicShift %d, n_DMRS2 %d, nPRS %d\n",frame_parms->pusch_config_common.ul_ReferenceSignalsPUSCH.cyclicShift,ue->ulsch[eNB_id]->n_DMRS2,ue->lte_frame_parms.pusch_config_common.ul_ReferenceSignalsPUSCH.nPRS[subframe<<1]);
|
||||
cyclic_shift1 = (frame_parms->pusch_config_common.ul_ReferenceSignalsPUSCH.cyclicShift +
|
||||
ue->ulsch[eNB_id]->harq_processes[harq_pid]->n_DMRS2 +
|
||||
frame_parms->pusch_config_common.ul_ReferenceSignalsPUSCH.nPRS[(subframe<<1)+1]+
|
||||
((ue->ulsch[0]->cooperation_flag==2)?10:0)+
|
||||
ant*6) % 12;
|
||||
if (ue!=NULL) {
|
||||
cyclic_shift0 = (fp->pusch_config_common.ul_ReferenceSignalsPUSCH.cyclicShift +
|
||||
ue->ulsch[eNB_id]->harq_processes[harq_pid]->n_DMRS2 +
|
||||
fp->pusch_config_common.ul_ReferenceSignalsPUSCH.nPRS[subframe<<1]+
|
||||
((ue->ulsch[0]->cooperation_flag==2)?10:0)+
|
||||
ant*6) % 12;
|
||||
// printf("PUSCH.cyclicShift %d, n_DMRS2 %d, nPRS %d\n",frame_parms->pusch_config_common.ul_ReferenceSignalsPUSCH.cyclicShift,ue->ulsch[eNB_id]->n_DMRS2,ue->lte_frame_parms.pusch_config_common.ul_ReferenceSignalsPUSCH.nPRS[subframe<<1]);
|
||||
cyclic_shift1 = (fp->pusch_config_common.ul_ReferenceSignalsPUSCH.cyclicShift +
|
||||
ue->ulsch[eNB_id]->harq_processes[harq_pid]->n_DMRS2 +
|
||||
fp->pusch_config_common.ul_ReferenceSignalsPUSCH.nPRS[(subframe<<1)+1]+
|
||||
((ue->ulsch[0]->cooperation_flag==2)?10:0)+
|
||||
ant*6) % 12;
|
||||
u0=fp->pusch_config_common.ul_ReferenceSignalsPUSCH.grouphop[subframe<<1];
|
||||
u1=fp->pusch_config_common.ul_ReferenceSignalsPUSCH.grouphop[1+(subframe<<1)];
|
||||
v0=fp->pusch_config_common.ul_ReferenceSignalsPUSCH.seqhop[subframe<<1];
|
||||
v1=fp->pusch_config_common.ul_ReferenceSignalsPUSCH.seqhop[1+(subframe<<1)];
|
||||
}
|
||||
|
||||
|
||||
// cyclic_shift0 = 0;
|
||||
// cyclic_shift1 = 0;
|
||||
Msc_RS = 12*nb_rb;
|
||||
@@ -90,9 +96,9 @@ int generate_drs_pusch(PHY_VARS_UE *ue,
|
||||
return(-1);
|
||||
}
|
||||
|
||||
for (l = (3 - frame_parms->Ncp),u=u0,v=v0,cyclic_shift=cyclic_shift0;
|
||||
for (l = (3 - fp->Ncp),u=u0,v=v0,cyclic_shift=cyclic_shift0;
|
||||
l<frame_parms->symbols_per_tti;
|
||||
l += (7 - frame_parms->Ncp),u=u1,v=v1,cyclic_shift=cyclic_shift1) {
|
||||
l += (7 - fp->Ncp),u=u1,v=v1,cyclic_shift=cyclic_shift1) {
|
||||
|
||||
drs_offset = 0;
|
||||
#ifdef DEBUG_DRS
|
||||
@@ -100,9 +106,9 @@ int generate_drs_pusch(PHY_VARS_UE *ue,
|
||||
#endif
|
||||
|
||||
|
||||
re_offset = frame_parms->first_carrier_offset;
|
||||
subframe_offset = subframe*frame_parms->symbols_per_tti*frame_parms->ofdm_symbol_size;
|
||||
symbol_offset = subframe_offset + frame_parms->ofdm_symbol_size*l;
|
||||
re_offset = fp->first_carrier_offset;
|
||||
subframe_offset = subframe*fp->symbols_per_tti*frame_parms->ofdm_symbol_size;
|
||||
symbol_offset = subframe_offset + fp->ofdm_symbol_size*l;
|
||||
|
||||
|
||||
#ifdef DEBUG_DRS
|
||||
@@ -110,7 +116,7 @@ int generate_drs_pusch(PHY_VARS_UE *ue,
|
||||
#endif
|
||||
alpha_ind = 0;
|
||||
|
||||
for (rb=0; rb<frame_parms->N_RB_UL; rb++) {
|
||||
for (rb=0; rb<fp->N_RB_UL; rb++) {
|
||||
|
||||
if ((rb >= first_rb) && (rb<(first_rb+nb_rb))) {
|
||||
|
||||
@@ -122,12 +128,12 @@ int generate_drs_pusch(PHY_VARS_UE *ue,
|
||||
ref_re = (int32_t) ul_ref_sigs[u][v][Msc_RS_idx][drs_offset<<1];
|
||||
ref_im = (int32_t) ul_ref_sigs[u][v][Msc_RS_idx][(drs_offset<<1)+1];
|
||||
|
||||
((int16_t*) txdataF)[2*(symbol_offset + re_offset)] = (int16_t) (((ref_re*alpha_re[alpha_ind]) -
|
||||
((int16_t*) txF)[2*(symbol_offset + re_offset)] = (int16_t) (((ref_re*alpha_re[alpha_ind]) -
|
||||
(ref_im*alpha_im[alpha_ind]))>>15);
|
||||
((int16_t*) txdataF)[2*(symbol_offset + re_offset)+1] = (int16_t) (((ref_re*alpha_im[alpha_ind]) +
|
||||
((int16_t*) txF)[2*(symbol_offset + re_offset)+1] = (int16_t) (((ref_re*alpha_im[alpha_ind]) +
|
||||
(ref_im*alpha_re[alpha_ind]))>>15);
|
||||
((short*) txdataF)[2*(symbol_offset + re_offset)] = (short) ((((short*) txdataF)[2*(symbol_offset + re_offset)]*(int32_t)amp)>>15);
|
||||
((short*) txdataF)[2*(symbol_offset + re_offset)+1] = (short) ((((short*) txdataF)[2*(symbol_offset + re_offset)+1]*(int32_t)amp)>>15);
|
||||
((short*) txF)[2*(symbol_offset + re_offset)] = (short) ((((short*) txF)[2*(symbol_offset + re_offset)]*(int32_t)amp)>>15);
|
||||
((short*) txF)[2*(symbol_offset + re_offset)+1] = (short) ((((short*) txF)[2*(symbol_offset + re_offset)+1]*(int32_t)amp)>>15);
|
||||
|
||||
|
||||
alpha_ind = (alpha_ind + cyclic_shift);
|
||||
@@ -140,14 +146,14 @@ int generate_drs_pusch(PHY_VARS_UE *ue,
|
||||
symbol_offset,
|
||||
alpha_ind,
|
||||
re_offset,
|
||||
((short*) txdataF)[2*(symbol_offset + re_offset)],
|
||||
((short*) txdataF)[2*(symbol_offset + re_offset)+1]);
|
||||
((short*) txF)[2*(symbol_offset + re_offset)],
|
||||
((short*) txF)[2*(symbol_offset + re_offset)+1]);
|
||||
|
||||
#endif // DEBUG_DRS
|
||||
re_offset++;
|
||||
drs_offset++;
|
||||
|
||||
if (re_offset >= frame_parms->ofdm_symbol_size)
|
||||
if (re_offset >= fp->ofdm_symbol_size)
|
||||
re_offset = 0;
|
||||
}
|
||||
|
||||
@@ -156,8 +162,8 @@ int generate_drs_pusch(PHY_VARS_UE *ue,
|
||||
|
||||
// check if we crossed the symbol boundary and skip DC
|
||||
|
||||
if (re_offset >= frame_parms->ofdm_symbol_size) {
|
||||
if (frame_parms->N_RB_DL&1) // odd number of RBs
|
||||
if (re_offset >= fp->ofdm_symbol_size) {
|
||||
if (fp->N_RB_DL&1) // odd number of RBs
|
||||
re_offset=6;
|
||||
else // even number of RBs (doesn't straddle DC)
|
||||
re_offset=0;
|
||||
|
||||
@@ -1660,15 +1660,17 @@ int32_t generate_srs_tx(PHY_VARS_UE *phy_vars_ue,
|
||||
/*!
|
||||
\brief This function generates the downlink reference signal for the PUSCH according to 36.211 v8.6.0. The DRS occuies the RS defined by rb_alloc and the symbols 2 and 8 for extended CP and 3 and 10 for normal CP.
|
||||
*/
|
||||
int generate_drs_pusch(PHY_VARS_UE *ue,
|
||||
UE_rxtx_proc_t *proc,
|
||||
LTE_DL_FRAME_PARMS *frame_parms,
|
||||
int32_t **txdataF,
|
||||
uint8_t eNB_id,
|
||||
short amp,
|
||||
unsigned int subframe,
|
||||
unsigned int first_rb,
|
||||
unsigned int nb_rb,
|
||||
uint8_t ant);
|
||||
|
||||
int32_t generate_drs_pusch(PHY_VARS_UE *phy_vars_ue,
|
||||
UE_rxtx_proc_t *proc,
|
||||
uint8_t eNB_id,
|
||||
int16_t amp,
|
||||
uint32_t subframe,
|
||||
uint32_t first_rb,
|
||||
uint32_t nb_rb,
|
||||
uint8_t ant);
|
||||
|
||||
/*!
|
||||
\brief This function initializes the Group Hopping, Sequence Hopping and nPRS sequences for PUCCH/PUSCH according to 36.211 v8.6.0. It should be called after configuration of UE (reception of SIB2/3) and initial configuration of eNB (or after reconfiguration of cell-specific parameters).
|
||||
|
||||
@@ -717,6 +717,8 @@ typedef struct RU_t_s{
|
||||
int rx_offset;
|
||||
/// flag to indicate the RU is a slave to another source
|
||||
int is_slave;
|
||||
/// flag to indicate that the RU should generate the DMRS sequence in slot 2 (subframe 1) for OTA synchronization and calibration
|
||||
int generate_dmrs_sync;
|
||||
/// flag to indicate if the RU has a control channel
|
||||
int has_ctrl_prt;
|
||||
/// counter to delay start of processing of RU until HW settles
|
||||
@@ -830,6 +832,8 @@ typedef struct RU_t_s{
|
||||
RU_proc_t proc;
|
||||
/// stats thread pthread descriptor
|
||||
pthread_t ru_stats_thread;
|
||||
/// OTA synchronization signal
|
||||
int16_t *dmrssync;
|
||||
} RU_t;
|
||||
|
||||
|
||||
|
||||
@@ -1851,6 +1851,8 @@ void ue_ulsch_uespec_procedures(PHY_VARS_UE *ue,UE_rxtx_proc_t *proc,uint8_t eNB
|
||||
for (aa=0; aa<1/*frame_parms->nb_antennas_tx*/; aa++)
|
||||
generate_drs_pusch(ue,
|
||||
proc,
|
||||
(LTE_DL_FRAME_PARMS *)NULL,
|
||||
(int32_t**)NULL,
|
||||
eNB_id,
|
||||
tx_amp,
|
||||
subframe_tx,
|
||||
|
||||
@@ -84,11 +84,28 @@ void feptx0(RU_t *ru,int slot) {
|
||||
6,
|
||||
fp->nb_prefix_samples,
|
||||
CYCLIC_PREFIX);
|
||||
else normal_prefix_mod(&ru->common.txdataF_BF[aa][slot*slot_sizeF],
|
||||
(int*)&ru->common.txdata[aa][slot_offset],
|
||||
7,
|
||||
fp);
|
||||
|
||||
else {
|
||||
AssertFatal(ru->generate_dmrs_sync==1 && (fp->frame_type != TDD || ru->is_slave == 1),
|
||||
"ru->generate_dmrs_sync should not be set, frame_type %d, is_slave %d\n",
|
||||
fp->frame_type,ru->is_slave);
|
||||
|
||||
if (ru->generate_dmrs_sync == 1 && slot == 0 && subframe == 1 && aa==0) {
|
||||
generate_drs_pusch((PHY_VARS_UE *)NULL,
|
||||
(UE_rxtx_proc_t*)NULL,
|
||||
fp,
|
||||
ru->common.txdataF_BF,
|
||||
0,
|
||||
AMP,
|
||||
1,
|
||||
0,
|
||||
fp->N_RB_DL,
|
||||
aa);
|
||||
}
|
||||
normal_prefix_mod(&ru->common.txdataF_BF[aa][slot*slot_sizeF],
|
||||
(int*)&ru->common.txdata[aa][slot_offset],
|
||||
7,
|
||||
fp);
|
||||
}
|
||||
/*
|
||||
len = fp->samples_per_tti>>1;
|
||||
|
||||
|
||||
+10
-51
@@ -123,7 +123,7 @@ extern volatile int oai_exit;
|
||||
extern void phy_init_RU(RU_t*);
|
||||
extern void phy_free_RU(RU_t*);
|
||||
|
||||
void init_RU(char*,clock_source_t clock_source,clock_source_t time_source);
|
||||
void init_RU(char*,clock_source_t clock_source,clock_source_t time_source,int generate_dmrssync);
|
||||
void stop_RU(int nb_ru);
|
||||
void do_ru_sync(RU_t *ru);
|
||||
|
||||
@@ -2042,8 +2042,8 @@ void *ru_thread_synch(void *arg) {
|
||||
RU_t *ru = (RU_t*)arg;
|
||||
LTE_DL_FRAME_PARMS *fp=&ru->frame_parms;
|
||||
int32_t sync_pos,sync_pos2;
|
||||
uint32_t peak_val;
|
||||
uint32_t sync_corr[307200] __attribute__((aligned(32)));
|
||||
int64_t peak_val;
|
||||
int64_t avg;
|
||||
static int ru_thread_synch_status=0;
|
||||
int cnt=0;
|
||||
|
||||
@@ -2052,7 +2052,7 @@ void *ru_thread_synch(void *arg) {
|
||||
wait_sync("ru_thread_synch");
|
||||
|
||||
// initialize variables for PSS detection
|
||||
lte_sync_time_init(&ru->frame_parms);
|
||||
ru_sync_time_init(ru);
|
||||
|
||||
while (!oai_exit) {
|
||||
|
||||
@@ -2064,63 +2064,22 @@ void *ru_thread_synch(void *arg) {
|
||||
// run intial synch like UE
|
||||
LOG_I(PHY,"Running initial synchronization\n");
|
||||
|
||||
sync_pos = lte_sync_time_eNB(ru->common.rxdata,
|
||||
fp,
|
||||
fp->samples_per_tti*5,
|
||||
ru->rx_offset = ru_sync_time(ru,
|
||||
&peak_val,
|
||||
sync_corr);
|
||||
&avg);
|
||||
LOG_I(PHY,"RU synch cnt %d: %d, val %d\n",cnt,sync_pos,peak_val);
|
||||
cnt++;
|
||||
if (sync_pos >= 0) {
|
||||
if (sync_pos >= fp->nb_prefix_samples)
|
||||
sync_pos2 = sync_pos - fp->nb_prefix_samples;
|
||||
else
|
||||
sync_pos2 = sync_pos + (fp->samples_per_tti*10) - fp->nb_prefix_samples;
|
||||
int sync_pos_slot;
|
||||
if (fp->frame_type == FDD) {
|
||||
|
||||
// PSS is hypothesized in last symbol of first slot in Frame
|
||||
sync_pos_slot = (fp->samples_per_tti>>1) - fp->ofdm_symbol_size - fp->nb_prefix_samples;
|
||||
}
|
||||
else {
|
||||
// PSS is hypothesized in 2nd symbol of third slot in Frame (S-subframe)
|
||||
sync_pos_slot = fp->samples_per_tti +
|
||||
(fp->ofdm_symbol_size<<1) +
|
||||
fp->nb_prefix_samples0 +
|
||||
(fp->nb_prefix_samples);
|
||||
}
|
||||
if (sync_pos2 >= sync_pos_slot)
|
||||
ru->rx_offset = sync_pos2 - sync_pos_slot;
|
||||
else
|
||||
ru->rx_offset = (fp->samples_per_tti*10) + sync_pos2 - sync_pos_slot;
|
||||
|
||||
|
||||
LOG_I(PHY,"Estimated sync_pos %d, peak_val %d => timing offset %d\n",sync_pos,peak_val,ru->rx_offset);
|
||||
|
||||
/*
|
||||
if ((peak_val > 300000) && (sync_pos > 0)) {
|
||||
// if (sync_pos++ > 3) {
|
||||
write_output("ru_sync.m","sync",(void*)&sync_corr[0],fp->samples_per_tti*5,1,2);
|
||||
write_output("ru_rx.m","rxs",(void*)ru->ru_time.rxdata[0][0],fp->samples_per_tti*10,1,1);
|
||||
exit(-1);
|
||||
}
|
||||
*/
|
||||
LOG_I(PHY,"Estimated peak_val %d dB, avg %d => timing offset %d\n",ru->rx_offset,dB_fixed(peak_val),dB_fixed(ru->rx_offset));
|
||||
ru->in_synch = 1;
|
||||
|
||||
} // symc_pos > 0
|
||||
else {
|
||||
if (cnt>1000) {
|
||||
write_output("ru_sync.m","sync",(void*)&sync_corr[0],fp->samples_per_tti*5,1,2);
|
||||
write_output("ru_rx.m","rxs",(void*)ru->common.rxdata[0],fp->samples_per_tti*10,1,1);
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
else AssertFatal(cnt<1000,"Cannot find synch reference\n");
|
||||
} // ru->in_synch==0
|
||||
|
||||
if (release_thread(&ru->proc.mutex_synch,&ru->proc.instance_cnt_synch,"ru_synch_thread") < 0) break;
|
||||
} // oai_exit
|
||||
|
||||
lte_sync_time_free();
|
||||
ru_sync_time_free(ru);
|
||||
|
||||
ru_thread_synch_status = 0;
|
||||
return &ru_thread_synch_status;
|
||||
@@ -2735,7 +2694,7 @@ void set_function_spec_param(RU_t *ru)
|
||||
|
||||
extern void RCconfig_RU(void);
|
||||
|
||||
void init_RU(char *rf_config_file, clock_source_t clock_source,clock_source_t time_source) {
|
||||
void init_RU(char *rf_config_file, clock_source_t clock_source,clock_source_t time_source,int send_dmrssync) {
|
||||
|
||||
int ru_id;
|
||||
RU_t *ru;
|
||||
|
||||
@@ -134,6 +134,7 @@ volatile int oai_exit = 0;
|
||||
|
||||
static clock_source_t clock_source = internal,time_source=internal;
|
||||
static int wait_for_sync = 0;
|
||||
static int send_dmrssync = 0;
|
||||
|
||||
unsigned int mmapped_dma=0;
|
||||
int single_thread_flag=1;
|
||||
@@ -1167,7 +1168,7 @@ int main( int argc, char **argv )
|
||||
printf("About to Init RU threads RC.nb_RU:%d\n", RC.nb_RU);
|
||||
if (RC.nb_RU >0) {
|
||||
printf("Initializing RU threads\n");
|
||||
init_RU(rf_config_file,clock_source,time_source);
|
||||
init_RU(rf_config_file,clock_source,time_source,send_dmrssync);
|
||||
for (ru_id=0;ru_id<RC.nb_RU;ru_id++) {
|
||||
RC.ru[ru_id]->rf_map.card=0;
|
||||
RC.ru[ru_id]->rf_map.chain=CC_id+chain_offset;
|
||||
|
||||
@@ -63,6 +63,7 @@
|
||||
#define CONFIG_HLP_PHYTST "test UE phy layer, mac disabled\n"
|
||||
#define CONFIG_HLP_DMAMAP "sets flag for improved EXMIMO UE performance\n"
|
||||
#define CONFIG_HLP_EXCCLK "tells hardware to use an external clock reference\n"
|
||||
#define CONFIG_HLP_DMRSSYNC "tells RU to insert DMRS in subframe 1 slot 0"
|
||||
#define CONFIG_HLP_USIM "use XOR autentication algo in case of test usim mode\n"
|
||||
#define CONFIG_HLP_NOSNGLT "Disables single-thread mode in lte-softmodem\n"
|
||||
#define CONFIG_HLP_TADV "Set timing_advance\n"
|
||||
@@ -145,6 +146,7 @@ extern int16_t dlsch_demod_shift;
|
||||
{"usim-test", CONFIG_HLP_USIM, PARAMFLAG_BOOL, u8ptr:&usim_test, defintval:0, TYPE_UINT8, 0}, \
|
||||
{"mmapped-dma", CONFIG_HLP_DMAMAP, PARAMFLAG_BOOL, uptr:&mmapped_dma, defintval:0, TYPE_INT, 0}, \
|
||||
{"external-clock", CONFIG_HLP_EXCCLK, PARAMFLAG_BOOL, uptr:&clock_source, defintval:0, TYPE_INT, 0}, \
|
||||
{"send_dmrs_sync", CONFIG_HLP_DMRSSYNC, PARAMFLAG_BOOL, uptr:&send_dmrssync, defintval:0, TYPE_INT, 0}, \
|
||||
{"wait-for-sync", NULL, PARAMFLAG_BOOL, iptr:&wait_for_sync, defintval:0, TYPE_INT, 0}, \
|
||||
{"single-thread-disable", CONFIG_HLP_NOSNGLT, PARAMFLAG_BOOL, iptr:&single_thread_flag, defintval:1, TYPE_INT, 0}, \
|
||||
{"threadIQ", NULL, 0, iptr:&(threads.iq), defintval:1, TYPE_INT, 0}, \
|
||||
@@ -245,7 +247,7 @@ extern void stop_eNB(int);
|
||||
extern void kill_eNB_proc(int inst);
|
||||
|
||||
// In lte-ru.c
|
||||
extern void init_RU(const char*,clock_source_t clock_source,clock_source_t time_source);
|
||||
extern void init_RU(const char*,clock_source_t clock_source,clock_source_t time_source,int send_dmrssync);
|
||||
extern void init_RU_proc(RU_t *ru);
|
||||
extern void stop_RU(int nb_ru);
|
||||
extern void kill_RU_proc(int inst);
|
||||
|
||||
Reference in New Issue
Block a user