Commit 06f78e9c authored by Matthieu Kanj's avatar Matthieu Kanj

msg3 functions

parent 99df8881
......@@ -963,6 +963,8 @@ unsigned char phy_threegpplte_turbo_decoder16avx2(int16_t *y,
switch (crc_type) {
case CRC24_A:
crc_len=3;
break;
case CRC24_B:
crc_len=3;
break;
......
......@@ -1256,6 +1256,8 @@ unsigned char phy_threegpplte_turbo_decoder16(short *y,
switch (crc_type) {
case CRC24_A:
crc_len=3;
break;
case CRC24_B:
crc_len=3;
break;
......
......@@ -18,6 +18,20 @@
* For more information about the OpenAirInterface (OAI) Software Alliance:
* contact@openairinterface.org
*/
/*! \file phy_procedures_lte_eNB.c
* \brief Implementation of eNB procedures from 36.213 LTE specifications
* \author R. Knopp, F. Kaltenberger, N. Nikaein, X. Foukas
* \date 2011
* \version 0.1
* \company Eurecom
* \email: knopp@eurecom.fr,florian.kaltenberger@eurecom.fr,navid.nikaein@eurecom.fr, x.foukas@sms.ed.ac.uk
* last changes: M. Kanj, V. Savaux
* date: 2018
* company: b<>com
* \email: matthieu.kanj@b-com.com, vincent.savaux@b-com.com
* \note
* \warning
*/
#include "defs.h"
#include "SCHED/defs.h"
......@@ -1675,6 +1689,7 @@ void phy_init_lte_top_NB_IoT(NB_IoT_DL_FRAME_PARMS *frame_parms)
//generate_ul_ref_sigs();
//generate_ul_ref_sigs_rx();
generate_ul_ref_sigs_rx_NB_IoT();
// generate_64qam_table();
//generate_16qam_table();
......
......@@ -93,6 +93,181 @@ void rotate_channel_single_carrier_NB_IoT(int16_t *estimated_channel,unsigned ch
}
/////////////////////////////////////////// temporary functions for channel estimation and rotation
void rotate_channel_sc_tmp_NB_IoT(int16_t *estimated_channel,
uint8_t l,
uint8_t Qm,
uint8_t counter_msg3)
{
int16_t e_phi_re[120] = {32767, 24811, 4807, -17531, -31357, -29956, -14010, 0, 21402, 32412, 27683, 9511, -13279, -29622, -32767, -24812, -4808, 17530, 31356, 29955, 14009, 0, -21403, -32413, -27684, -9512, 13278, 29621, 32767, 24811, 4807, -17531, -31357, -29956, -14010, 0, 21402, 32412, 27683, 9511, -13279, -29622, -32767, -24812, -4808, 17530, 31356, 29955, 14009, -1, -21403, -32413, -27684, -9512, 13278, 29621, 32767, 24811, 4807, -17531, -31357, -29956, -14010, 0, 21402, 32412, 27683, 9511, -13279, -29622, -32767, -24812, -4808, 17530, 31356, 29955, 14009, 0, -21403, -32413, -27684, -9512, 13278, 29621, 32767, 24811, 4807, -17531, -31357, -29956, -14010, -1, 21402, 32412, 27683, 9511, -13279, -29622, -32767, -24812, -4808, 17530, 31356, 29955, 14009, 0, -21403, -32413, -27684, -9512, 13278, 29621};
int16_t e_phi_im[120] = {0, -21403, -32413, -27684, -9512, 13278, 29621, 32767, 24811, 4807, -17531, -31357, -29956, -14010, -1, 21402, 32412, 27683, 9511, -13279, -29622, -32767, -24812, -4808, 17530, 31356, 29955, 14009, 0, -21403, -32413, -27684, -9512, 13278, 29621, 32767, 24811, 4807, -17531, -31357, -29956, -14010, 0, 21402, 32412, 27683, 9511, -13279, -29622, -32767, -24812, -4808, 17530, 31356, 29955, 14009, -1, -21403, -32413, -27684, -9512, 13278, 29621, 32767, 24811, 4807, -17531, -31357, -29956, -14010, 0, 21402, 32412, 27683, 9511, -13279, -29622, -32767, -24812, -4808, 17530, 31356, 29955, 14009, 0, -21403, -32413, -27684, -9512, 13278, 29621, 32767, 24811, 4807, -17531, -31357, -29956, -14010, -1, 21402, 32412, 27683, 9511, -13279, -29622, -32767, -24812, -4808, 17530, 31356, 29955, 14009};
int16_t pi_2_re[2] = {32767 , 0};
int16_t pi_2_im[2] = {0 , 32768};
//int16_t pi_4_re[2] = {32767 , 25735};
//int16_t pi_4_im[2] = {0 , 25736};
int16_t pi_4_re[2] = {32767 , 23170};
int16_t pi_4_im[2] = {0 , 23170};
int k;
int16_t est_channel_re, est_channel_im, est_channel_re2, est_channel_im2;
for (k=0;k<12;k++)
{
est_channel_re = estimated_channel[k<<1];
est_channel_im = estimated_channel[(k<<1)+1];
if (Qm == 1)
{
est_channel_re2 = (int16_t)(((int32_t)pi_2_re[l%2] * (int32_t)est_channel_re +
(int32_t)pi_2_im[l%2] * (int32_t)est_channel_im)>>15);
est_channel_im2 = (int16_t)(((int32_t)pi_2_re[l%2] * (int32_t)est_channel_im -
(int32_t)pi_2_im[l%2] * (int32_t)est_channel_re)>>15);
}
if(Qm == 2)
{
est_channel_re2 = (int16_t)(((int32_t)pi_4_re[l%2] * (int32_t)est_channel_re +
(int32_t)pi_4_im[l%2] * (int32_t)est_channel_im)>>15);
est_channel_im2 = (int16_t)(((int32_t)pi_4_re[l%2] * (int32_t)est_channel_im -
(int32_t)pi_4_im[l%2] * (int32_t)est_channel_re)>>15);
}
estimated_channel[k<<1] = (int16_t)(((int32_t)e_phi_re[14*(8-counter_msg3) + l] * (int32_t)est_channel_re2 +
(int32_t)e_phi_im[14*(8-counter_msg3) + l] * (int32_t)est_channel_im2)>>15);
estimated_channel[(k<<1)+1] = (int16_t)(((int32_t)e_phi_re[14*(8-counter_msg3) + l] * (int32_t)est_channel_im2 -
(int32_t)e_phi_im[14*(8-counter_msg3) + l] * (int32_t)est_channel_re2)>>15);
}
}
int ul_chest_tmp_NB_IoT(int32_t **rxdataF_ext,
int32_t **ul_ch_estimates,
uint8_t l, //symbol within slot
uint8_t Ns,
uint8_t counter_msg3,
LTE_DL_FRAME_PARMS *frame_parms)
{
int pilot_pos1 = 3, pilot_pos2 = 10; // holds for npusch format 1, and 15 kHz subcarrier bandwidth
uint16_t ul_sc_start; // subcarrier start index into UL RB
uint8_t Qm = 2; // needed to rotate the estimated channel
uint32_t u; //for group hopping
uint32_t I_sc = 11;
int symbol_offset;
uint16_t aa,k,n;
//int32_t **ul_ch_estimates=pusch_vars->drs_ch_estimates[eNB_id];
int16_t *received_data, *estimated_channel, *pilot_sig; // pointers to
unsigned int index_Nsc_RU=0;
uint8_t symbol; //symbol within subframe
int16_t average_channel[24]; // average channel over a RB and 2 slots
int32_t *p_average_channel = (int32_t *)&average_channel;
int16_t *ul_ch1, *ul_ch2;
u=0; //Ncell_ID%16;
ul_sc_start = get_UL_sc_start_NB_IoT(I_sc); // NB-IoT: get the used subcarrier in RB
symbol = l + 7*(Ns&1);
if (l == pilot_pos1)
{
symbol_offset = frame_parms->N_RB_UL*12*(l+(7*(Ns&1)));
for (aa=0; aa<frame_parms->nb_antennas_rx; aa++)
{
received_data = (int16_t *)&rxdataF_ext[aa][symbol_offset];
estimated_channel = (int16_t *)&ul_ch_estimates[aa][symbol_offset];
pilot_sig = &ul_ref_sigs_rx_NB_IoT[u][index_Nsc_RU][24 + 24*((8-counter_msg3)*2+Ns)-(ul_sc_start<<1)]; // pilot values depends on the slots
for (k=0;k<12;k++)
{
// Multiplication by the complex conjugate of the pilot
estimated_channel[k<<1] = (int16_t)(((int32_t)received_data[k<<1]*(int32_t)pilot_sig[k<<1] +
(int32_t)received_data[(k<<1)+1]*(int32_t)pilot_sig[(k<<1)+1])>>15); //real part of estimated channel
estimated_channel[(k<<1)+1] = (int16_t)(((int32_t)received_data[(k<<1)+1]*(int32_t)pilot_sig[k<<1] -
(int32_t)received_data[k<<1]*(int32_t)pilot_sig[(k<<1)+1])>>15); //imaginary part of estimated channel
}
rotate_channel_sc_tmp_NB_IoT(estimated_channel,symbol,Qm,counter_msg3);
//printf("\n");
/*for (k=11;k<12;k++)
{
printf(" re_chest = %d im_chest = %d pilot_sig_re =%d pilot_sig_im =%d received_data_re =%d received_data_im=%d ",estimated_channel[k<<1],estimated_channel[(k<<1)+1],pilot_sig[k<<1],pilot_sig[(k<<1)+1],received_data[k<<1],received_data[(k<<1)+1]);
}
printf("\n");
for (k=0;k<40;k++)
{
printf(" pilot_sig_re =%d pilot_sig_im =%d ",pilot_sig[k<<1],pilot_sig[(k<<1)+1]);
}
printf("\n");*/
if (Ns&1) //we are in the second slot of the sub-frame, so do the interpolation
{
ul_ch1 = (int16_t *)&ul_ch_estimates[aa][frame_parms->N_RB_UL*12*pilot_pos1];
ul_ch2 = (int16_t *)&ul_ch_estimates[aa][frame_parms->N_RB_UL*12*pilot_pos2];
// Here, the channel is supposed to be quasi-static during one subframe
// Then, an average over 2 pilot symbols is performed to increase the SNR
// This part may be improved
for (k=0;k<12;k++)
{
average_channel[k<<1] = (int16_t)(((int32_t)ul_ch1[k<<1] + (int32_t)ul_ch2[k<<1])/2);
average_channel[1+(k<<1)] = (int16_t)(((int32_t)ul_ch1[1+(k<<1)] + (int32_t)ul_ch2[1+(k<<1)])/2);
}
for (n=0; n<frame_parms->symbols_per_tti; n++)
{
for (k=0;k<12;k++)
{
ul_ch_estimates[aa][frame_parms->N_RB_UL*12*n + k] = p_average_channel[k];
}
}
/*for (k=11;k<12;k++)
{
printf(" re_chest_av = %d im_chest_av = %d ",ul_ch2[k<<1],ul_ch2[1+(k<<1)]);
}
printf("\n");*/
}
}
}
return(0);
}
int ul_chequal_tmp_NB_IoT(int32_t **rxdataF_ext,
int32_t **rxdataF_comp,
int32_t **ul_ch_estimates,
uint8_t l, //symbol within slot
uint8_t Ns,
LTE_DL_FRAME_PARMS *frame_parms)
{
int symbol_offset;
uint16_t aa,k;
int16_t *received_data, *estimated_channel, *equal_data;
symbol_offset = frame_parms->N_RB_UL*12*(l+(7*(Ns&1)));
for (aa=0; aa<frame_parms->nb_antennas_rx; aa++)
{
received_data = (int16_t *)&rxdataF_ext[aa][symbol_offset];
estimated_channel = (int16_t *)&ul_ch_estimates[aa][symbol_offset];
equal_data = (int16_t *)&rxdataF_comp[aa][symbol_offset];
for (k=0;k<12;k++)
{
// Multiplication by the complex conjugate of the channel
//printf("\nkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkk %d",k);
equal_data[k<<1] = (int16_t)(((int32_t)received_data[k<<1]*(int32_t)estimated_channel[k<<1] +
(int32_t)received_data[(k<<1)+1]*(int32_t)estimated_channel[(k<<1)+1])>>15); //real part of estimated channel
equal_data[(k<<1)+1] = (int16_t)(((int32_t)received_data[(k<<1)+1]*(int32_t)estimated_channel[k<<1] -
(int32_t)received_data[k<<1]*(int32_t)estimated_channel[(k<<1)+1])>>15); //imaginary part of estimated channel
}
}
return(0);
}
/////////////////////////////////////////////////////////////////////////////
int32_t ul_channel_estimation_NB_IoT(PHY_VARS_eNB *eNB,
eNB_rxtx_proc_t *proc,
uint8_t eNB_id,
......
......@@ -31,6 +31,10 @@ void lte_gold_NB_IoT(LTE_DL_FRAME_PARMS *frame_parms,
uint32_t lte_gold_table_NB_IoT[20][2][14],
uint16_t Nid_cell);
unsigned int lte_gold_generic_NB_IoT(unsigned int *x1, unsigned int *x2, unsigned char reset);
/*! \brief This function generates the Narrowband reference signal (NRS) sequence (36-211, Sec 6.10.1.1)
@param phy_vars_eNB Pointer to eNB variables
@param output Output vector for OFDM symbol (Frequency Domain)
......
......@@ -21,7 +21,7 @@
/*! \file PHY/LTE_REFSIG/lte_ul_ref_NB_IoT.c
* \function called by lte_dl_cell_spec_NB_IoT.c , TS 36-211, V13.4.0 2017-02
* \author: Vincent Savaux
* \date 2017
* \date 2018
* \version 0.0
* \company b<>com
* \email: vincent.savaux@b-com.com
......@@ -42,7 +42,7 @@
// uint16_t ref_primes[33] = {11,23,31,47,59,71,89,107,113,139,179,191,211,239,283,293,317,359,383,431,479,523,571,599,647,719,863,887,953,971,1069,1151,1193};
uint16_t sequence_length[4] = {32,3,6,12}; //the "32" value corresponds to the max gold sequence length
uint16_t sequence_length[4] = {100,100,100,100}; //the "32" value corresponds to the max gold sequence length
// int16_t *ul_ref_sigs[30][33];
int16_t *ul_ref_sigs_rx_NB_IoT[30][4]; //these contain the sequences in repeated format and quantized to QPSK ifdef IFFT_FPGA
......@@ -151,7 +151,7 @@ int16_t w_n[256] = {
// }
// }
void generate_ul_ref_sigs_rx_NB_IoT(void)
/*void generate_ul_ref_sigs_rx_NB_IoT(void)
{
unsigned int u,index_Nsc_RU,n; // Vincent: index_Nsc_RU 0,1,2,3 ---> number of sc 1,3,6,12
......@@ -172,12 +172,17 @@ void generate_ul_ref_sigs_rx_NB_IoT(void)
// ul_ref_sigs_rx_NB_IoT[u][index_Nsc_RU] = (int16_t*)malloc16(2*sizeof(int16_t)*sequence_length[index_Nsc_RU]);
switch (index_Nsc_RU){
case 0: // 36.211, Section 10.1.4.1.1
ul_ref_sigs_rx_NB_IoT[u][index_Nsc_RU] = (int16_t*)malloc16(sizeof(int16_t)*(2*sequence_length[index_Nsc_RU]*12+24)); // *12 is mandatory to fit channel estimation functions
ul_ref_sigs_rx_NB_IoT[u][index_Nsc_RU] = (int16_t*)malloc(sizeof(int16_t)*(2*sequence_length[index_Nsc_RU]*12+24)); // *12 is mandatory to fit channel estimation functions
// NB-IoT: for same reason, +24 is added in order to fit the possible subcarrier start shift when index_Nsc_RU = 0, 1, 2 --> see ul_sc_start in channel estimation function
for (n=0; n<sequence_length[index_Nsc_RU]; n++) {
ref_sigs_sc1[n<<1] = qpsk[(s>>n)&1]*w_n[16*u+n%16];
if (n!=0 && n%32==0)
{
s = lte_gold_generic_NB_IoT(&x1, &x2, 0);
}
ref_sigs_sc1[n<<1] = qpsk[(s>>(n%32))&1]*w_n[16*u+n%16];
// ref_sigs_sc1[1+(n<<1)] = qpsk[(s>>n)&1]*w_n[16*u+n%16];
ref_sigs_sc1[1+(n<<1)] = ref_sigs_sc1[n<<1];
}
if (npusch_format==1){
for (n=0; n<sequence_length[index_Nsc_RU]; n++) {
......@@ -192,7 +197,7 @@ void generate_ul_ref_sigs_rx_NB_IoT(void)
}
break;
case 1: // 36.211, Section 10.1.4.1.2
ul_ref_sigs_rx_NB_IoT[u][index_Nsc_RU] = (int16_t*)malloc16(sizeof(int16_t)*(2*12+24)); // *12 is mandatory to fit channel estimation functions
ul_ref_sigs_rx_NB_IoT[u][index_Nsc_RU] = (int16_t*)malloc(sizeof(int16_t)*(2*12+24)); // *12 is mandatory to fit channel estimation functions
for (n=0; n<sequence_length[index_Nsc_RU]; n++) {
// ul_ref_sigs_rx_NB_IoT[u][index_Nsc_RU][n<<1] = (int16_t)(floor(32767*cos(M_PI*ref3[(u*3) + n]/4 + alpha3[threetnecyclicshift])));
// ul_ref_sigs_rx_NB_IoT[u][index_Nsc_RU][1+(n<<1)]= (int16_t)(floor(32767*sin(M_PI*ref3[(u*3) + n]/4 + alpha3[threetnecyclicshift])));
......@@ -201,7 +206,7 @@ void generate_ul_ref_sigs_rx_NB_IoT(void)
}
break;
case 2:
ul_ref_sigs_rx_NB_IoT[u][index_Nsc_RU] = (int16_t*)malloc16(sizeof(int16_t)*(2*12+24)); // *12 is mandatory to fit channel estimation functions
ul_ref_sigs_rx_NB_IoT[u][index_Nsc_RU] = (int16_t*)malloc(sizeof(int16_t)*(2*12+24)); // *12 is mandatory to fit channel estimation functions
for (n=0; n<sequence_length[index_Nsc_RU]; n++) {
// ul_ref_sigs_rx_NB_IoT[u][index_Nsc_RU][n<<1] = (int16_t)(floor(32767*cos(M_PI*ref6[(u*6) + n]/4 + alpha6[sixtonecyclichift])));
// ul_ref_sigs_rx_NB_IoT[u][index_Nsc_RU][1+(n<<1)]= (int16_t)(floor(32767*sin(M_PI*ref6[(u*6) + n]/4 + alpha6[sixtonecyclichift])));
......@@ -210,7 +215,7 @@ void generate_ul_ref_sigs_rx_NB_IoT(void)
}
break;
case 3:
ul_ref_sigs_rx_NB_IoT[u][index_Nsc_RU] = (int16_t*)malloc16(sizeof(int16_t)*(2*12+24)); // *12 is mandatory to fit channel estimation functions
ul_ref_sigs_rx_NB_IoT[u][index_Nsc_RU] = (int16_t*)malloc(sizeof(int16_t)*(2*12+24)); // *12 is mandatory to fit channel estimation functions
for (n=0; n<sequence_length[index_Nsc_RU]; n++) {
ul_ref_sigs_rx_NB_IoT[u][index_Nsc_RU][n<<1] = (int16_t)(floor(32767*cos(M_PI*ref12_NB_IoT[(u*12) + n]/4)));
ul_ref_sigs_rx_NB_IoT[u][index_Nsc_RU][1+(n<<1)]= (int16_t)(floor(32767*sin(M_PI*ref12_NB_IoT[(u*12) + n]/4)));
......@@ -221,6 +226,54 @@ void generate_ul_ref_sigs_rx_NB_IoT(void)
}
}*/
void generate_ul_ref_sigs_rx_NB_IoT(void)
{
unsigned int u,index_Nsc_RU,n; // Vincent: index_Nsc_RU 0,1,2,3 ---> number of sc 1,3,6,12
uint8_t npusch_format = 1; // NB-IoT: format 1 (data), or 2: ack. Should be defined in higher layer
int16_t a;
int16_t qpsk[2];
unsigned int x1, x2=35; // NB-IoT: defined in 36.211, Section 10.1.4.1.1
int16_t ref_sigs_sc1[2*sequence_length[0]];
uint32_t s;
a = ONE_OVER_SQRT2_Q15_NB_IoT;
qpsk[0] = a;
qpsk[1] = -a;
s = lte_gold_generic_NB_IoT(&x1, &x2, 1);
//printf("\n\n\n in generate_ul_ref_sigs_rx_NB_IoT %d \n\n\n",a);
for (index_Nsc_RU=0; index_Nsc_RU<4; index_Nsc_RU++)
{
for (u=0; u<u_max[index_Nsc_RU]; u++)
{
// ul_ref_sigs_rx_NB_IoT[u][index_Nsc_RU] = (int16_t*)malloc16(2*sizeof(int16_t)*sequence_length[index_Nsc_RU]);
switch (index_Nsc_RU)
{
case 0: // 36.211, Section 10.1.4.1.1
ul_ref_sigs_rx_NB_IoT[u][index_Nsc_RU] = (int16_t*)malloc(sizeof(int16_t)*(2*sequence_length[index_Nsc_RU]*12+24)); // *12 is mandatory to fit channel estimation functions
// NB-IoT: for same reason, +24 is added in order to fit the possible subcarrier start shift when index_Nsc_RU = 0, 1, 2 --> see ul_sc_start in channel estimation function
for (n=0; n<sequence_length[index_Nsc_RU]; n++) {
if (n>0 && n%32==0)
{
s = lte_gold_generic_NB_IoT(&x1, &x2, 0);
}
ref_sigs_sc1[n<<1] = qpsk[(s>>(n%32))&1]*w_n[16*u+n%16];
// ref_sigs_sc1[1+(n<<1)] = qpsk[(s>>n)&1]*w_n[16*u+n%16];
ref_sigs_sc1[1+(n<<1)] = ref_sigs_sc1[n<<1];
}
for (n=0; n<sequence_length[index_Nsc_RU]; n++) {
ul_ref_sigs_rx_NB_IoT[u][index_Nsc_RU][12*(n<<1)+24] = ref_sigs_sc1[n<<1]; // ul_ref_sigs_rx_NB_IoT is filled every 12 RE, real part
ul_ref_sigs_rx_NB_IoT[u][index_Nsc_RU][1+12*(n<<1)+24]= ref_sigs_sc1[1+(n<<1)]; // ul_ref_sigs_rx_NB_IoT is filled every 12 RE, imaginary part
}
break;
}
}
}
}
void free_ul_ref_sigs_NB_IoT(void)
......
......@@ -172,7 +172,7 @@ int dlsch_encoding_rar_NB_IoT(unsigned char *a,
dlsch->length_e = G; // G*Nsf (number_of_subframes) = total number of bits to transmit G=236
int32_t numbits = A+24;
if(option ==1)
{
......@@ -189,7 +189,7 @@ if(option ==1)
}
}
int32_t numbits = A+24;
if(option==1)
......@@ -218,14 +218,14 @@ if(option ==1)
crc = crc24a_NB_IoT(npbch_a_x,A)>>8;
for (int j=0; j<7; j++)
for (int j=0; j<15; j++)
{
npbch_a_crc_x[j] = npbch_a_x[j];
}
npbch_a_crc_x[7] = ((uint8_t*)&crc)[2];
npbch_a_crc_x[8] = ((uint8_t*)&crc)[1];
npbch_a_crc_x[9] = ((uint8_t*)&crc)[0];
npbch_a_crc_x[15] = ((uint8_t*)&crc)[2];
npbch_a_crc_x[16] = ((uint8_t*)&crc)[1];
npbch_a_crc_x[17] = ((uint8_t*)&crc)[0];
dlsch->B = numbits; // The length of table b in bits
//memcpy(dlsch->b,a,numbits/8); // comment if option 2
......
......@@ -26,6 +26,10 @@
* \version 0.1
* \company Eurecom
* \email: knopp@eurecom.fr
* \last changes: M. Kanj, V. Savaux
* \date: 2018
* \company: b<>com
* \email: matthieu.kanj@b-com.com, vincent.savaux@b-com.com
* \note
* \warning
*/
......@@ -321,16 +325,16 @@ void rx_ulsch_NB_IoT(PHY_VARS_eNB *phy_vars_eNB,
NB_IoT_eNB_NULSCH_t **ulsch,
uint8_t cooperation_flag);
void ulsch_extract_rbs_single_NB_IoT(int32_t **rxdataF,
int32_t **rxdataF_ext,
// uint32_t first_rb,
uint16_t UL_RB_ID_NB_IoT, // index of UL NB_IoT resource block
uint8_t N_sc_RU, // number of subcarriers in UL
// uint32_t I_sc, // subcarrier indication field
uint32_t nb_rb,
uint8_t l,
uint8_t Ns,
LTE_DL_FRAME_PARMS *frame_parms);
void ulsch_extract_rbs_single_NB_IoT(int32_t **rxdataF,
int32_t **rxdataF_ext,
// uint32_t first_rb,
uint16_t UL_RB_ID_NB_IoT, // index of UL NB_IoT resource block !!! may be defined twice : in frame_parms and in NB_IoT_UL_eNB_HARQ_t
uint8_t N_sc_RU, // number of subcarriers in UL
uint8_t subframe,// uint32_t I_sc, // NB_IoT: subcarrier indication field: must be defined in higher layer
uint32_t nb_rb,
uint8_t l,
uint8_t Ns,
LTE_DL_FRAME_PARMS *frame_parms);
void ulsch_channel_level_NB_IoT(int32_t **drs_ch_estimates_ext,
LTE_DL_FRAME_PARMS *frame_parms,
......@@ -380,6 +384,7 @@ void rotate_single_carrier_NB_IoT(PHY_VARS_eNB *eNB,
int32_t **rxdataF_comp,
uint8_t UE_id,
uint8_t symbol,
uint8_t counter_msg3,
uint8_t Qm);
void fill_rbs_zeros_NB_IoT(PHY_VARS_eNB *eNB,
......@@ -402,7 +407,7 @@ int32_t ulsch_qpsk_llr_NB_IoT(PHY_VARS_eNB *eNB,
int16_t *ulsch_llr,
uint8_t symbol,
uint8_t UE_id,
int16_t **llrp);
int16_t *llrp);
void rotate_bpsk_NB_IoT(PHY_VARS_eNB *eNB,
LTE_DL_FRAME_PARMS *frame_parms,
......@@ -466,6 +471,27 @@ int dlsch_qpsk_llr_NB_IoT(NB_IoT_DL_FRAME_PARMS *frame_parms,
int16_t **llr32p,
uint8_t beamforming_mode);
/// Vincent: temporary functions
int ul_chest_tmp_NB_IoT(int32_t **rxdataF_ext,
int32_t **ul_ch_estimates,
uint8_t l, //symbol within slot
uint8_t Ns,
uint8_t counter_msg3,
LTE_DL_FRAME_PARMS *frame_parms);
void rotate_channel_sc_tmp_NB_IoT(int16_t *estimated_channel,
uint8_t l,
uint8_t Qm,
uint8_t counter_msg3);
int ul_chequal_tmp_NB_IoT(int32_t **rxdataF_ext,
int32_t **rxdataF_comp,
int32_t **ul_ch_estimates,
uint8_t l, //symbol within slot
uint8_t Ns,
LTE_DL_FRAME_PARMS *frame_parms);
///
////////////////////////////NB-IoT testing ///////////////////////////////
void clean_eNb_ulsch_NB_IoT(NB_IoT_eNB_NULSCH_t *ulsch);
......
......@@ -450,7 +450,7 @@ int32_t ulsch_bpsk_llr_NB_IoT(PHY_VARS_eNB *eNB,
{
int16_t *rxF;
uint32_t I_sc = eNB->ulsch_NB_IoT[UE_id]->harq_process->I_sc; // NB_IoT: subcarrier indication field: must be defined in higher layer
uint32_t I_sc = 11;//eNB->ulsch_NB_IoT[UE_id]->harq_process->I_sc; // NB_IoT: subcarrier indication field: must be defined in higher layer
uint16_t ul_sc_start; // subcarrier start index into UL RB
// int i;
......@@ -510,16 +510,17 @@ int32_t ulsch_qpsk_llr_NB_IoT(PHY_VARS_eNB *eNB,
int16_t *ulsch_llr,
uint8_t symbol,
uint8_t UE_id,
int16_t **llrp)
int16_t *llrp)
{
int32_t *rxF;
int32_t **llrp32 = (int32_t **)llrp;
uint32_t I_sc = eNB->ulsch_NB_IoT[UE_id]->harq_process->I_sc; // NB_IoT: subcarrier indication field: must be defined in higher layer
int32_t *llrp32; // = (int32_t *)llrp;
uint32_t I_sc = 11;//eNB->ulsch_NB_IoT[UE_id]->harq_process->I_sc; // NB_IoT: subcarrier indication field: must be defined in higher layer
uint16_t ul_sc_start; // subcarrier start index into UL RB
uint8_t Nsc_RU = eNB->ulsch_NB_IoT[UE_id]->harq_process->N_sc_RU; // Vincent: number of sc 1,3,6,12
uint8_t Nsc_RU = 1;//eNB->ulsch_NB_IoT[UE_id]->harq_process->N_sc_RU; // Vincent: number of sc 1,3,6,12
int i;
llrp32 = (int32_t *)&llrp[0];
ul_sc_start = get_UL_sc_start_NB_IoT(I_sc); // NB-IoT: get the used subcarrier in RB
rxF = (int32_t *)&rxdataF_comp[0][(symbol*frame_parms->N_RB_DL*12) + ul_sc_start];
......@@ -527,9 +528,12 @@ int32_t ulsch_qpsk_llr_NB_IoT(PHY_VARS_eNB *eNB,
for (i=0; i<Nsc_RU; i++) {
//printf("%d,%d,%d,%d,%d,%d,%d,%d\n",((int16_t *)rxF)[0],((int16_t *)rxF)[1],((int16_t *)rxF)[2],((int16_t *)rxF)[3],((int16_t *)rxF)[4],((int16_t *)rxF)[5],((int16_t *)rxF)[6],((int16_t *)rxF)[7]);
*(*llrp32) = *rxF;
/**(*llrp32) = *rxF;
rxF++;
(*llrp32)++;
(*llrp32)++;*/
llrp32[i] = rxF[i];
/*printf("\nin llr_%d === %d",ul_sc_start,(int32_t)llrp[i]);
printf("\n in llr_%d === %d",ul_sc_start,llrp32[i]);*/
}
return(0);
......@@ -606,7 +610,7 @@ void ulsch_extract_rbs_single_NB_IoT(int32_t **rxdataF,
// uint32_t first_rb,
uint16_t UL_RB_ID_NB_IoT, // index of UL NB_IoT resource block !!! may be defined twice : in frame_parms and in NB_IoT_UL_eNB_HARQ_t
uint8_t N_sc_RU, // number of subcarriers in UL
// uint32_t I_sc, // NB_IoT: subcarrier indication field: must be defined in higher layer
uint8_t subframe,// uint32_t I_sc, // NB_IoT: subcarrier indication field: must be defined in higher layer
uint32_t nb_rb,
uint8_t l,
uint8_t Ns,
......@@ -637,7 +641,8 @@ void ulsch_extract_rbs_single_NB_IoT(int32_t **rxdataF,
// Note that FFT splits the RBs
// !!! Note that frame_parms->N_RB_UL is the number of RB in LTE
// rxdataF_ext[aarx][symbol*frame_parms->N_RB_UL*12 + n] = rxdataF[aarx][UL_RB_ID_NB_IoT*12 + ul_sc_start + frame_parms->first_carrier_offset + symbol*frame_parms->ofdm_symbol_size + n];
rxdataF_ext[aarx][symbol*frame_parms->N_RB_UL*12 + n] = rxdataF[aarx][UL_RB_ID_NB_IoT*12 + frame_parms->first_carrier_offset + symbol*frame_parms->ofdm_symbol_size + n];
rxdataF_ext[aarx][symbol*frame_parms->N_RB_UL*12 + n] = rxdataF[aarx][UL_RB_ID_NB_IoT*12 + frame_parms->first_carrier_offset + (symbol)*frame_parms->ofdm_symbol_size + n];
//rxdataF_ext[aarx][symbol*12 + n] = rxdataF[aarx][UL_RB_ID_NB_IoT*12 + frame_parms->first_carrier_offset + symbol*frame_parms->ofdm_symbol_size + n];
}
......@@ -656,14 +661,15 @@ void ulsch_extract_rbs_single_NB_IoT(int32_t **rxdataF,
// }
} else { // RB NB-IoT is in the second half
for (n=0;n<12;n++){ // extract whole RB of 12 subcarriers
// Note that FFT splits the RBs
// rxdataF_ext[aarx][symbol*frame_parms->N_RB_UL*12 + n] = rxdataF[aarx][6*(2*UL_RB_ID_NB_IoT - frame_parms->N_RB_UL) + ul_sc_start + symbol*frame_parms->ofdm_symbol_size + n];
rxdataF_ext[aarx][symbol*frame_parms->N_RB_UL*12 + n] = rxdataF[aarx][6*(2*UL_RB_ID_NB_IoT - frame_parms->N_RB_UL) + symbol*frame_parms->ofdm_symbol_size + n];
rxdataF_ext[aarx][symbol*frame_parms->N_RB_UL*12 + n] = rxdataF[aarx][6*(2*UL_RB_ID_NB_IoT - frame_parms->N_RB_UL) + (symbol)*frame_parms->ofdm_symbol_size + n];
//printf(" rx_22_%d = %d ",n,rxdataF[aarx][6*(2*UL_RB_ID_NB_IoT - frame_parms->N_RB_UL) + (subframe*14+symbol)*frame_parms->ofdm_symbol_size + n]);
//printf(" rx_20_%d = %d ",n,rxdataF[aarx][6*(2*(UL_RB_ID_NB_IoT-7) - frame_parms->N_RB_UL) + (subframe*14+symbol)*frame_parms->ofdm_symbol_size + n]);
//rxdataF_ext[aarx][symbol*12 + n] = rxdataF[aarx][6*(2*UL_RB_ID_NB_IoT - frame_parms->N_RB_UL) + symbol*frame_parms->ofdm_symbol_size + n];
}
//#ifdef OFDMA_ULSCH
// rxF = &rxdataF[aarx][(1 + 6*(2*first_rb - frame_parms->N_RB_UL) + symbol*frame_parms->ofdm_symbol_size)*2];
//#else
......@@ -1340,16 +1346,22 @@ void fill_rbs_zeros_NB_IoT(PHY_VARS_eNB *eNB,
}
//for (m=0;m<12;m++)
//{ // 12 is the number of subcarriers per RB
//printf(" rxdataF_comp32_%d = %d",m,rxdataF_comp32[m]);
//}
void rotate_single_carrier_NB_IoT(PHY_VARS_eNB *eNB,
LTE_DL_FRAME_PARMS *frame_parms,
int32_t **rxdataF_comp,
uint8_t UE_id,
uint8_t symbol,
uint8_t symbol,
uint8_t counter_msg3,
uint8_t Qm)
{
uint32_t I_sc = eNB->ulsch_NB_IoT[UE_id]->harq_process->I_sc; // NB_IoT: subcarrier indication field: must be defined in higher layer
uint32_t I_sc = 11;//eNB->ulsch_NB_IoT[UE_id]->harq_process->I_sc; // NB_IoT: subcarrier indication field: must be defined in higher layer
uint16_t ul_sc_start; // subcarrier start index into UL RB
int16_t pi_2_re[2] = {32767 , 0};
int16_t pi_2_im[2] = {0 , 32768};
......@@ -1379,6 +1391,11 @@ void rotate_single_carrier_NB_IoT(PHY_VARS_eNB *eNB,
}
/*int ooo;
for (ooo=0;ooo<12;ooo++){
printf(" rx_data_%d = %d ",ooo,rxdataF_comp[0][symbol*frame_parms->N_RB_DL*12 + ooo]);
}*/
void rotate_bpsk_NB_IoT(PHY_VARS_eNB *eNB,
LTE_DL_FRAME_PARMS *frame_parms,
int32_t **rxdataF_comp,
......@@ -1619,7 +1636,7 @@ void rx_ulsch_NB_IoT(PHY_VARS_eNB *eNB,
// ulsch[UE_id]->harq_process->first_rb,
22, //ulsch[UE_id]->harq_process->UL_RB_ID_NB_IoT, // index of UL NB_IoT resource block
ulsch[UE_id]->harq_process->N_sc_RU, // number of subcarriers in UL
// ulsch[UE_id]->harq_process->I_sc, // subcarrier indication field
0,// ulsch[UE_id]->harq_process->I_sc, // subcarrier indication field
ulsch[UE_id]->harq_process->nb_rb,
l%(frame_parms->symbols_per_tti/2),
l/(frame_parms->symbols_per_tti/2),
......@@ -1889,7 +1906,8 @@ void rx_ulsch_NB_IoT(PHY_VARS_eNB *eNB,
frame_parms,
pusch_vars->rxdataF_comp[eNB_id],
UE_id,
l,
l,
0,
Qm);
}
......@@ -1906,7 +1924,8 @@ void rx_ulsch_NB_IoT(PHY_VARS_eNB *eNB,
frame_parms,
pusch_vars->rxdataF_comp[eNB_id],
UE_id,
l,
l,
0,
Qm);
......
......@@ -521,7 +521,7 @@ NB_IoT_eNB_NULSCH_t *ulsch_NB_IoT[NUMBER_OF_UE_MAX+1];
IF_Module_NB_IoT_t *if_inst;
UL_IND_NB_IoT_t UL_INFO;
uint8_t msg3_pdu[6];
//////////////////// END /////////////////////////////////
......
......@@ -76,6 +76,9 @@ typedef struct {
uint8_t dci_to_transmit;
uint32_t frame_dscr_msg3;
uint32_t subframe_dscr_msg3;
uint8_t rar_to_transmit;
uint8_t subframe_SP;
uint8_t subframe_SP2;
......@@ -86,7 +89,8 @@ typedef struct {
uint8_t there_is_sib23;
int next_frame_tx_DCI;
int next_subframe_tx_DCI;
int subframe_delay;
int subframe_real;
uint32_t sheduling_info_rar;
uint8_t flag_scrambling;
......
......@@ -26,6 +26,9 @@
* \version 0.1
* \company Eurecom
* \email: knopp@eurecom.fr,florian.kaltenberger@eurecom.fr,navid.nikaein@eurecom.fr, x.foukas@sms.ed.ac.uk
* \last changes: M. Kanj, V. Savaux
* \date: 2018
* \company: b<>com
* \email: matthieu.kanj@b-com.com, vincent.savaux@b-com.com
* \note
* \warning
......@@ -37,8 +40,8 @@
#include "SCHED/extern.h"
///////// NB-IoT testing /////////////////////
#include "PHY/extern_NB_IoT.h"
//#include "PHY/defs_NB_IoT.h"
#include "PHY/defs_NB_IoT.h"
#include "PHY/vars_NB_IoT.h"
/////////////////////////////////////////////
#include "PHY/LTE_TRANSPORT/if4_tools.h"
#include "PHY/LTE_TRANSPORT/if5_tools.h"
......@@ -124,34 +127,6 @@ extern int rx_sig_fifo;
#endif
static inline unsigned int lte_gold_unscram_NB_IoT(unsigned int *x1, unsigned int *x2, unsigned char reset) __attribute__((always_inline));
static inline unsigned int lte_gold_unscram_NB_IoT(unsigned int *x1, unsigned int *x2, unsigned char reset)
{
int n;
if (reset) {
*x1 = 1+ (1<<31);
*x2=*x2 ^ ((*x2 ^ (*x2>>1) ^ (*x2>>2) ^ (*x2>>3))<<31);
// skip first 50 double words (1600 bits)
// printf("n=0 : x1 %x, x2 %x\n",x1,x2);
for (n=1; n<50; n++) {
*x1 = (*x1>>1) ^ (*x1>>4);
*x1 = *x1 ^ (*x1<<31) ^ (*x1<<28);
*x2 = (*x2>>1) ^ (*x2>>2) ^ (*x2>>3) ^ (*x2>>4);
*x2 = *x2 ^ (*x2<<31) ^ (*x2<<30) ^ (*x2<<29) ^ (*x2<<28);
}
}
*x1 = (*x1>>1) ^ (*x1>>4);
*x1 = *x1 ^ (*x1<<31) ^ (*x1<<28);
*x2 = (*x2>>1) ^ (*x2>>2) ^ (*x2>>3) ^ (*x2>>4);
*x2 = *x2 ^ (*x2<<31) ^ (*x2<<30) ^ (*x2<<29) ^ (*x2<<28);
return(*x1^*x2);
// printf("n=%d : c %x\n",n,x1^x2);
}
uint8_t is_SR_subframe(PHY_VARS_eNB *eNB,eNB_rxtx_proc_t *proc,uint8_t UE_id)
{
......@@ -526,6 +501,9 @@ void pmch_procedures(PHY_VARS_eNB *eNB,eNB_rxtx_proc_t *proc,PHY_VARS_RN *rn,rel
#endif
}
int16_t buffer_npusch[153600];
int16_t buffer_npusch_ext[153600];
void common_signal_procedures (PHY_VARS_eNB *eNB,eNB_rxtx_proc_t *proc) {
LTE_DL_FRAME_PARMS *fp=&eNB->frame_parms;
......@@ -535,24 +513,61 @@ void common_signal_procedures (PHY_VARS_eNB *eNB,eNB_rxtx_proc_t *proc) {
int frame = proc->frame_tx;
RA_TEMPLATE *RA_template = (RA_TEMPLATE *)&eNB_mac_inst[eNB->Mod_id].common_channels[eNB->CC_id].RA_template[0];
//int With_NSSS=0;
int framerx = proc->frame_rx;
int subframerx = proc->subframe_rx;
//int With_NSSS=0;
//printf("\n in eNB_fep_full in frame_tx = %d \n",frame);
/*if (proc->flag_msg3==1 && framerx==proc->frame_msg3 && subframerx==9)
{
printf("\n\n\n\n in writing in frame %d \n\n\n\n",frame);
int16_t *Rx_buffer;
FILE *fich = fopen("xyzabc.txt","w");
Rx_buffer = &eNB->common_vars.rxdata[0][0][0]; // get the whole frame
memcpy(&buffer_npusch[0],&Rx_buffer[0],307200);
int pp;
for (pp=0;pp<153600;pp++)
{
fprintf(fich," %d ",buffer_npusch[pp]);
}
fclose(fich);
exit(0);
}*/
/////////////////////////////////////////////////////////////////////////////
/////////////////////////////////////////////////// RX NPUSH //////////////////////////////////////
if(subframe>0 && proc->flag_msg3==1 && frame==proc->frame_msg3 && proc->counter_msg3>0) ///&& frame == ????
if(subframe==proc->subframe_real && proc->flag_msg3==1 && frame==proc->frame_msg3 && proc->counter_msg3>0) ///&& frame == ????
{
proc->subframe_real++;
if(proc->subframe_real==10) ///&& frame == ????
{
proc->subframe_real=0;
proc->frame_msg3++;
}
if (proc->counter_msg3 ==8)
{
proc->frame_dscr_msg3 = framerx;
proc->subframe_dscr_msg3 = subframerx;
}
//printf("frame %d in demod NPUSCH = \n",frame);
/////////////////////////////////////////////////// NPUSH DEMOD ////////////////////////////////////
// LTE_eNB_COMMON *common_vars = &eNB->common_vars;
LTE_eNB_PUSCH *pusch_vars = eNB->pusch_vars[0];
//NB_IoT_DL_FRAME_PARMS *frame_parms = &eNB->frame_parms;
NB_IoT_eNB_NULSCH_t **ulsch_NB_IoT = &eNB->ulsch_NB_IoT[0][0];
int l,i;
int32_t avgU[2];
int32_t avgs;
uint8_t log2_maxh = 0;
NB_IoT_eNB_NULSCH_t **ulsch_NB_IoT = &eNB->ulsch_NB_IoT;//[0][0];
int l; //i;
//int32_t avgU[2];
//int32_t avgs;
//uint8_t log2_maxh = 0;
uint8_t pilot_pos1 = 3, pilot_pos2 = 10; // holds for npusch format 1, and 15 kHz subcarrier bandwidth
int16_t *llrp;
uint8_t nb_rb=1; //ulsch_NB_IoT[0]->harq_process->nb_rb, //////////////// high level parameter
//buffer_npusch = common_vars->rxdataF[0];
//printf("\n\n frame_msg3=%d subframe = %d\n",frame,proc->subframe_real);
for (l=0; l<fp->symbols_per_tti; l++)
{
......@@ -562,104 +577,89 @@ void common_signal_procedures (PHY_VARS_eNB *eNB,eNB_rxtx_proc_t *proc) {
// ulsch[UE_id]->harq_process->first_rb,
22, //ulsch[UE_id]->harq_process->UL_RB_ID_NB_IoT, // index of UL NB_IoT resource block
1, //ulsch_NB_IoT[0]->harq_process->N_sc_RU, // number of subcarriers in UL //////////////// high level parameter
// ulsch[UE_id]->harq_process->I_sc, // subcarrier indication field
(uint8_t)proc->subframe_delay,//subframe,// ulsch[UE_id]->harq_process->I_sc, // subcarrier indication field
nb_rb,
l%(fp->symbols_per_tti/2),
l/(fp->symbols_per_tti/2),
fp);
/* ul_channel_estimation_NB_IoT(eNB,proc,
0,
0,
l%(fp->symbols_per_tti/2),
l/(fp->symbols_per_tti/2),
1, // N_sc_RU
0);*/
}
/// Channel Estimation
ul_chest_tmp_NB_IoT(pusch_vars->rxdataF_ext[0],
pusch_vars->drs_ch_estimates[0],
l%(fp->symbols_per_tti/2), //symbol within slot
l/(fp->symbols_per_tti/2),
proc->counter_msg3,
fp);
/*for (i=0; i<fp->nb_antennas_rx; i++)
{
pusch_vars->ulsch_power[i] = signal_energy_nodc(pusch_vars->drs_ch_estimates[0][i], 12);
}
ulsch_channel_level_NB_IoT(pusch_vars->drs_ch_estimates[0],
fp,
avgU,
nb_rb); */
for (l=0; l<fp->symbols_per_tti; l++)
{
/*avgs = 0;
/// Equalization
ul_chequal_tmp_NB_IoT(pusch_vars->rxdataF_ext[0],
pusch_vars->rxdataF_comp[0],
pusch_vars->drs_ch_estimates[0],
l%(fp->symbols_per_tti/2), //symbol within slot
l/(fp->symbols_per_tti/2),
fp);
for (i=0; i<fp->nb_antennas_rx; i++)
{
avgs = cmax(avgs,avgU[(i<<1)]);
}
for (l=0; l<fp->symbols_per_tti; l++)
{
log2_maxh = (log2_approx(avgs)/2)+ log2_approx(fp->nb_antennas_rx-1)+4;*/
/// In case of 1 subcarrier: BPSK and QPSK should be rotated by pi/2 and pi/4, respectively
rotate_single_carrier_NB_IoT(eNB,
fp,
pusch_vars->rxdataF_comp[0],
0, // UE ID
l,
proc->counter_msg3,
2); // Qm
for (l=0; l<fp->symbols_per_tti; l++) {
}
if (l==pilot_pos1 || l==pilot_pos2) // skip pilots
{
l++;
}
/* ulsch_channel_compensation_NB_IoT(pusch_vars->rxdataF_ext[0],
pusch_vars->drs_ch_estimates[0],
pusch_vars->ul_ch_mag[0],
pusch_vars->ul_ch_magb[0],
pusch_vars->rxdataF_comp[0],
fp,
l,
2, //Qm
nb_rb,
log2_maxh); // log2_maxh+I0_shift
freq_equalization_NB_IoT(fp,
pusch_vars->rxdataF_comp[0],
pusch_vars->ul_ch_mag[0],
pusch_vars->ul_ch_magb[0],
l,
12, //NscRU: keep 12, even if the actual number of sc is not 12
2); // Qm*/
fill_rbs_zeros_NB_IoT(eNB,
fp,
pusch_vars->rxdataF_comp[0],
0, // UE ID
l);
proc->subframe_delay++;
if(proc->subframe_delay==10) ///&& frame == ????
{
proc->subframe_delay=0;
}
proc->subframe_delay++;
///////// IDFT inverse precoding is done over the whole subframe of 14 - 2 (pilots) symbols
lte_idft_NB_IoT(fp,
(uint32_t*)pusch_vars->rxdataF_comp[0][0],
12); // IDFT size
llrp = (int16_t*)&pusch_vars->llr[0];
///////// IDFT inverse precoding is done over the whole subframe of 14 - 2 (pilots) symbols
//lte_idft_NB_IoT(fp,
// (uint32_t*)pusch_vars->rxdataF_ext[0][0],
// 12); // IDFT size
llrp = (int16_t*)&pusch_vars->llr[0+ (8-proc->counter_msg3)*24];
int ii=0;
for (l=0; l<fp->symbols_per_tti; l++)
{
if (l==pilot_pos1 || l==pilot_pos2) // skip pilots
{
l++;
}
// In case of 1 subcarrier: BPSK and QPSK should be rotated by pi/2 and pi/4, respectively
//if (Nsc_RU == 1){
rotate_single_carrier_NB_IoT(eNB,
fp,
pusch_vars->rxdataF_comp[0],
0, // UE ID
l,
2); // Qm
ulsch_qpsk_llr_NB_IoT(eNB,
fp,
pusch_vars->rxdataF_comp[0],
pusch_vars->llr,
l,
l,
0, // UE ID
&llrp); //// !!! Pensez à créer un buffer de longueur 8 subframes
&llrp[ii*2]); //// !!! Pensez à créer un buffer de longueur 8 subframes
ii++;
}
/*printf("\n");
for (l=0;l<24;l++){
printf(" llr = %d ",pusch_vars->llr[(8-proc->counter_msg3)*24+l]);
}*/
/////////////////////////////////////////////////// NPUSH DECOD ////////////////////////////////////
if(proc->counter_msg3==1)
{
//printf("\nframe %d in decod NPUSCH = \n",frame);
int16_t *ulsch_llr = eNB->pusch_vars[0]->llr; //UE_id=0
//NB_IoT_DL_FRAME_PARMS *frame_parms = &eNB->frame_parms;
//NB_IoT_eNB_NULSCH_t *ulsch = eNB->ulsch[0];
......@@ -668,30 +668,47 @@ void common_signal_procedures (PHY_VARS_eNB *eNB,eNB_rxtx_proc_t *proc) {
//uint8_t harq_pid;
unsigned int A;
uint8_t Q_m;
unsigned int i2,j,j2;
unsigned int j,j2; //i2,
int iprime;
//unsigned int ret = 0;
int r,Kr;
unsigned int sumKr=0;
unsigned int G,H,Hprime,Hpp,Cmux,Rmux_prime; // Q_CQI,Q_RI=0
uint32_t x1, x2, s=0;
int16_t c;
//int16_t c;
int16_t y[6*14*1200] __attribute__((aligned(32)));
uint8_t ytag[14*1200];
int16_t cseq[6*14*1200];
uint32_t subframe = 1; // first subframe of Msg3 received // required for scrambling
//int16_t cseq[6*14*1200];
//uint32_t subframe = 1; // first subframe of Msg3 received // required for scrambling
uint32_t rnti_tmp= 65522; // true rnti should be used
uint8_t reset;
/*int16_t *Rx_buffer;
FILE *fich = fopen("xyzabc.txt","w");
Rx_buffer = &ulsch_llr[0]; // get the whole frame
memcpy(&buffer_npusch[0],&Rx_buffer[0],2*2*8*12);
int pp;
for (pp=0;pp<2*8*12;pp++)
{
fprintf(fich," %d ",buffer_npusch[pp]);
}
fclose(fich);
exit(0); */
// NB-IoT ///////////////////////////////////////////////
// x1 is set in lte_gold_generic
// x2 should not reinitialized each subframe
// x2 should be reinitialized according to 36.211 Sections 10.1.3.1 and 10.1.3.6
x2 = (rnti_tmp<<14) + ((uint32_t)subframe<<9) + ((proc->frame_msg3%2)<<13) + fp->Nid_cell; //this is c_init in 36.211 Sec 10.1.3.1
x2 = (rnti_tmp<<14) + (proc->subframe_dscr_msg3<<9) + ((proc->frame_dscr_msg3%2)<<13) + fp->Nid_cell; //this is c_init in 36.211 Sec 10.1.3.1
//ulsch_harq = ulsch[0]->harq_process;
A = 88; // ulsch_harq->TBS;
Q_m = get_Qm_ul_NB_IoT(2,1); ///// ulsch_harq->mcs,ulsch_harq->N_sc_RU
G = (1 * Q_m) * 6 * 16; // Vincent : see 36.212, Section 5.1.4.1.2
//G = ulsch_harq->N_sc_RU * Q_m) * ulsch_harq->Nsymb_UL * ulsch_harq->Nslot_UL; (= number of RE * 2 - pilots)
//printf("ulsch_harq->round = %d",ulsch_harq->round);
if (ulsch_harq->round == 0)
{
// This is a new packet, so compute quantities regarding segmentation
......@@ -706,6 +723,7 @@ void common_signal_procedures (PHY_VARS_eNB *eNB,eNB_rxtx_proc_t *proc) {
&ulsch_harq->Kminus,
&ulsch_harq->F);
// CLEAR LLR's HERE for first packet in process
//printf("\nin segmentation\n");
}
sumKr = 0;
......@@ -733,66 +751,43 @@ void common_signal_procedures (PHY_VARS_eNB *eNB,eNB_rxtx_proc_t *proc) {
Rmux_prime = Hpp/Cmux;
// Clear "tag" interleaving matrix to allow for CQI/DATA identification
memset(ytag,0,Cmux*Rmux_prime);
i = 0;
memset(y,LTE_NULL_NB_IoT,Q_m*Hpp);
// read in buffer and unscramble llrs for everything but placeholder bits
// llrs stored per symbol correspond to columns of interleaving matrix
s = lte_gold_unscram_NB_IoT(&x1, &x2, 1);
i2 = 0;
for (i=0; i<((Hpp*Q_m)>>5); i++)
{
#if defined(__x86_64__) || defined(__i386__)
#ifndef __AVX2__
((__m128i*)cseq)[i2++] = ((__m128i*)unscrambling_lut_NB_IoT)[(s&65535)<<1];
((__m128i*)cseq)[i2++] = ((__m128i*)unscrambling_lut_NB_IoT)[1+((s&65535)<<1)];
s>>=16;
((__m128i*)cseq)[i2++] = ((__m128i*)unscrambling_lut_NB_IoT)[(s&65535)<<1];
((__m128i*)cseq)[i2++] = ((__m128i*)unscrambling_lut_NB_IoT)[1+((s&65535)<<1)];
#else
((__m256i*)cseq)[i2++] = ((__m256i*)unscrambling_lut_NB_IoT)[s&65535];
((__m256i*)cseq)[i2++] = ((__m256i*)unscrambling_lut_NB_IoT)[(s>>16)&65535];
#endif
#elif defined(__arm__)
((int16x8_t*)cseq)[i2++] = ((int16x8_t*)unscrambling_lut_NB_IoT)[(s&65535)<<1];
((int16x8_t*)cseq)[i2++] = ((int16x8_t*)unscrambling_lut_NB_IoT)[1+((s&65535)<<1)];
s>>=16;
((int16x8_t*)cseq)[i2++] = ((int16x8_t*)unscrambling_lut_NB_IoT)[(s&65535)<<1];
((int16x8_t*)cseq)[i2++] = ((int16x8_t*)unscrambling_lut_NB_IoT)[1+((s&65535)<<1)];
#endif
s = lte_gold_unscram_NB_IoT(&x1, &x2, 0);
}
i = 0;
reset = 1;
switch (Q_m)
{
case 1:
for (j=0; j<Cmux; j++)
{
y[j] = cseq[j]*ulsch_llr[j];
//y[j] = cseq[j]*ulsch_llr[j]; /// To be defined for bpsk
}
break;
case 2:
for (j=0; j<Cmux; j++)
for (j=0; j<Cmux*2; j++)
{
i2 = j<<1;
for (r=0; r<Rmux_prime; r++)
{
c = cseq[i];
// printf("ulsch %d: %d * ",i,c);
y[i2++] = c*ulsch_llr[i++];
// printf("%d\n",ulsch_llr[i-1]);
c = cseq[i];
// printf("ulsch %d: %d * ",i,c);
y[i2] = c*ulsch_llr[i++];
// printf("%d\n",ulsch_llr[i-1]);
i2 = (i2+(Cmux<<1)-1);
}
if (j%32==0)
{
s = lte_gold_generic(&x1, &x2, reset);
// printf("lte_gold[%d]=%x\n",i,s);
reset = 0;
}
if (((s>>(j%32))&1)==0)
{
y[j] = -ulsch_llr[j];
}else
{
y[j] = ulsch_llr[j];
}
}
break;
}
printf("\n \n");
/*for (j=0;j<140;j++){
printf(" y = %d ",y[j]);
}*/
// CQI and Data bits
j = 0;
j2 = 0;
......@@ -808,9 +803,14 @@ void common_signal_procedures (PHY_VARS_eNB *eNB,eNB_rxtx_proc_t *proc) {
ep[6] = yp[6];
ep[7] = yp[7];
}
/*printf("\n \n");
for (j=0;j<140;j++){
printf(" e = %d ",ulsch_harq->e[j]);
}*/
// Do ULSCH Decoding for data portion
// uint8_t llr8_flag=0; // ? to be verified
// ret = eNB->td(eNB,0,harq_pid,llr8_flag);
r=0;
Kr=0;
unsigned int r_offset=0,Kr_bytes,iind;
......@@ -886,7 +886,7 @@ void common_signal_procedures (PHY_VARS_eNB *eNB,eNB_rxtx_proc_t *proc) {
1, //////////////////////////////// not used
0, //Uplink
1,
1,//ulsch_harq->rvidx,
0,//ulsch_harq->rvidx,
(ulsch_harq->round==0)?1:0, // clear
2,//get_Qm_ul(ulsch_harq->mcs),
1,
......@@ -896,11 +896,21 @@ void common_signal_procedures (PHY_VARS_eNB *eNB,eNB_rxtx_proc_t *proc) {
LOG_E(PHY,"ulsch_decoding.c: Problem in rate matching\n");
//return(-1);
}
r_offset += E;
r_offset += E;
/*printf("\n \n");
for (j=0;j<140;j++){
printf(" w = %d ",ulsch_harq->w[r][j]);
}*/
sub_block_deinterleaving_turbo(4+Kr,
&ulsch_harq->d[r][96],
ulsch_harq->w[r]);
ulsch_harq->w[r]);
/*printf("\n \n");
for (j=0;j<140;j++){
printf(" d = %d ",ulsch_harq->d[r][96+j]);
}*/
if (ulsch_harq->C == 1)
{
......@@ -908,7 +918,7 @@ void common_signal_procedures (PHY_VARS_eNB *eNB,eNB_rxtx_proc_t *proc) {
}else{
crc_type = CRC24_B;
}
// turbo decoding and CRC
ret = tc(&ulsch_harq->d[r][96],
ulsch_harq->c[r],
Kr,
......@@ -925,8 +935,10 @@ void common_signal_procedures (PHY_VARS_eNB *eNB,eNB_rxtx_proc_t *proc) {
&eNB->ulsch_tc_intl1_stats,
&eNB->ulsch_tc_intl2_stats);
if (ret != (1+ulsch_NB_IoT[0]->max_turbo_iterations))
{
if (ret != (1+ulsch_NB_IoT[0]->max_turbo_iterations))
{
//printf("\n in last cdn \n");
if (r<ulsch_harq->Cminus)
{
Kr = ulsch_harq->Kminus;
......@@ -947,21 +959,34 @@ void common_signal_procedures (PHY_VARS_eNB *eNB,eNB_rxtx_proc_t *proc) {
offset += (Kr_bytes- ((ulsch_harq->C>1)?3:0));
}
} else {
//printf("\n in last cdn break \n");
break;
}
} // r loop end
printf("pdu[0] = %d",ulsch_harq->b[0]);
printf("pdu[1] = %d",ulsch_harq->b[1]);
printf("pdu[2] = %d",ulsch_harq->b[2]);
printf("pdu[3] = %d",ulsch_harq->b[3]);
//printf("pdu[4] = %d",ulsch_harq->b[4]);
///////////////////////// scheduling of msg 4 DCI //////////////////////////
proc->flag_DCI_msg4=1;
proc->counter_DCI_msg4=4;
////////////////////////////////////////////////////////////////////////////
uint8_t *msg3 = &eNB->msg3_pdu[0];
printf("pdu[0] = %d \n",ulsch_harq->b[0]);
printf("pdu[1] = %d \n",ulsch_harq->b[1]);
printf("pdu[2] = %d \n",ulsch_harq->b[2]);
printf("pdu[3] = %d \n",ulsch_harq->b[3]);
printf("pdu[2] = %d \n",ulsch_harq->b[4]);
printf("pdu[3] = %d \n",ulsch_harq->b[5]);
printf("pdu[3] = %d \n",ulsch_harq->b[6]);
printf("pdu[3] = %d \n",ulsch_harq->b[7]);
printf("pdu[2] = %d \n",ulsch_harq->b[8]);
printf("pdu[3] = %d \n",ulsch_harq->b[9]);
uint8_t xo = 128;
int m =0;
for(m=0; m<6;m++)
{
if((ulsch_harq->b[2+m]<<7) == 128)
{
msg3[m]= (ulsch_harq->b[3+m]>>1) ^ xo;
} else {
msg3[m]= (ulsch_harq->b[3+m]>>1);
}
}
} // NPUSH decode end
proc->counter_msg3--;
......@@ -985,17 +1010,18 @@ if(proc->flag_msg4 == 1 && proc->counter_msg4 > 0)
{
NB_IoT_DL_eNB_RAR_t *rar = &eNB->ndlsch_rar.content_rar;
uint8_t tab_rar[15];
uint8_t *nas_id = &eNB->msg3_pdu[0];
//uint8_t *NAS_tab = &eNB->tab_nas;
// avoid subframe 9 and subframe 0 of next frame
tab_rar[0]=63;
tab_rar[1]=60;
tab_rar[2]=0;
tab_rar[3]=99; // NAS part 1
tab_rar[4]=64; // NAS part 2
tab_rar[5]=255; // NAS part 3
tab_rar[6]=242; // NAS part 4
tab_rar[7]=64; // NAS part 5
tab_rar[8]=0; // NAS part 6
tab_rar[3]=nas_id[0]; // NAS part 1
tab_rar[4]=nas_id[1]; // NAS part 2
tab_rar[5]=nas_id[2]; // NAS part 3
tab_rar[6]=nas_id[3]; // NAS part 4
tab_rar[7]=nas_id[4]; // NAS part 5
tab_rar[8]=nas_id[5]; // NAS part 6
tab_rar[9]=30;
tab_rar[10]=3;
tab_rar[11]=0;
......@@ -1140,6 +1166,10 @@ if(proc->flag_DCI_msg4 ==1 && proc->counter_DCI_msg4>0)
proc->frame_msg3=0;
proc->counter_msg3=0;
proc->flag_scrambling =0;
proc->subframe_real=-1;
proc->subframe_delay=-1;
proc->flag_msg4 =0;
proc->subframe_SP2 =0;
proc->subframe_SP =0;
......@@ -1462,7 +1492,7 @@ if(subframe !=5 && subframe !=0)
tab_rar[0]=64 + RA_template[0].preamble_index;
tab_rar[1]=0;
tab_rar[2]=9;
tab_rar[3]=99;
tab_rar[3]=96;
tab_rar[4]=64;
tab_rar[5]=255; // 16
tab_rar[6]=242; // 5*/
......@@ -1522,6 +1552,8 @@ if(subframe !=5 && subframe !=0)
proc->flag_msg3 =1;
proc->frame_msg3=frame+1;
proc->counter_msg3 = 8;
proc->subframe_real=9;
proc->subframe_delay=5;
}
}
......@@ -1569,6 +1601,8 @@ if(subframe !=5 && subframe !=0)
proc->flag_msg3 =1;
proc->frame_msg3=frame+1;
proc->counter_msg3 = 8;
proc->subframe_delay=5;
proc->subframe_real=9;
}
}
......
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