Commit 400900f4 authored by Laurent THOMAS's avatar Laurent THOMAS

set correct type on many variables, fix a lot of dangerous cast, remove global...

set correct type on many variables, fix a lot of dangerous cast, remove global vars that are likely race conditions in QPSK
parent 767f1b43
...@@ -27,7 +27,7 @@ ...@@ -27,7 +27,7 @@
//#define NR_CSIRS_DEBUG //#define NR_CSIRS_DEBUG
void nr_generate_csi_rs(const NR_DL_FRAME_PARMS *frame_parms, void nr_generate_csi_rs(const NR_DL_FRAME_PARMS *frame_parms,
int32_t **dataF, c16_t **dataF,
const int16_t amp, const int16_t amp,
nr_csi_info_t *nr_csi_info, nr_csi_info_t *nr_csi_info,
const nfapi_nr_dl_tti_csi_rs_pdu_rel15_t *csi_params, const nfapi_nr_dl_tti_csi_rs_pdu_rel15_t *csi_params,
...@@ -39,8 +39,8 @@ void nr_generate_csi_rs(const NR_DL_FRAME_PARMS *frame_parms, ...@@ -39,8 +39,8 @@ void nr_generate_csi_rs(const NR_DL_FRAME_PARMS *frame_parms,
uint8_t *N_ports, uint8_t *N_ports,
uint8_t *j_cdm, uint8_t *j_cdm,
uint8_t *k_overline, uint8_t *k_overline,
uint8_t *l_overline) { uint8_t *l_overline)
{
#ifdef NR_CSIRS_DEBUG #ifdef NR_CSIRS_DEBUG
LOG_I(NR_PHY, "csi_params->subcarrier_spacing = %i\n", csi_params->subcarrier_spacing); LOG_I(NR_PHY, "csi_params->subcarrier_spacing = %i\n", csi_params->subcarrier_spacing);
LOG_I(NR_PHY, "csi_params->cyclic_prefix = %i\n", csi_params->cyclic_prefix); LOG_I(NR_PHY, "csi_params->cyclic_prefix = %i\n", csi_params->cyclic_prefix);
......
...@@ -311,7 +311,7 @@ void free_nr_ru_prach_entry(RU_t *ru, int prach_id); ...@@ -311,7 +311,7 @@ void free_nr_ru_prach_entry(RU_t *ru, int prach_id);
uint8_t get_nr_prach_duration(uint8_t prach_format); uint8_t get_nr_prach_duration(uint8_t prach_format);
void nr_generate_csi_rs(const NR_DL_FRAME_PARMS *frame_parms, void nr_generate_csi_rs(const NR_DL_FRAME_PARMS *frame_parms,
int32_t **dataF, c16_t **dataF,
const int16_t amp, const int16_t amp,
nr_csi_info_t *nr_csi_info, nr_csi_info_t *nr_csi_info,
const nfapi_nr_dl_tti_csi_rs_pdu_rel15_t *csi_params, const nfapi_nr_dl_tti_csi_rs_pdu_rel15_t *csi_params,
......
...@@ -465,22 +465,22 @@ static void nr_ulsch_channel_level(int **ul_ch_estimates_ext, ...@@ -465,22 +465,22 @@ static void nr_ulsch_channel_level(int **ul_ch_estimates_ext,
simde_m_empty(); simde_m_empty();
} }
static void nr_ulsch_channel_compensation(c16_t *rxFext, static void nr_ulsch_channel_compensation(int nrOfLayers,
c16_t *chFext, int nb_rx_ant,
c16_t *ul_ch_maga, int buffer_length,
c16_t *ul_ch_magb, c16_t rxFext[][buffer_length],
c16_t *ul_ch_magc, c16_t chFext[][nb_rx_ant][buffer_length],
c16_t ul_ch_maga[][buffer_length],
c16_t ul_ch_magb[][buffer_length],
c16_t ul_ch_magc[][buffer_length],
int32_t **rxComp, int32_t **rxComp,
c16_t *rho, c16_t rho[][nrOfLayers][buffer_length],
NR_DL_FRAME_PARMS *frame_parms, NR_DL_FRAME_PARMS *frame_parms,
nfapi_nr_pusch_pdu_t* rel15_ul, nfapi_nr_pusch_pdu_t *rel15_ul,
uint32_t symbol, uint32_t symbol,
uint32_t buffer_length,
uint32_t output_shift) uint32_t output_shift)
{ {
int mod_order = rel15_ul->qam_mod_order; int mod_order = rel15_ul->qam_mod_order;
int nrOfLayers = rel15_ul->nrOfLayers;
int nb_rx_ant = frame_parms->nb_antennas_rx;
simde__m256i QAM_ampa_256 = simde_mm256_setzero_si256(); simde__m256i QAM_ampa_256 = simde_mm256_setzero_si256();
simde__m256i QAM_ampb_256 = simde_mm256_setzero_si256(); simde__m256i QAM_ampb_256 = simde_mm256_setzero_si256();
...@@ -502,32 +502,31 @@ static void nr_ulsch_channel_compensation(c16_t *rxFext, ...@@ -502,32 +502,31 @@ static void nr_ulsch_channel_compensation(c16_t *rxFext,
QAM_ampc_256 = simde_mm256_set1_epi16(QAM256_n3); QAM_ampc_256 = simde_mm256_set1_epi16(QAM256_n3);
} }
simde__m256i xmmp0, xmmp1, xmmp2, xmmp3, xmmp4;
simde__m256i complex_shuffle256 = simde_mm256_set_epi8(29,28,31,30,25,24,27,26,21,20,23,22,17,16,19,18,13,12,15,14,9,8,11,10,5,4,7,6,1,0,3,2); simde__m256i complex_shuffle256 = simde_mm256_set_epi8(29,28,31,30,25,24,27,26,21,20,23,22,17,16,19,18,13,12,15,14,9,8,11,10,5,4,7,6,1,0,3,2);
simde__m256i conj256 = simde_mm256_set_epi16(1,-1,1,-1,1,-1,1,-1,1,-1,1,-1,1,-1,1,-1); simde__m256i conj256 = simde_mm256_set_epi16(1,-1,1,-1,1,-1,1,-1,1,-1,1,-1,1,-1,1,-1);
for (int aatx = 0; aatx < nrOfLayers; aatx++) { for (int aatx = 0; aatx < nrOfLayers; aatx++) {
simde__m256i *rxComp_256 = (simde__m256i*) &rxComp[aatx * nb_rx_ant][symbol * buffer_length]; simde__m256i *rxComp_256 = (simde__m256i *)&rxComp[aatx * nb_rx_ant][symbol * buffer_length];
simde__m256i *rxF_ch_maga_256 = (simde__m256i*)&ul_ch_maga[aatx * buffer_length]; simde__m256i *rxF_ch_maga_256 = (simde__m256i *)ul_ch_maga[aatx];
simde__m256i *rxF_ch_magb_256 = (simde__m256i*)&ul_ch_magb[aatx * buffer_length]; simde__m256i *rxF_ch_magb_256 = (simde__m256i *)ul_ch_magb[aatx];
simde__m256i *rxF_ch_magc_256 = (simde__m256i*)&ul_ch_magc[aatx * buffer_length]; simde__m256i *rxF_ch_magc_256 = (simde__m256i *)ul_ch_magc[aatx];
for (int aarx = 0; aarx < nb_rx_ant; aarx++) { for (int aarx = 0; aarx < nb_rx_ant; aarx++) {
simde__m256i *rxF_256 = (simde__m256i*) &rxFext[aarx * buffer_length]; simde__m256i *rxF_256 = (simde__m256i *)rxFext[aarx];
simde__m256i *chF_256 = (simde__m256i*) &chFext[(aatx * nb_rx_ant + aarx) * buffer_length]; simde__m256i *chF_256 = (simde__m256i *)chFext[aatx][aarx];
for (int i = 0; i < buffer_length >> 3; i++) for (int i = 0; i < buffer_length >> 3; i++)
{ {
xmmp0 = simde_mm256_madd_epi16(chF_256[i], rxF_256[i]); simde__m256i xmmp0 = simde_mm256_madd_epi16(chF_256[i], rxF_256[i]);
// xmmp0 contains real part of 4 consecutive outputs (32-bit) of conj(H_m[i])*R_m[i] // xmmp0 contains real part of 4 consecutive outputs (32-bit) of conj(H_m[i])*R_m[i]
xmmp1 = simde_mm256_shuffle_epi8(chF_256[i], complex_shuffle256); simde__m256i xmmp1 = simde_mm256_shuffle_epi8(chF_256[i], complex_shuffle256);
xmmp1 = simde_mm256_sign_epi16(xmmp1, conj256); xmmp1 = simde_mm256_sign_epi16(xmmp1, conj256);
xmmp1 = simde_mm256_madd_epi16(xmmp1, rxF_256[i]); xmmp1 = simde_mm256_madd_epi16(xmmp1, rxF_256[i]);
// xmmp1 contains imag part of 4 consecutive outputs (32-bit) of conj(H_m[i])*R_m[i] // xmmp1 contains imag part of 4 consecutive outputs (32-bit) of conj(H_m[i])*R_m[i]
xmmp0 = simde_mm256_srai_epi32(xmmp0, output_shift); xmmp0 = simde_mm256_srai_epi32(xmmp0, output_shift);
xmmp1 = simde_mm256_srai_epi32(xmmp1, output_shift); xmmp1 = simde_mm256_srai_epi32(xmmp1, output_shift);
xmmp2 = simde_mm256_unpacklo_epi32(xmmp0, xmmp1); simde__m256i xmmp2 = simde_mm256_unpacklo_epi32(xmmp0, xmmp1);
xmmp3 = simde_mm256_unpackhi_epi32(xmmp0, xmmp1); simde__m256i xmmp3 = simde_mm256_unpackhi_epi32(xmmp0, xmmp1);
xmmp4 = simde_mm256_packs_epi32(xmmp2, xmmp3); simde__m256i xmmp4 = simde_mm256_packs_epi32(xmmp2, xmmp3);
xmmp0 = simde_mm256_madd_epi16(chF_256[i], chF_256[i]); // |h|^2 xmmp0 = simde_mm256_madd_epi16(chF_256[i], chF_256[i]); // |h|^2
xmmp0 = simde_mm256_srai_epi32(xmmp0, output_shift); xmmp0 = simde_mm256_srai_epi32(xmmp0, output_shift);
...@@ -549,21 +548,21 @@ static void nr_ulsch_channel_compensation(c16_t *rxFext, ...@@ -549,21 +548,21 @@ static void nr_ulsch_channel_compensation(c16_t *rxFext,
} }
if (rho != NULL) { if (rho != NULL) {
for (int atx = 0; atx < nrOfLayers; atx++) { for (int atx = 0; atx < nrOfLayers; atx++) {
simde__m256i *rho_256 = (simde__m256i * )&rho[(aatx * nrOfLayers + atx) * buffer_length]; simde__m256i *rho_256 = (simde__m256i *)rho[aatx][atx];
simde__m256i *chF_256 = (simde__m256i *)&chFext[(aatx * nb_rx_ant + aarx) * buffer_length]; simde__m256i *chF_256 = (simde__m256i *)chFext[aatx][aarx];
simde__m256i *chF2_256 = (simde__m256i *)&chFext[ (atx * nb_rx_ant + aarx) * buffer_length]; simde__m256i *chF2_256 = (simde__m256i *)chFext[atx][aarx];
for (int i = 0; i < buffer_length >> 3; i++) { for (int i = 0; i < buffer_length >> 3; i++) {
// multiply by conjugated channel // multiply by conjugated channel
xmmp0 = simde_mm256_madd_epi16(chF_256[i], chF2_256[i]); simde__m256i xmmp0 = simde_mm256_madd_epi16(chF_256[i], chF2_256[i]);
// xmmp0 contains real part of 4 consecutive outputs (32-bit) // xmmp0 contains real part of 4 consecutive outputs (32-bit)
xmmp1 = simde_mm256_shuffle_epi8(chF_256[i], complex_shuffle256); simde__m256i xmmp1 = simde_mm256_shuffle_epi8(chF_256[i], complex_shuffle256);
xmmp1 = simde_mm256_sign_epi16(xmmp1, conj256); xmmp1 = simde_mm256_sign_epi16(xmmp1, conj256);
xmmp1 = simde_mm256_madd_epi16(xmmp1, chF2_256[i]); xmmp1 = simde_mm256_madd_epi16(xmmp1, chF2_256[i]);
// xmmp0 contains imag part of 4 consecutive outputs (32-bit) // xmmp0 contains imag part of 4 consecutive outputs (32-bit)
xmmp0 = simde_mm256_srai_epi32(xmmp0, output_shift); xmmp0 = simde_mm256_srai_epi32(xmmp0, output_shift);
xmmp1 = simde_mm256_srai_epi32(xmmp1, output_shift); xmmp1 = simde_mm256_srai_epi32(xmmp1, output_shift);
xmmp2 = simde_mm256_unpacklo_epi32(xmmp0, xmmp1); simde__m256i xmmp2 = simde_mm256_unpacklo_epi32(xmmp0, xmmp1);
xmmp3 = simde_mm256_unpackhi_epi32(xmmp0, xmmp1); simde__m256i xmmp3 = simde_mm256_unpackhi_epi32(xmmp0, xmmp1);
rho_256[i] = simde_mm256_adds_epi16(rho_256[i], simde_mm256_packs_epi32(xmmp2, xmmp3)); rho_256[i] = simde_mm256_adds_epi16(rho_256[i], simde_mm256_packs_epi32(xmmp2, xmmp3));
} }
...@@ -571,20 +570,17 @@ static void nr_ulsch_channel_compensation(c16_t *rxFext, ...@@ -571,20 +570,17 @@ static void nr_ulsch_channel_compensation(c16_t *rxFext,
} }
} }
} }
simde_mm_empty();
simde_m_empty();
} }
// Zero Forcing Rx function: nr_det_HhH() // Zero Forcing Rx function: nr_det_HhH()
static void nr_ulsch_det_HhH (int32_t *after_mf_00,//a static void nr_ulsch_det_HhH(c16_t *after_mf_00, // a
int32_t *after_mf_01,//b c16_t *after_mf_01, // b
int32_t *after_mf_10,//c c16_t *after_mf_10, // c
int32_t *after_mf_11,//d c16_t *after_mf_11, // d
int32_t *det_fin,//1/ad-bc c16_t *det_fin, // 1/ad-bc
unsigned short nb_rb, unsigned short nb_rb,
unsigned char symbol, unsigned char symbol,
int32_t shift) int32_t shift)
{ {
int16_t nr_conjug2[8]__attribute__((aligned(16))) = {1,-1,1,-1,1,-1,1,-1} ; int16_t nr_conjug2[8]__attribute__((aligned(16))) = {1,-1,1,-1,1,-1,1,-1} ;
unsigned short rb; unsigned short rb;
...@@ -643,35 +639,28 @@ static void nr_ulsch_det_HhH (int32_t *after_mf_00,//a ...@@ -643,35 +639,28 @@ static void nr_ulsch_det_HhH (int32_t *after_mf_00,//a
* *
* *
* */ * */
static void nr_ulsch_conjch0_mult_ch1(int *ch0, static void nr_ulsch_conjch0_mult_ch1(c16_t *ch0, c16_t *ch1, c16_t *ch0conj_ch1, unsigned short nb_rb, unsigned char output_shift0)
int *ch1,
int32_t *ch0conj_ch1,
unsigned short nb_rb,
unsigned char output_shift0)
{ {
//This function is used to compute multiplications in H_hermitian * H matrix //This function is used to compute multiplications in H_hermitian * H matrix
short nr_conjugate[8]__attribute__((aligned(16))) = {-1,1,-1,1,-1,1,-1,1}; short nr_conjugate[8]__attribute__((aligned(16))) = {-1,1,-1,1,-1,1,-1,1};
unsigned short rb; unsigned short rb;
simde__m128i *dl_ch0_128,*dl_ch1_128, *ch0conj_ch1_128, mmtmpD0,mmtmpD1,mmtmpD2,mmtmpD3; simde__m128i *dl_ch0_128 = (simde__m128i *)ch0;
simde__m128i *dl_ch1_128 = (simde__m128i *)ch1;
dl_ch0_128 = (simde__m128i *)ch0;
dl_ch1_128 = (simde__m128i *)ch1;
ch0conj_ch1_128 = (simde__m128i *)ch0conj_ch1; simde__m128i *ch0conj_ch1_128 = (simde__m128i *)ch0conj_ch1;
for (rb=0; rb<3*nb_rb; rb++) { for (rb=0; rb<3*nb_rb; rb++) {
simde__m128i D0 = simde_mm_madd_epi16(dl_ch0_128[0], dl_ch1_128[0]);
mmtmpD0 = simde_mm_madd_epi16(dl_ch0_128[0],dl_ch1_128[0]); simde__m128i D1 = simde_mm_shufflelo_epi16(dl_ch0_128[0], SIMDE_MM_SHUFFLE(2, 3, 0, 1));
mmtmpD1 = simde_mm_shufflelo_epi16(dl_ch0_128[0], SIMDE_MM_SHUFFLE(2,3,0,1)); D1 = simde_mm_shufflehi_epi16(D1, SIMDE_MM_SHUFFLE(2, 3, 0, 1));
mmtmpD1 = simde_mm_shufflehi_epi16(mmtmpD1, SIMDE_MM_SHUFFLE(2,3,0,1)); D1 = simde_mm_sign_epi16(D1, *(simde__m128i *)nr_conjugate);
mmtmpD1 = simde_mm_sign_epi16(mmtmpD1,*(simde__m128i*)&nr_conjugate[0]); D1 = simde_mm_madd_epi16(D1, dl_ch1_128[0]);
mmtmpD1 = simde_mm_madd_epi16(mmtmpD1,dl_ch1_128[0]); D0 = simde_mm_srai_epi32(D0, output_shift0);
mmtmpD0 = simde_mm_srai_epi32(mmtmpD0,output_shift0); D1 = simde_mm_srai_epi32(D1, output_shift0);
mmtmpD1 = simde_mm_srai_epi32(mmtmpD1,output_shift0); simde__m128i D2 = simde_mm_unpacklo_epi32(D0, D1);
mmtmpD2 = simde_mm_unpacklo_epi32(mmtmpD0,mmtmpD1); simde__m128i D3 = simde_mm_unpackhi_epi32(D0, D1);
mmtmpD3 = simde_mm_unpackhi_epi32(mmtmpD0,mmtmpD1);
ch0conj_ch1_128[0] = simde_mm_packs_epi32(D2, D3);
ch0conj_ch1_128[0] = simde_mm_packs_epi32(mmtmpD2,mmtmpD3);
/*printf("\n Computing conjugates \n"); /*printf("\n Computing conjugates \n");
print_shorts("ch0:",(int16_t*)&dl_ch0_128[0]); print_shorts("ch0:",(int16_t*)&dl_ch0_128[0]);
...@@ -682,8 +671,6 @@ static void nr_ulsch_conjch0_mult_ch1(int *ch0, ...@@ -682,8 +671,6 @@ static void nr_ulsch_conjch0_mult_ch1(int *ch0,
dl_ch1_128+=1; dl_ch1_128+=1;
ch0conj_ch1_128+=1; ch0conj_ch1_128+=1;
} }
simde_mm_empty();
simde_m_empty();
} }
static simde__m128i nr_ulsch_comp_muli_sum(simde__m128i input_x, static simde__m128i nr_ulsch_comp_muli_sum(simde__m128i input_x,
...@@ -742,10 +729,7 @@ static simde__m128i nr_ulsch_comp_muli_sum(simde__m128i input_x, ...@@ -742,10 +729,7 @@ static simde__m128i nr_ulsch_comp_muli_sum(simde__m128i input_x,
//print_ints("unpack lo:",&tmp_z0[0]); //print_ints("unpack lo:",&tmp_z0[0]);
tmp_z1 = simde_mm_unpackhi_epi32(xy_re_128,xy_im_128); tmp_z1 = simde_mm_unpackhi_epi32(xy_re_128,xy_im_128);
//print_ints("unpack hi:",&tmp_z1[0]); //print_ints("unpack hi:",&tmp_z1[0]);
output = simde_mm_packs_epi32(tmp_z0,tmp_z1); output = simde_mm_packs_epi32(tmp_z0, tmp_z1);
simde_mm_empty();
simde_m_empty();
return(output); return(output);
} }
...@@ -753,61 +737,55 @@ static simde__m128i nr_ulsch_comp_muli_sum(simde__m128i input_x, ...@@ -753,61 +737,55 @@ static simde__m128i nr_ulsch_comp_muli_sum(simde__m128i input_x,
* *
* *
* */ * */
static void nr_ulsch_construct_HhH_elements(int *conjch00_ch00, static void nr_ulsch_construct_HhH_elements(c16_t *conjch00_ch00,
int *conjch01_ch01, c16_t *conjch01_ch01,
int *conjch11_ch11, c16_t *conjch11_ch11,
int *conjch10_ch10,// c16_t *conjch10_ch10, //
int *conjch20_ch20, c16_t *conjch20_ch20,
int *conjch21_ch21, c16_t *conjch21_ch21,
int *conjch30_ch30, c16_t *conjch30_ch30,
int *conjch31_ch31, c16_t *conjch31_ch31,
int *conjch00_ch01,//00_01 c16_t *conjch00_ch01, // 00_01
int *conjch01_ch00,//01_00 c16_t *conjch01_ch00, // 01_00
int *conjch10_ch11,//10_11 c16_t *conjch10_ch11, // 10_11
int *conjch11_ch10,//11_10 c16_t *conjch11_ch10, // 11_10
int *conjch20_ch21, c16_t *conjch20_ch21,
int *conjch21_ch20, c16_t *conjch21_ch20,
int *conjch30_ch31, c16_t *conjch30_ch31,
int *conjch31_ch30, c16_t *conjch31_ch30,
int32_t *after_mf_00, c16_t *after_mf_00,
int32_t *after_mf_01, c16_t *after_mf_01,
int32_t *after_mf_10, c16_t *after_mf_10,
int32_t *after_mf_11, c16_t *after_mf_11,
unsigned short nb_rb, unsigned short nb_rb,
unsigned char symbol) unsigned char symbol)
{ {
//This function is used to construct the (H_hermitian * H matrix) matrix elements //This function is used to construct the (H_hermitian * H matrix) matrix elements
unsigned short rb; unsigned short rb;
simde__m128i *conjch00_ch00_128, *conjch01_ch01_128, *conjch11_ch11_128, *conjch10_ch10_128; simde__m128i *conjch00_ch00_128 = (simde__m128i *)conjch00_ch00;
simde__m128i *conjch20_ch20_128, *conjch21_ch21_128, *conjch30_ch30_128, *conjch31_ch31_128; simde__m128i *conjch01_ch01_128 = (simde__m128i *)conjch01_ch01;
simde__m128i *conjch00_ch01_128, *conjch01_ch00_128, *conjch10_ch11_128, *conjch11_ch10_128; simde__m128i *conjch11_ch11_128 = (simde__m128i *)conjch11_ch11;
simde__m128i *conjch20_ch21_128, *conjch21_ch20_128, *conjch30_ch31_128, *conjch31_ch30_128; simde__m128i *conjch10_ch10_128 = (simde__m128i *)conjch10_ch10;
simde__m128i *after_mf_00_128, *after_mf_01_128, *after_mf_10_128, *after_mf_11_128;
simde__m128i *conjch20_ch20_128 = (simde__m128i *)conjch20_ch20;
conjch00_ch00_128 = (simde__m128i *)conjch00_ch00; simde__m128i *conjch21_ch21_128 = (simde__m128i *)conjch21_ch21;
conjch01_ch01_128 = (simde__m128i *)conjch01_ch01; simde__m128i *conjch30_ch30_128 = (simde__m128i *)conjch30_ch30;
conjch11_ch11_128 = (simde__m128i *)conjch11_ch11; simde__m128i *conjch31_ch31_128 = (simde__m128i *)conjch31_ch31;
conjch10_ch10_128 = (simde__m128i *)conjch10_ch10;
simde__m128i *conjch00_ch01_128 = (simde__m128i *)conjch00_ch01;
conjch20_ch20_128 = (simde__m128i *)conjch20_ch20; simde__m128i *conjch01_ch00_128 = (simde__m128i *)conjch01_ch00;
conjch21_ch21_128 = (simde__m128i *)conjch21_ch21; simde__m128i *conjch10_ch11_128 = (simde__m128i *)conjch10_ch11;
conjch30_ch30_128 = (simde__m128i *)conjch30_ch30; simde__m128i *conjch11_ch10_128 = (simde__m128i *)conjch11_ch10;
conjch31_ch31_128 = (simde__m128i *)conjch31_ch31;
simde__m128i *conjch20_ch21_128 = (simde__m128i *)conjch20_ch21;
conjch00_ch01_128 = (simde__m128i *)conjch00_ch01; simde__m128i *conjch21_ch20_128 = (simde__m128i *)conjch21_ch20;
conjch01_ch00_128 = (simde__m128i *)conjch01_ch00; simde__m128i *conjch30_ch31_128 = (simde__m128i *)conjch30_ch31;
conjch10_ch11_128 = (simde__m128i *)conjch10_ch11; simde__m128i *conjch31_ch30_128 = (simde__m128i *)conjch31_ch30;
conjch11_ch10_128 = (simde__m128i *)conjch11_ch10;
simde__m128i *after_mf_00_128 = (simde__m128i *)after_mf_00;
conjch20_ch21_128 = (simde__m128i *)conjch20_ch21; simde__m128i *after_mf_01_128 = (simde__m128i *)after_mf_01;
conjch21_ch20_128 = (simde__m128i *)conjch21_ch20; simde__m128i *after_mf_10_128 = (simde__m128i *)after_mf_10;
conjch30_ch31_128 = (simde__m128i *)conjch30_ch31; simde__m128i *after_mf_11_128 = (simde__m128i *)after_mf_11;
conjch31_ch30_128 = (simde__m128i *)conjch31_ch30;
after_mf_00_128 = (simde__m128i *)after_mf_00;
after_mf_01_128 = (simde__m128i *)after_mf_01;
after_mf_10_128 = (simde__m128i *)after_mf_10;
after_mf_11_128 = (simde__m128i *)after_mf_11;
for (rb=0; rb<3*nb_rb; rb++) { for (rb=0; rb<3*nb_rb; rb++) {
...@@ -862,83 +840,52 @@ static void nr_ulsch_construct_HhH_elements(int *conjch00_ch00, ...@@ -862,83 +840,52 @@ static void nr_ulsch_construct_HhH_elements(int *conjch00_ch00,
after_mf_10_128 += 1; after_mf_10_128 += 1;
after_mf_11_128 += 1; after_mf_11_128 += 1;
} }
simde_mm_empty();
simde_m_empty();
} }
// MMSE Rx function: nr_ulsch_mmse_2layers() // MMSE Rx function: nr_ulsch_mmse_2layers()
static uint8_t nr_ulsch_mmse_2layers(NR_DL_FRAME_PARMS *frame_parms, static uint8_t nr_ulsch_mmse_2layers(NR_DL_FRAME_PARMS *frame_parms,
int buffer_length,
int nb_rx_ant,
int **rxdataF_comp, int **rxdataF_comp,
int **ul_ch_mag, c16_t ul_ch_mag[][buffer_length],
int **ul_ch_magb, c16_t ul_ch_magb[][buffer_length],
int **ul_ch_magc, c16_t ul_ch_magc[][buffer_length],
int **ul_ch_estimates_ext, c16_t ul_ch_estimates_ext[][nb_rx_ant][buffer_length],
unsigned short nb_rb, unsigned short nb_rb,
unsigned char n_rx, unsigned char n_rx,
unsigned char mod_order, unsigned char mod_order,
int shift, int shift,
unsigned char symbol, unsigned char symbol,
int length, int length,
uint32_t noise_var, uint32_t noise_var)
uint32_t buffer_length)
{ {
int *ch00, *ch01, *ch10, *ch11;
int *ch20, *ch30, *ch21, *ch31;
uint32_t nb_rb_0 = length/12 + ((length%12)?1:0); uint32_t nb_rb_0 = length/12 + ((length%12)?1:0);
/* we need at least alignment to 16 bytes, let's put 32 to be sure /* we need at least alignment to 16 bytes, let's put 32 to be sure
* (maybe not necessary but doesn't hurt) * (maybe not necessary but doesn't hurt)
*/ */
int32_t conjch00_ch01[12*nb_rb] __attribute__((aligned(32))); c16_t conjch00_ch01[12 * nb_rb] __attribute__((aligned(32)));
int32_t conjch01_ch00[12*nb_rb] __attribute__((aligned(32))); c16_t conjch01_ch00[12 * nb_rb] __attribute__((aligned(32)));
int32_t conjch10_ch11[12*nb_rb] __attribute__((aligned(32))); c16_t conjch10_ch11[12 * nb_rb] __attribute__((aligned(32)));
int32_t conjch11_ch10[12*nb_rb] __attribute__((aligned(32))); c16_t conjch11_ch10[12 * nb_rb] __attribute__((aligned(32)));
int32_t conjch00_ch00[12*nb_rb] __attribute__((aligned(32))); c16_t conjch00_ch00[12 * nb_rb] __attribute__((aligned(32)));
int32_t conjch01_ch01[12*nb_rb] __attribute__((aligned(32))); c16_t conjch01_ch01[12 * nb_rb] __attribute__((aligned(32)));
int32_t conjch10_ch10[12*nb_rb] __attribute__((aligned(32))); c16_t conjch10_ch10[12 * nb_rb] __attribute__((aligned(32)));
int32_t conjch11_ch11[12*nb_rb] __attribute__((aligned(32))); c16_t conjch11_ch11[12 * nb_rb] __attribute__((aligned(32)));
int32_t conjch20_ch20[12*nb_rb] __attribute__((aligned(32))); c16_t conjch20_ch20[12 * nb_rb] __attribute__((aligned(32)));
int32_t conjch21_ch21[12*nb_rb] __attribute__((aligned(32))); c16_t conjch21_ch21[12 * nb_rb] __attribute__((aligned(32)));
int32_t conjch30_ch30[12*nb_rb] __attribute__((aligned(32))); c16_t conjch30_ch30[12 * nb_rb] __attribute__((aligned(32)));
int32_t conjch31_ch31[12*nb_rb] __attribute__((aligned(32))); c16_t conjch31_ch31[12 * nb_rb] __attribute__((aligned(32)));
int32_t conjch20_ch21[12*nb_rb] __attribute__((aligned(32))); c16_t conjch20_ch21[12 * nb_rb] __attribute__((aligned(32)));
int32_t conjch30_ch31[12*nb_rb] __attribute__((aligned(32))); c16_t conjch30_ch31[12 * nb_rb] __attribute__((aligned(32)));
int32_t conjch21_ch20[12*nb_rb] __attribute__((aligned(32))); c16_t conjch21_ch20[12 * nb_rb] __attribute__((aligned(32)));
int32_t conjch31_ch30[12*nb_rb] __attribute__((aligned(32))); c16_t conjch31_ch30[12 * nb_rb] __attribute__((aligned(32)));
int32_t af_mf_00[12*nb_rb] __attribute__((aligned(32))); c16_t af_mf_00[12 * nb_rb] __attribute__((aligned(32)));
int32_t af_mf_01[12*nb_rb] __attribute__((aligned(32))); c16_t af_mf_01[12 * nb_rb] __attribute__((aligned(32)));
int32_t af_mf_10[12*nb_rb] __attribute__((aligned(32))); c16_t af_mf_10[12 * nb_rb] __attribute__((aligned(32)));
int32_t af_mf_11[12*nb_rb] __attribute__((aligned(32))); c16_t af_mf_11[12 * nb_rb] __attribute__((aligned(32)));
int32_t determ_fin[12*nb_rb] __attribute__((aligned(32))); c16_t determ_fin[12 * nb_rb] __attribute__((aligned(32)));
switch (n_rx) {
case 2://
ch00 = &((int *)ul_ch_estimates_ext)[0 * buffer_length];
ch01 = &((int *)ul_ch_estimates_ext)[2 * buffer_length];
ch10 = &((int *)ul_ch_estimates_ext)[1 * buffer_length];
ch11 = &((int *)ul_ch_estimates_ext)[3 * buffer_length];
ch20 = NULL;
ch21 = NULL;
ch30 = NULL;
ch31 = NULL;
break;
case 4://
ch00 = &((int *)ul_ch_estimates_ext)[0 * buffer_length];
ch01 = &((int *)ul_ch_estimates_ext)[4 * buffer_length];
ch10 = &((int *)ul_ch_estimates_ext)[1 * buffer_length];
ch11 = &((int *)ul_ch_estimates_ext)[5 * buffer_length];
ch20 = &((int *)ul_ch_estimates_ext)[2 * buffer_length];
ch21 = &((int *)ul_ch_estimates_ext)[6 * buffer_length];
ch30 = &((int *)ul_ch_estimates_ext)[3 * buffer_length];
ch31 = &((int *)ul_ch_estimates_ext)[7 * buffer_length];
break;
default:
return -1;
break;
}
/* 1- Compute the rx channel matrix after compensation: (1/2^log2_max)x(H_herm x H) /* 1- Compute the rx channel matrix after compensation: (1/2^log2_max)x(H_herm x H)
* for n_rx = 2 * for n_rx = 2
...@@ -950,106 +897,46 @@ static uint8_t nr_ulsch_mmse_2layers(NR_DL_FRAME_PARMS *frame_parms, ...@@ -950,106 +897,46 @@ static uint8_t nr_ulsch_mmse_2layers(NR_DL_FRAME_PARMS *frame_parms,
if (n_rx>=2){ if (n_rx>=2){
// (1/2^log2_maxh)*conj_H_00xH_00: (1/(64*2))conjH_00*H_00*2^15 // (1/2^log2_maxh)*conj_H_00xH_00: (1/(64*2))conjH_00*H_00*2^15
nr_ulsch_conjch0_mult_ch1(ch00, nr_ulsch_conjch0_mult_ch1(ul_ch_estimates_ext[0][0], ul_ch_estimates_ext[0][0], conjch00_ch00, nb_rb_0, shift);
ch00,
conjch00_ch00,
nb_rb_0,
shift);
// (1/2^log2_maxh)*conj_H_10xH_10: (1/(64*2))conjH_10*H_10*2^15 // (1/2^log2_maxh)*conj_H_10xH_10: (1/(64*2))conjH_10*H_10*2^15
nr_ulsch_conjch0_mult_ch1(ch10, nr_ulsch_conjch0_mult_ch1(ul_ch_estimates_ext[1][0], ul_ch_estimates_ext[1][0], conjch10_ch10, nb_rb_0, shift);
ch10,
conjch10_ch10,
nb_rb_0,
shift);
// conj_H_00xH_01 // conj_H_00xH_01
nr_ulsch_conjch0_mult_ch1(ch00, nr_ulsch_conjch0_mult_ch1(ul_ch_estimates_ext[0][0],
ch01, ul_ch_estimates_ext[0][1],
conjch00_ch01, conjch00_ch01,
nb_rb_0, nb_rb_0,
shift); // this shift is equal to the channel level log2_maxh shift); // this shift is equal to the channel level log2_maxh
// conj_H_10xH_11 // conj_H_10xH_11
nr_ulsch_conjch0_mult_ch1(ch10, nr_ulsch_conjch0_mult_ch1(ul_ch_estimates_ext[1][0], ul_ch_estimates_ext[1][1], conjch10_ch11, nb_rb_0, shift);
ch11,
conjch10_ch11,
nb_rb_0,
shift);
// conj_H_01xH_01 // conj_H_01xH_01
nr_ulsch_conjch0_mult_ch1(ch01, nr_ulsch_conjch0_mult_ch1(ul_ch_estimates_ext[0][1], ul_ch_estimates_ext[0][1], conjch01_ch01, nb_rb_0, shift);
ch01,
conjch01_ch01,
nb_rb_0,
shift);
// conj_H_11xH_11 // conj_H_11xH_11
nr_ulsch_conjch0_mult_ch1(ch11, nr_ulsch_conjch0_mult_ch1(ul_ch_estimates_ext[1][1], ul_ch_estimates_ext[1][1], conjch11_ch11, nb_rb_0, shift);
ch11,
conjch11_ch11,
nb_rb_0,
shift);
// conj_H_01xH_00 // conj_H_01xH_00
nr_ulsch_conjch0_mult_ch1(ch01, nr_ulsch_conjch0_mult_ch1(ul_ch_estimates_ext[0][1], ul_ch_estimates_ext[0][0], conjch01_ch00, nb_rb_0, shift);
ch00,
conjch01_ch00,
nb_rb_0,
shift);
// conj_H_11xH_10 // conj_H_11xH_10
nr_ulsch_conjch0_mult_ch1(ch11, nr_ulsch_conjch0_mult_ch1(ul_ch_estimates_ext[1][1], ul_ch_estimates_ext[1][0], conjch11_ch10, nb_rb_0, shift);
ch10,
conjch11_ch10,
nb_rb_0,
shift);
} }
if (n_rx==4){ if (n_rx==4){
// (1/2^log2_maxh)*conj_H_20xH_20: (1/(64*2*16))conjH_20*H_20*2^15 // (1/2^log2_maxh)*conj_H_20xH_20: (1/(64*2*16))conjH_20*H_20*2^15
nr_ulsch_conjch0_mult_ch1(ch20, nr_ulsch_conjch0_mult_ch1(ul_ch_estimates_ext[2][0], ul_ch_estimates_ext[2][0], conjch20_ch20, nb_rb_0, shift);
ch20,
conjch20_ch20,
nb_rb_0,
shift);
// (1/2^log2_maxh)*conj_H_30xH_30: (1/(64*2*4))conjH_30*H_30*2^15 // (1/2^log2_maxh)*conj_H_30xH_30: (1/(64*2*4))conjH_30*H_30*2^15
nr_ulsch_conjch0_mult_ch1(ch30, nr_ulsch_conjch0_mult_ch1(ul_ch_estimates_ext[3][0], ul_ch_estimates_ext[3][0], conjch30_ch30, nb_rb_0, shift);
ch30,
conjch30_ch30,
nb_rb_0,
shift);
// (1/2^log2_maxh)*conj_H_20xH_20: (1/(64*2))conjH_20*H_20*2^15 // (1/2^log2_maxh)*conj_H_20xH_20: (1/(64*2))conjH_20*H_20*2^15
nr_ulsch_conjch0_mult_ch1(ch20, nr_ulsch_conjch0_mult_ch1(ul_ch_estimates_ext[2][0], ul_ch_estimates_ext[2][1], conjch20_ch21, nb_rb_0, shift);
ch21,
conjch20_ch21, nr_ulsch_conjch0_mult_ch1(ul_ch_estimates_ext[3][0], ul_ch_estimates_ext[3][1], conjch30_ch31, nb_rb_0, shift);
nb_rb_0,
shift); nr_ulsch_conjch0_mult_ch1(ul_ch_estimates_ext[2][1], ul_ch_estimates_ext[2][1], conjch21_ch21, nb_rb_0, shift);
nr_ulsch_conjch0_mult_ch1(ch30, nr_ulsch_conjch0_mult_ch1(ul_ch_estimates_ext[3][1], ul_ch_estimates_ext[3][1], conjch31_ch31, nb_rb_0, shift);
ch31,
conjch30_ch31,
nb_rb_0,
shift);
nr_ulsch_conjch0_mult_ch1(ch21,
ch21,
conjch21_ch21,
nb_rb_0,
shift);
nr_ulsch_conjch0_mult_ch1(ch31,
ch31,
conjch31_ch31,
nb_rb_0,
shift);
// (1/2^log2_maxh)*conj_H_20xH_20: (1/(64*2))conjH_20*H_20*2^15 // (1/2^log2_maxh)*conj_H_20xH_20: (1/(64*2))conjH_20*H_20*2^15
nr_ulsch_conjch0_mult_ch1(ch21, nr_ulsch_conjch0_mult_ch1(ul_ch_estimates_ext[2][1], ul_ch_estimates_ext[2][0], conjch21_ch20, nb_rb_0, shift);
ch20,
conjch21_ch20, nr_ulsch_conjch0_mult_ch1(ul_ch_estimates_ext[3][1], ul_ch_estimates_ext[3][0], conjch31_ch30, nb_rb_0, shift);
nb_rb_0,
shift);
nr_ulsch_conjch0_mult_ch1(ch31,
ch30,
conjch31_ch30,
nb_rb_0,
shift);
nr_ulsch_construct_HhH_elements(conjch00_ch00, nr_ulsch_construct_HhH_elements(conjch00_ch00,
conjch01_ch01, conjch01_ch01,
...@@ -1254,8 +1141,6 @@ static uint8_t nr_ulsch_mmse_2layers(NR_DL_FRAME_PARMS *frame_parms, ...@@ -1254,8 +1141,6 @@ static uint8_t nr_ulsch_mmse_2layers(NR_DL_FRAME_PARMS *frame_parms,
after_mf_c_128 += 1; after_mf_c_128 += 1;
after_mf_d_128 += 1; after_mf_d_128 += 1;
} }
simde_mm_empty();
simde_m_empty();
return(0); return(0);
} }
...@@ -1280,9 +1165,8 @@ static void inner_rx(PHY_VARS_gNB *gNB, ...@@ -1280,9 +1165,8 @@ static void inner_rx(PHY_VARS_gNB *gNB,
int buffer_length = (rel15_ul->rb_size * NR_NB_SC_PER_RB + 15) & ~15; int buffer_length = (rel15_ul->rb_size * NR_NB_SC_PER_RB + 15) & ~15;
c16_t rxFext[nb_rx_ant][buffer_length] __attribute__((aligned(32))); c16_t rxFext[nb_rx_ant][buffer_length] __attribute__((aligned(32)));
c16_t chFext[nb_layer][nb_rx_ant][buffer_length] __attribute__((aligned(32))); c16_t chFext[nb_layer][nb_rx_ant][buffer_length] __attribute__((aligned(32)));
memset(rxFext, 0, sizeof(rxFext));
memset(rxFext, 0, sizeof(c16_t) * nb_rx_ant * buffer_length); memset(chFext, 0, sizeof(chFext));
memset(chFext, 0, sizeof(c16_t) * nb_layer * nb_rx_ant* buffer_length);
for (int aarx = 0; aarx < nb_rx_ant; aarx++) { for (int aarx = 0; aarx < nb_rx_ant; aarx++) {
for (int aatx = 0; aatx < nb_layer; aatx++) { for (int aatx = 0; aatx < nb_layer; aatx++) {
...@@ -1303,35 +1187,37 @@ static void inner_rx(PHY_VARS_gNB *gNB, ...@@ -1303,35 +1187,37 @@ static void inner_rx(PHY_VARS_gNB *gNB,
c16_t rxF_ch_magb [nb_layer][buffer_length] __attribute__((aligned(32))); c16_t rxF_ch_magb [nb_layer][buffer_length] __attribute__((aligned(32)));
c16_t rxF_ch_magc [nb_layer][buffer_length] __attribute__((aligned(32))); c16_t rxF_ch_magc [nb_layer][buffer_length] __attribute__((aligned(32)));
memset(rho, 0, sizeof(c16_t) * nb_layer * nb_layer* buffer_length); memset(rho, 0, sizeof(rho));
memset(rxF_ch_maga, 0, sizeof(c16_t) * nb_layer * buffer_length); memset(rxF_ch_maga, 0, sizeof(rxF_ch_maga));
memset(rxF_ch_magb, 0, sizeof(c16_t) * nb_layer * buffer_length); memset(rxF_ch_magb, 0, sizeof(rxF_ch_magb));
memset(rxF_ch_magc, 0, sizeof(c16_t) * nb_layer * buffer_length); memset(rxF_ch_magc, 0, sizeof(rxF_ch_magc));
for (int i = 0; i < nb_layer; i++) for (int i = 0; i < nb_layer; i++)
memset(&pusch_vars->rxdataF_comp[i*nb_rx_ant][symbol * buffer_length], 0, sizeof(int32_t) * buffer_length); memset(&pusch_vars->rxdataF_comp[i * nb_rx_ant][symbol * buffer_length], 0, sizeof(c16_t) * buffer_length);
nr_ulsch_channel_compensation((c16_t*)rxFext, nr_ulsch_channel_compensation(nb_layer,
(c16_t*)chFext, nb_rx_ant,
(c16_t*)rxF_ch_maga, buffer_length,
(c16_t*)rxF_ch_magb, rxFext,
(c16_t*)rxF_ch_magc, chFext,
rxF_ch_maga,
rxF_ch_magb,
rxF_ch_magc,
pusch_vars->rxdataF_comp, pusch_vars->rxdataF_comp,
(nb_layer == 1) ? NULL : (c16_t*)rho, (nb_layer == 1) ? NULL : rho,
frame_parms, frame_parms,
rel15_ul, rel15_ul,
symbol, symbol,
buffer_length,
output_shift); output_shift);
if (nb_layer == 1 && rel15_ul->transform_precoding == transformPrecoder_enabled && rel15_ul->qam_mod_order <= 6) { if (nb_layer == 1 && rel15_ul->transform_precoding == transformPrecoder_enabled && rel15_ul->qam_mod_order <= 6) {
if (rel15_ul->qam_mod_order > 2) if (rel15_ul->qam_mod_order > 2)
nr_freq_equalization(frame_parms, nr_freq_equalization(frame_parms,
&pusch_vars->rxdataF_comp[0][symbol * buffer_length], &pusch_vars->rxdataF_comp[0][symbol * buffer_length],
(int *)rxF_ch_maga, (int *)rxF_ch_maga,
(int *)rxF_ch_magb, (int *)rxF_ch_magb,
symbol, symbol,
pusch_vars->ul_valid_re_per_slot[symbol], pusch_vars->ul_valid_re_per_slot[symbol],
rel15_ul->qam_mod_order); rel15_ul->qam_mod_order);
nr_idft(&pusch_vars->rxdataF_comp[0][symbol * buffer_length], pusch_vars->ul_valid_re_per_slot[symbol]); nr_idft(&pusch_vars->rxdataF_comp[0][symbol * buffer_length], pusch_vars->ul_valid_re_per_slot[symbol]);
} }
if (rel15_ul->pdu_bit_map & PUSCH_PDU_BITMAP_PUSCH_PTRS) { if (rel15_ul->pdu_bit_map & PUSCH_PDU_BITMAP_PUSCH_PTRS) {
...@@ -1362,31 +1248,32 @@ static void inner_rx(PHY_VARS_gNB *gNB, ...@@ -1362,31 +1248,32 @@ static void inner_rx(PHY_VARS_gNB *gNB,
} }
else { else {
nr_ulsch_mmse_2layers(frame_parms, nr_ulsch_mmse_2layers(frame_parms,
(int32_t **)pusch_vars->rxdataF_comp, buffer_length,
(int **)rxF_ch_maga, nb_rx_ant,
(int **)rxF_ch_magb, pusch_vars->rxdataF_comp,
(int **)rxF_ch_magc, rxF_ch_maga,
(int **)chFext, rxF_ch_magb,
rxF_ch_magc,
chFext,
rel15_ul->rb_size, rel15_ul->rb_size,
frame_parms->nb_antennas_rx, frame_parms->nb_antennas_rx,
rel15_ul->qam_mod_order, rel15_ul->qam_mod_order,
pusch_vars->log2_maxh, pusch_vars->log2_maxh,
symbol, symbol,
pusch_vars->ul_valid_re_per_slot[symbol], pusch_vars->ul_valid_re_per_slot[symbol],
nvar, nvar);
buffer_length);
} }
} }
if (nb_layer != 2 || rel15_ul->qam_mod_order >= 6) if (nb_layer != 2 || rel15_ul->qam_mod_order >= 6)
for (int aatx = 0; aatx < nb_layer; aatx++) for (int aatx = 0; aatx < nb_layer; aatx++)
nr_ulsch_compute_llr((int32_t*)&pusch_vars->rxdataF_comp[aatx * nb_rx_ant][symbol * buffer_length], nr_ulsch_compute_llr((int32_t *)&pusch_vars->rxdataF_comp[aatx * nb_rx_ant][symbol * buffer_length],
(int32_t*)rxF_ch_maga[aatx], (int32_t *)rxF_ch_maga[aatx],
(int32_t*)rxF_ch_magb[aatx], (int32_t *)rxF_ch_magb[aatx],
(int32_t*)rxF_ch_magc[aatx], (int32_t *)rxF_ch_magc[aatx],
&llr[aatx][pusch_vars->llr_offset[symbol]], &llr[aatx][pusch_vars->llr_offset[symbol]],
pusch_vars->ul_valid_re_per_slot[symbol], pusch_vars->ul_valid_re_per_slot[symbol],
symbol, symbol,
rel15_ul->qam_mod_order); rel15_ul->qam_mod_order);
} }
typedef struct puschSymbolProc_s { typedef struct puschSymbolProc_s {
...@@ -1415,10 +1302,9 @@ static void nr_pusch_symbol_processing(void *arg) ...@@ -1415,10 +1302,9 @@ static void nr_pusch_symbol_processing(void *arg)
NR_gNB_PUSCH *pusch_vars = &gNB->pusch_vars[ulsch_id]; NR_gNB_PUSCH *pusch_vars = &gNB->pusch_vars[ulsch_id];
for (int symbol = rdata->startSymbol; symbol < rdata->startSymbol+rdata->numSymbols; symbol++) { for (int symbol = rdata->startSymbol; symbol < rdata->startSymbol+rdata->numSymbols; symbol++) {
int dmrs_symbol_flag = (rel15_ul->ul_dmrs_symb_pos >> symbol) & 0x01; int dmrs_symbol_flag = (rel15_ul->ul_dmrs_symb_pos >> symbol) & 0x01;
if (dmrs_symbol_flag == 1) if (dmrs_symbol_flag == 1) {
{
if ((rel15_ul->ul_dmrs_symb_pos >> ((symbol + 1) % frame_parms->symbols_per_slot)) & 0x01) if ((rel15_ul->ul_dmrs_symb_pos >> ((symbol + 1) % frame_parms->symbols_per_slot)) & 0x01)
AssertFatal(1==0,"Double DMRS configuration is not yet supported\n"); AssertFatal(1 == 0, "Double DMRS configuration is not yet supported\n");
gNB->pusch_vars[ulsch_id].dmrs_symbol = symbol; gNB->pusch_vars[ulsch_id].dmrs_symbol = symbol;
} }
......
...@@ -233,14 +233,34 @@ static const short filt16_middle4[16] = {4096, 8192, 8192, 8192, 8192, 8192, 819 ...@@ -233,14 +233,34 @@ static const short filt16_middle4[16] = {4096, 8192, 8192, 8192, 8192, 8192, 819
static const short filt16_end[16] = {4096, 8192, 8192, 8192, 12288, 16384, 16384, 16384, 0, 0, 0, 0, 0, 0, 0, 0}; static const short filt16_end[16] = {4096, 8192, 8192, 8192, 12288, 16384, 16384, 16384, 0, 0, 0, 0, 0, 0, 0, 0};
// CSI-RS // CSI-RS
static const short filt24_start[24] = {12288, 11605, 10923, 10240, 9557, 8875, 8192, 7509, 6827, 6144, 5461, 4779, static const c16_t filt24_start[12] =
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}; {{12288, 11605}, {10923, 10240}, {9557, 8875}, {8192, 7509}, {6827, 6144}, {5461, 4779}, {0}, {0}, {0}, {0}, {0}, {0}};
static const short filt24_end[24] = {4096, 4779, 5461, 6144, 6827, 7509, 8192, 8875, 9557, 10240, 10923, 11605, static const c16_t filt24_end[12] = {{4096, 4779},
16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384}; {5461, 6144},
{6827, 7509},
static const short filt24_middle[24] = {4096, 4779, 5461, 6144, 6827, 7509, 8192, 8875, 9557, 10240, 10923, 11605, {8192, 8875},
12288, 11605, 10923, 10240, 9557, 8875, 8192, 7509, 6827, 6144, 5461, 4779}; {9557, 10240},
{10923, 11605},
{16384, 16384},
{16384, 16384},
{16384, 16384},
{16384, 16384},
{16384, 16384},
{16384, 16384}};
static const c16_t filt24_middle[12] = {{4096, 4779},
{5461, 6144},
{6827, 7509},
{8192, 8875},
{9557, 10240},
{10923, 11605},
{12288, 11605},
{10923, 10240},
{9557, 8875},
{8192, 7509},
{6827, 6144},
{5461, 4779}};
// UL // UL
static const short filt16_ul_p0[16] = {4096, 4096, 4096, 4096, 4096, 4096, 4096, 4096, 0, 0, 0, 0, 0, 0, 0, 0}; static const short filt16_ul_p0[16] = {4096, 4096, 4096, 4096, 4096, 4096, 4096, 4096, 0, 0, 0, 0, 0, 0, 0, 0};
......
...@@ -39,23 +39,28 @@ extern openair0_config_t openair0_cfg[]; ...@@ -39,23 +39,28 @@ extern openair0_config_t openair0_cfg[];
// #define DEBUG_PDSCH // #define DEBUG_PDSCH
// #define DEBUG_PDCCH // #define DEBUG_PDCCH
#define DEBUG_PDCCH_IQ(idx)
// #define DEBUG_PDCCH(idx) printf("pilot %d : rxF - > (%d,%d) ch -> (%d,%d), pil -> (%d,%d) \n",idx,
// rxF->r,rxF->i,ch.r,ch.i,pil->r,pil->i);
// #define DEBUG_PBCH(a...) printf(a) // #define DEBUG_PBCH(a...) printf(a)
#define DEBUG_PBCH(a...) #define DEBUG_PBCH(a...)
//#define DEBUG_PRS_CHEST // To enable PRS Matlab dumps //#define DEBUG_PRS_CHEST // To enable PRS Matlab dumps
//#define DEBUG_PRS_PRINTS // To enable PRS channel estimation debug logs //#define DEBUG_PRS_PRINTS // To enable PRS channel estimation debug logs
#define PRS_PRINTS
// #define PRS_PRINTS printf("[Rx %d] pilot %3d, SNR %+2d dB: rxF - > (%+3d, %+3d) ch -> (%+3d, %+3d), pil -> (%+d, %+d) \n", rxAnt,
// 0, snr, rxF->r,rxF->i,ch.r,ch.i,pil->r,pil->i)
#define CH_INTERP 0 #define CH_INTERP 0
#define NO_INTERP 1 #define NO_INTERP 1
/* Generic function to find the peak of channel estimation buffer */ /* Generic function to find the peak of channel estimation buffer */
void peak_estimator(int32_t *buffer, int32_t buf_len, int32_t *peak_idx, int32_t *peak_val, int32_t mean_val) static int32_t peak_estimator(int32_t *buffer, int32_t buf_len, int32_t *peak_idx, int32_t mean_val)
{ {
int32_t max_val = 0, max_idx = 0, abs_val = 0; int32_t max_val = 0, max_idx = 0, abs_val = 0;
for(int k = 0; k < buf_len; k++) for (int k = 0; k < buf_len; k++) {
{ abs_val = squaredMod(((c16_t *)buffer)[k]);
abs_val = squaredMod(((c16_t*)buffer)[k]); if (abs_val > max_val) {
if(abs_val > max_val)
{
max_val = abs_val; max_val = abs_val;
max_idx = k; max_idx = k;
} }
...@@ -64,11 +69,11 @@ void peak_estimator(int32_t *buffer, int32_t buf_len, int32_t *peak_idx, int32_t ...@@ -64,11 +69,11 @@ void peak_estimator(int32_t *buffer, int32_t buf_len, int32_t *peak_idx, int32_t
// Check for detection threshold // Check for detection threshold
LOG_D(PHY, "PRS ToA estimator: max_val %d, mean_val %d, max_idx %d\n", max_val, mean_val, max_idx); LOG_D(PHY, "PRS ToA estimator: max_val %d, mean_val %d, max_idx %d\n", max_val, mean_val, max_idx);
if ((mean_val != 0) && (max_val / mean_val > 10)) { if ((mean_val != 0) && (max_val / mean_val > 10)) {
*peak_val = max_val;
*peak_idx = max_idx; *peak_idx = max_idx;
return max_val;
} else { } else {
*peak_val = 0;
*peak_idx = 0; *peak_idx = 0;
return 0;
} }
} }
...@@ -80,12 +85,12 @@ int nr_prs_channel_estimation(uint8_t gNB_id, ...@@ -80,12 +85,12 @@ int nr_prs_channel_estimation(uint8_t gNB_id,
NR_DL_FRAME_PARMS *frame_params, NR_DL_FRAME_PARMS *frame_params,
c16_t rxdataF[][ue->frame_parms.samples_per_slot_wCP]) c16_t rxdataF[][ue->frame_parms.samples_per_slot_wCP])
{ {
uint8_t rxAnt = 0, idx = 0;
prs_config_t *prs_cfg = &ue->prs_vars[gNB_id]->prs_resource[rsc_id].prs_cfg; prs_config_t *prs_cfg = &ue->prs_vars[gNB_id]->prs_resource[rsc_id].prs_cfg;
prs_meas_t **prs_meas = ue->prs_vars[gNB_id]->prs_resource[rsc_id].prs_meas; prs_meas_t **prs_meas = ue->prs_vars[gNB_id]->prs_resource[rsc_id].prs_meas;
c16_t ch_tmp_buf[ ue->frame_parms.ofdm_symbol_size] __attribute__((aligned(32))); const int symbolSz = ue->frame_parms.ofdm_symbol_size;
int32_t chF_interpol[frame_params->nb_antennas_rx][NR_PRS_IDFT_OVERSAMP_FACTOR*ue->frame_parms.ofdm_symbol_size] __attribute__((aligned(32))); c16_t ch_tmp_buf[symbolSz] __attribute__((aligned(32)));
int32_t chT_interpol[frame_params->nb_antennas_rx][NR_PRS_IDFT_OVERSAMP_FACTOR*ue->frame_parms.ofdm_symbol_size] __attribute__((aligned(32))); int32_t chF_interpol[frame_params->nb_antennas_rx][NR_PRS_IDFT_OVERSAMP_FACTOR * symbolSz] __attribute__((aligned(32)));
int32_t chT_interpol[frame_params->nb_antennas_rx][NR_PRS_IDFT_OVERSAMP_FACTOR * symbolSz] __attribute__((aligned(32)));
memset(ch_tmp_buf,0,sizeof(ch_tmp_buf)); memset(ch_tmp_buf,0,sizeof(ch_tmp_buf));
memset(chF_interpol,0,sizeof(chF_interpol)); memset(chF_interpol,0,sizeof(chF_interpol));
memset(chT_interpol,0,sizeof(chF_interpol)); memset(chT_interpol,0,sizeof(chF_interpol));
...@@ -93,16 +98,11 @@ int nr_prs_channel_estimation(uint8_t gNB_id, ...@@ -93,16 +98,11 @@ int nr_prs_channel_estimation(uint8_t gNB_id,
int slot_prs = int slot_prs =
(proc->nr_slot_rx - rep_num * prs_cfg->PRSResourceTimeGap + frame_params->slots_per_frame) % frame_params->slots_per_frame; (proc->nr_slot_rx - rep_num * prs_cfg->PRSResourceTimeGap + frame_params->slots_per_frame) % frame_params->slots_per_frame;
int16_t *rxF, *pil, mod_prs[NR_MAX_PRS_LENGTH << 1];
const int16_t *fl, *fm, *fmm, *fml, *fmr, *fr;
int16_t ch[2] = {0}, noiseFig[2] = {0};
int16_t k_prime = 0, k = 0;
int32_t ch_pwr = 0, snr = 0, rsrp = 0, mean_val = 0, prs_toa = 0;
double ch_pwr_dbm = 0.0f; double ch_pwr_dbm = 0.0f;
#ifdef DEBUG_PRS_CHEST #ifdef DEBUG_PRS_CHEST
char filename[64] = {0}, varname[64] = {0}; char filename[64] = {0}, varname[64] = {0};
#endif #endif
int16_t *ch_tmp = (int16_t *)ch_tmp_buf; c16_t *ch_tmp = ch_tmp_buf;
int16_t scale_factor = (1.0f/(float)(prs_cfg->NumPRSSymbols))*(1<<15); int16_t scale_factor = (1.0f/(float)(prs_cfg->NumPRSSymbols))*(1<<15);
int16_t num_pilots = (12/prs_cfg->CombSize)*prs_cfg->NumRB; int16_t num_pilots = (12/prs_cfg->CombSize)*prs_cfg->NumRB;
int16_t first_half = frame_params->ofdm_symbol_size - frame_params->first_carrier_offset; int16_t first_half = frame_params->ofdm_symbol_size - frame_params->first_carrier_offset;
...@@ -111,389 +111,328 @@ int nr_prs_channel_estimation(uint8_t gNB_id, ...@@ -111,389 +111,328 @@ int nr_prs_channel_estimation(uint8_t gNB_id,
LOG_D(PHY, "start_offset %d, first_half %d, second_half %d\n", start_offset, first_half, second_half); LOG_D(PHY, "start_offset %d, first_half %d, second_half %d\n", start_offset, first_half, second_half);
int16_t k_prime_table[K_PRIME_TABLE_ROW_SIZE][K_PRIME_TABLE_COL_SIZE] = PRS_K_PRIME_TABLE; int16_t k_prime_table[K_PRIME_TABLE_ROW_SIZE][K_PRIME_TABLE_COL_SIZE] = PRS_K_PRIME_TABLE;
for(int l = prs_cfg->SymbolStart; l < prs_cfg->SymbolStart+prs_cfg->NumPRSSymbols; l++) for(int l = prs_cfg->SymbolStart; l < prs_cfg->SymbolStart+prs_cfg->NumPRSSymbols; l++) {
{
uint32_t *gold_prs = nr_gold_prs(ue->prs_vars[gNB_id]->prs_resource[rsc_id].prs_cfg.NPRSID, slot_prs, l); uint32_t *gold_prs = nr_gold_prs(ue->prs_vars[gNB_id]->prs_resource[rsc_id].prs_cfg.NPRSID, slot_prs, l);
int symInd = l-prs_cfg->SymbolStart; int symInd = l - prs_cfg->SymbolStart;
if (prs_cfg->CombSize == 2) { int k_prime;
k_prime = k_prime_table[0][symInd]; switch (prs_cfg->CombSize) {
} case 2:
else if (prs_cfg->CombSize == 4){ k_prime = k_prime_table[0][symInd];
k_prime = k_prime_table[1][symInd]; break;
} case 4:
else if (prs_cfg->CombSize == 6){ k_prime = k_prime_table[1][symInd];
k_prime = k_prime_table[2][symInd]; break;
case 6:
k_prime = k_prime_table[2][symInd];
break;
case 12:
k_prime = k_prime_table[3][symInd];
break;
default:
LOG_E(PHY, "impossible prs_cfg->CombSize %d\n", prs_cfg->CombSize);
return -1;
} }
else if (prs_cfg->CombSize == 12){
k_prime = k_prime_table[3][symInd]; #ifdef DEBUG_PRS_PRINTS
} printf(
"[gNB %d][rsc %d] PRS config l %d k_prime %d:\nprs_cfg->SymbolStart %d\nprs_cfg->NumPRSSymbols %d\nprs_cfg->NumRB "
#ifdef DEBUG_PRS_PRINTS "%d\nprs_cfg->CombSize %d\n",
printf("[gNB %d][rsc %d] PRS config l %d k_prime %d:\nprs_cfg->SymbolStart %d\nprs_cfg->NumPRSSymbols %d\nprs_cfg->NumRB %d\nprs_cfg->CombSize %d\n", gNB_id, rsc_id, l, k_prime, prs_cfg->SymbolStart, prs_cfg->NumPRSSymbols, prs_cfg->NumRB, prs_cfg->CombSize); gNB_id,
rsc_id,
l,
k_prime,
prs_cfg->SymbolStart,
prs_cfg->NumPRSSymbols,
prs_cfg->NumRB,
prs_cfg->CombSize);
#endif #endif
// Pilots generation and modulation // Pilots generation and modulation
c16_t mod_prs[NR_MAX_PRS_LENGTH];
AssertFatal(num_pilots > 0, "num_pilots needs to be gt 0 or mod_prs[0] UB"); AssertFatal(num_pilots > 0, "num_pilots needs to be gt 0 or mod_prs[0] UB");
for (int m = 0; m < num_pilots; m++) for (int m = 0; m < num_pilots; m++) {
{ int idx = (((gold_prs[(m << 1) >> 5]) >> ((m << 1) & 0x1f)) & 3);
idx = (((gold_prs[(m << 1) >> 5]) >> ((m << 1) & 0x1f)) & 3); mod_prs[m].r = nr_qpsk_mod_table[idx << 1];
mod_prs[m<<1] = nr_qpsk_mod_table[idx<<1]; mod_prs[m].i = nr_qpsk_mod_table[(idx << 1) + 1];
mod_prs[(m<<1)+1] = nr_qpsk_mod_table[(idx<<1) + 1]; }
}
for (int rxAnt = 0; rxAnt < frame_params->nb_antennas_rx; rxAnt++) {
for (rxAnt=0; rxAnt < frame_params->nb_antennas_rx; rxAnt++)
{
// reset variables // reset variables
snr = 0; int snr = 0;
rsrp = 0; int rsrp = 0;
// calculate RE offset // calculate RE offset
k = (prs_cfg->REOffset + k_prime) % prs_cfg->CombSize + prs_cfg->RBOffset * 12 + frame_params->first_carrier_offset; int k = (prs_cfg->REOffset + k_prime) % prs_cfg->CombSize + prs_cfg->RBOffset * 12 + frame_params->first_carrier_offset;
// Channel estimation and interpolation // Channel estimation and interpolation
pil = (int16_t *)&mod_prs[0]; c16_t *pil = (c16_t *)&mod_prs[0];
rxF = (int16_t *)&rxdataF[rxAnt][l*frame_params->ofdm_symbol_size + k]; c16_t *rxF = &rxdataF[rxAnt][l * frame_params->ofdm_symbol_size + k];
const c16_t *fl, *fm, *fmm, *fml, *fmr, *fr;
if(prs_cfg->CombSize == 2) if (prs_cfg->CombSize == 2) {
{
// Choose the interpolation filters // Choose the interpolation filters
switch (k_prime) { switch (k_prime) {
case 0: case 0:
fl = filt8_l0; fl = (c16_t *)filt8_l0;
fml = filt8_m0; fml = (c16_t *)filt8_m0;
fmm = filt8_mm0; fmm = (c16_t *)filt8_mm0;
fmr = filt8_mr0; fmr = (c16_t *)filt8_mr0;
fm = filt8_m0; fm = (c16_t *)filt8_m0;
fr = filt8_r0; fr = (c16_t *)filt8_r0;
break; break;
case 1: case 1:
fl = filt8_l1; fl = (c16_t *)filt8_l1;
fmm = filt8_mm1; fmm = (c16_t *)filt8_mm1;
fml = filt8_ml1; fml = (c16_t *)filt8_ml1;
fmr = fmm; fmr = (c16_t *)fmm;
fm = filt8_m1; fm = (c16_t *)filt8_m1;
fr = filt8_r1; fr = (c16_t *)filt8_r1;
break; break;
default: default:
LOG_I(PHY, "%s: ERROR!! Invalid k_prime=%d for PRS comb_size %d, symbol %d\n",__FUNCTION__, k_prime, prs_cfg->CombSize, l); LOG_I(PHY,
return(-1); "%s: ERROR!! Invalid k_prime=%d for PRS comb_size %d, symbol %d\n",
__FUNCTION__,
k_prime,
prs_cfg->CombSize,
l);
return (-1);
break; break;
} }
c16_t ch = c16mulShift(*rxF, *pil, 15);
//Start pilot // Start pilot
ch[0] = (int16_t)(((int32_t)rxF[0]*pil[0] + (int32_t)rxF[1]*pil[1])>>15); multaddRealVectorComplexScalar(fl, ch, ch_tmp, 8);
ch[1] = (int16_t)(((int32_t)rxF[1]*pil[0] - (int32_t)rxF[0]*pil[1])>>15);
multadd_real_vector_complex_scalar(fl,
ch,
ch_tmp,
8);
// SNR & RSRP estimation // SNR & RSRP estimation
rsrp += squaredMod(*((c16_t *)rxF)); rsrp += squaredMod(*rxF);
noiseFig[0] = rxF[0] - (int16_t)(((int32_t)ch[0]*pil[0] - (int32_t)ch[1]*pil[1])>>15); c16_t noiseFig = c16mulShift(ch, *pil, 15);
noiseFig[1] = rxF[1] - (int16_t)(((int32_t)ch[1]*pil[0] + (int32_t)ch[0]*pil[1])>>15); snr += 10 * log10(squaredMod(*rxF) - squaredMod(noiseFig)) - 10 * log10(squaredMod(noiseFig));
snr += 10*log10(squaredMod(*(c16_t*)rxF) - squaredMod(*(c16_t*)noiseFig)) - 10*log10(squaredMod(*(c16_t*)noiseFig)); PRS_PRINTS;
#ifdef DEBUG_PRS_PRINTS pil++;
printf("[Rx %d] pilot %3d, SNR %+2d dB: rxF - > (%+3d, %+3d) addr %p ch -> (%+3d, %+3d), pil -> (%+d, %+d) \n", rxAnt, 0, snr, rxF[0],rxF[1],&rxF[0],ch[0],ch[1],pil[0],pil[1]); k = (k + prs_cfg->CombSize) % frame_params->ofdm_symbol_size;
#endif rxF = &rxdataF[rxAnt][l * frame_params->ofdm_symbol_size + k];
pil +=2;
k = (k+prs_cfg->CombSize) % frame_params->ofdm_symbol_size; // Middle pilots
rxF = (int16_t *)&rxdataF[rxAnt][l*frame_params->ofdm_symbol_size + k]; for (int pIdx = 1; pIdx < num_pilots - 1; pIdx += 2) {
c16_t ch = c16mulShift(*rxF, *pil, 15);
//Middle pilots const c16_t *tmp = pIdx == 1 /*2nd pilot*/ ? fml : fm;
for(int pIdx = 1; pIdx < num_pilots-1; pIdx+=2) multaddRealVectorComplexScalar(tmp, ch, ch_tmp, 8);
{
ch[0] = (int16_t)(((int32_t)rxF[0]*pil[0] + (int32_t)rxF[1]*pil[1])>>15);
ch[1] = (int16_t)(((int32_t)rxF[1]*pil[0] - (int32_t)rxF[0]*pil[1])>>15);
if(pIdx == 1) // 2nd pilot
{
multadd_real_vector_complex_scalar(fml,
ch,
ch_tmp,
8);
}
else
{
multadd_real_vector_complex_scalar(fm,
ch,
ch_tmp,
8);
}
// SNR & RSRP estimation // SNR & RSRP estimation
rsrp += squaredMod(*((c16_t *)rxF)); rsrp += squaredMod(*rxF);
noiseFig[0] = rxF[0] - (int16_t)(((int32_t)ch[0]*pil[0] - (int32_t)ch[1]*pil[1])>>15); c16_t noiseFig = c16mulShift(ch, *pil, 15);
noiseFig[1] = rxF[1] - (int16_t)(((int32_t)ch[1]*pil[0] + (int32_t)ch[0]*pil[1])>>15); snr += 10 * log10(squaredMod(*rxF) - squaredMod(noiseFig)) - 10 * log10(squaredMod(noiseFig));
snr += 10*log10(squaredMod(*(c16_t*)rxF) - squaredMod(*(c16_t*)noiseFig)) - 10*log10(squaredMod(*(c16_t*)noiseFig)); PRS_PRINTS;
#ifdef DEBUG_PRS_PRINTS pil++;
printf("[Rx %d] pilot %3d, SNR %+2d dB: rxF - > (%+3d, %+3d) addr %p ch -> (%+3d, %+3d), pil -> (%+d, %+d) \n", rxAnt, pIdx, snr/(pIdx+1), rxF[0],rxF[1],&rxF[0],ch[0],ch[1],pil[0],pil[1]); k = (k + prs_cfg->CombSize) % frame_params->ofdm_symbol_size;
#endif rxF = &rxdataF[rxAnt][l * frame_params->ofdm_symbol_size + k];
pil +=2; ch = c16mulShift(*rxF, *pil, 15);
k = (k+prs_cfg->CombSize) % frame_params->ofdm_symbol_size; const c16_t *tmp2 = pIdx == num_pilots - 3 /*2nd pilot*/ ? fmr : fmm;
rxF = (int16_t *)&rxdataF[rxAnt][l*frame_params->ofdm_symbol_size + k]; multaddRealVectorComplexScalar(tmp2, ch, ch_tmp, 8);
ch[0] = (int16_t)(((int32_t)rxF[0]*pil[0] + (int32_t)rxF[1]*pil[1])>>15);
ch[1] = (int16_t)(((int32_t)rxF[1]*pil[0] - (int32_t)rxF[0]*pil[1])>>15);
if(pIdx == (num_pilots-3)) // 2nd last pilot
{
multadd_real_vector_complex_scalar(fmr,
ch,
ch_tmp,
8);
}
else
{
multadd_real_vector_complex_scalar(fmm,
ch,
ch_tmp,
8);
}
// SNR & RSRP estimation // SNR & RSRP estimation
rsrp += squaredMod(*((c16_t *)rxF)); rsrp += squaredMod(*rxF);
noiseFig[0] = rxF[0] - (int16_t)(((int32_t)ch[0]*pil[0] - (int32_t)ch[1]*pil[1])>>15); noiseFig = c16mulShift(ch, *pil, 15);
noiseFig[1] = rxF[1] - (int16_t)(((int32_t)ch[1]*pil[0] + (int32_t)ch[0]*pil[1])>>15); snr += 10 * log10(squaredMod(*rxF) - squaredMod(noiseFig)) - 10 * log10(squaredMod(noiseFig));
snr += 10*log10(squaredMod(*((c16_t*)rxF)) - squaredMod(*((c16_t*)noiseFig))) - 10*log10(squaredMod(*((c16_t*)noiseFig))); PRS_PRINTS;
#ifdef DEBUG_PRS_PRINTS pil++;
printf("[Rx %d] pilot %3d, SNR %+2d dB: rxF - > (%+3d, %+3d) addr %p ch -> (%+3d, %+3d), pil -> (%+d, %+d) \n", rxAnt, pIdx+1, snr/(pIdx+2), rxF[0],rxF[1],&rxF[0],ch[0],ch[1],pil[0],pil[1]); k = (k + prs_cfg->CombSize) % frame_params->ofdm_symbol_size;
#endif rxF = &rxdataF[rxAnt][l * frame_params->ofdm_symbol_size + k];
pil +=2; ch_tmp += 4;
k = (k+prs_cfg->CombSize) % frame_params->ofdm_symbol_size;
rxF = (int16_t *)&rxdataF[rxAnt][l*frame_params->ofdm_symbol_size + k];
ch_tmp +=8;
} }
//End pilot // End pilot
ch[0] = (int16_t)(((int32_t)rxF[0]*pil[0] + (int32_t)rxF[1]*pil[1])>>15); ch = c16mulShift(*rxF, *pil, 15);
ch[1] = (int16_t)(((int32_t)rxF[1]*pil[0] - (int32_t)rxF[0]*pil[1])>>15); multaddRealVectorComplexScalar(fr, ch, ch_tmp, 8);
multadd_real_vector_complex_scalar(fr,
ch,
ch_tmp,
8);
// SNR & RSRP estimation // SNR & RSRP estimation
rsrp += squaredMod(*((c16_t *)rxF)); rsrp += squaredMod(*rxF);
noiseFig[0] = rxF[0] - (int16_t)(((int32_t)ch[0] * pil[0] - (int32_t)ch[1] * pil[1]) >> 15); noiseFig = c16mulShift(ch, *pil, 15);
noiseFig[1] = rxF[1] - (int16_t)(((int32_t)ch[1] * pil[0] + (int32_t)ch[0] * pil[1]) >> 15); snr += 10 * log10(squaredMod(*rxF) - squaredMod(noiseFig)) - 10 * log10(squaredMod(noiseFig));
snr += 10 * log10(squaredMod(*((c16_t *)rxF)) - squaredMod(*((c16_t *)noiseFig))) - 10 * log10(squaredMod(*((c16_t *)noiseFig))); PRS_PRINTS;
#ifdef DEBUG_PRS_PRINTS } else if (prs_cfg->CombSize == 4) {
printf("[Rx %d] pilot %3d, SNR %+2d dB: rxF - > (%+3d, %+3d) addr %p ch -> (%+3d, %+3d), pil -> (%+d, %+d) \n",
rxAnt,
num_pilots - 1,
snr / num_pilots,
rxF[0],
rxF[1],
&rxF[0],
ch[0],
ch[1],
pil[0],
pil[1]);
#endif
}
else if(prs_cfg->CombSize == 4)
{
// Choose the interpolation filters // Choose the interpolation filters
switch (k_prime) { switch (k_prime) {
case 0: case 0:
fl = (short int *)filt16a_l0; fl = filt16a_l0;
fml = filt16a_mm0; fml = (c16_t *)filt16a_mm0;
fmm = filt16a_mm0; fmm = (c16_t *)filt16a_mm0;
fmr = (short int *)filt16a_m0; fmr = filt16a_m0;
fm = (short int *)filt16a_m0; fm = filt16a_m0;
fr = (short int *)filt16a_r0; fr = filt16a_r0;
break; break;
case 1: case 1:
fl = (short int *)filt16a_l1; fl = filt16a_l1;
fml = filt16a_ml1; fml = (c16_t *)filt16a_ml1;
fmm = filt16a_mm1; fmm = (c16_t *)filt16a_mm1;
fmr = filt16a_mr1; fmr = (c16_t *)filt16a_mr1;
fm = (short int *)filt16a_m1; fm = filt16a_m1;
fr = (short int *)filt16a_r1; fr = filt16a_r1;
break; break;
case 2: case 2:
fl = (short int *)filt16a_l2; fl = filt16a_l2;
fml = filt16a_ml2; fml = (c16_t *)filt16a_ml2;
fmm = filt16a_mm2; fmm = (c16_t *)filt16a_mm2;
fmr = filt16a_mr2; fmr = (c16_t *)filt16a_mr2;
fm = (short int *)filt16a_m2; fm = filt16a_m2;
fr = (short int *)filt16a_r2; fr = filt16a_r2;
break; break;
case 3: case 3:
fl = (short int *)filt16a_l3; fl = filt16a_l3;
fml = filt16a_ml3; fml = (c16_t *)filt16a_ml3;
fmm = filt16a_mm3; fmm = (c16_t *)filt16a_mm3;
fmr = filt16a_mm3; fmr = (c16_t *)filt16a_mm3;
fm = (short int *)filt16a_m3; fm = filt16a_m3;
fr = (short int *)filt16a_r3; fr = filt16a_r3;
break; break;
default: default:
LOG_I(PHY, "%s: ERROR!! Invalid k_prime=%d for PRS comb_size %d, symbol %d\n",__FUNCTION__, k_prime, prs_cfg->CombSize, l); LOG_I(PHY,
return(-1); "%s: ERROR!! Invalid k_prime=%d for PRS comb_size %d, symbol %d\n",
__FUNCTION__,
k_prime,
prs_cfg->CombSize,
l);
return (-1);
break; break;
} }
//Start pilot // Start pilot
ch[0] = (int16_t)(((int32_t)rxF[0]*pil[0] + (int32_t)rxF[1]*pil[1])>>15); c16_t ch = c16mulShift(*rxF, *pil, 15);
ch[1] = (int16_t)(((int32_t)rxF[1]*pil[0] - (int32_t)rxF[0]*pil[1])>>15); // Start pilot
multadd_real_vector_complex_scalar(fl, multaddRealVectorComplexScalar(fl, ch, ch_tmp, 8);
ch,
ch_tmp,
16);
// SNR & RSRP estimation // SNR & RSRP estimation
rsrp += squaredMod(*((c16_t *)rxF)); rsrp += squaredMod(*rxF);
noiseFig[0] = rxF[0] - (int16_t)(((int32_t)ch[0]*pil[0] - (int32_t)ch[1]*pil[1])>>15); c16_t noiseFig = c16mulShift(ch, *pil, 15);
noiseFig[1] = rxF[1] - (int16_t)(((int32_t)ch[1]*pil[0] + (int32_t)ch[0]*pil[1])>>15); snr += 10 * log10(squaredMod(*rxF) - squaredMod(noiseFig)) - 10 * log10(squaredMod(noiseFig));
snr += 10*log10(squaredMod(*((c16_t*)rxF)) - squaredMod(*((c16_t*)noiseFig))) - 10*log10(squaredMod(*((c16_t*)noiseFig))); PRS_PRINTS;
#ifdef DEBUG_PRS_PRINTS pil++;
printf("[Rx %d] pilot %3d, SNR %+2d dB: rxF - > (%+3d, %+3d) addr %p ch -> (%+3d, %+3d), pil -> (%+d, %+d) \n", rxAnt, 0, snr, rxF[0],rxF[1],&rxF[0],ch[0],ch[1],pil[0],pil[1]); k = (k + prs_cfg->CombSize) % frame_params->ofdm_symbol_size;
#endif rxF = &rxdataF[rxAnt][l * frame_params->ofdm_symbol_size + k];
pil +=2; ch = c16mulShift(*rxF, *pil, 15);
k = (k+prs_cfg->CombSize) % frame_params->ofdm_symbol_size; multaddRealVectorComplexScalar(fml, ch, ch_tmp, 8);
rxF = (int16_t *)&rxdataF[rxAnt][l*frame_params->ofdm_symbol_size + k];
ch[0] = (int16_t)(((int32_t)rxF[0]*pil[0] + (int32_t)rxF[1]*pil[1])>>15);
ch[1] = (int16_t)(((int32_t)rxF[1]*pil[0] - (int32_t)rxF[0]*pil[1])>>15);
multadd_real_vector_complex_scalar(fml,
ch,
ch_tmp,
16);
// SNR & RSRP estimation // SNR & RSRP estimation
rsrp += squaredMod(*((c16_t *)rxF)); rsrp += squaredMod(*rxF);
noiseFig[0] = rxF[0] - (int16_t)(((int32_t)ch[0]*pil[0] - (int32_t)ch[1]*pil[1])>>15); noiseFig = c16mulShift(ch, *pil, 15);
noiseFig[1] = rxF[1] - (int16_t)(((int32_t)ch[1]*pil[0] + (int32_t)ch[0]*pil[1])>>15); snr += 10 * log10(squaredMod(*rxF) - squaredMod(noiseFig)) - 10 * log10(squaredMod(noiseFig));
snr += 10*log10(squaredMod(*((c16_t*)rxF)) - squaredMod(*((c16_t*)noiseFig))) - 10*log10(squaredMod(*((c16_t*)noiseFig))); PRS_PRINTS;
#ifdef DEBUG_PRS_PRINTS pil++;
printf("[Rx %d] pilot %3d, SNR %+2d dB: rxF - > (%+3d, %+3d) addr %p ch -> (%+3d, %+3d), pil -> (%+d, %+d) \n", rxAnt, 1, snr/2, rxF[0],rxF[1],&rxF[0],ch[0],ch[1],pil[0],pil[1]); k = (k + prs_cfg->CombSize) % frame_params->ofdm_symbol_size;
#endif rxF = &rxdataF[rxAnt][l * frame_params->ofdm_symbol_size + k];
pil +=2; ch_tmp += 4;
k = (k+prs_cfg->CombSize) % frame_params->ofdm_symbol_size;
rxF = (int16_t *)&rxdataF[rxAnt][l*frame_params->ofdm_symbol_size + k]; // Middle pilots
ch_tmp +=8; for (int pIdx = 2; pIdx < num_pilots - 2; pIdx++) {
c16_t ch = c16mulShift(*rxF, *pil, 15);
//Middle pilots multaddRealVectorComplexScalar(fmm, ch, ch_tmp, 8);
for(int pIdx = 2; pIdx < num_pilots-2; pIdx++)
{
ch[0] = (int16_t)(((int32_t)rxF[0]*pil[0] + (int32_t)rxF[1]*pil[1])>>15);
ch[1] = (int16_t)(((int32_t)rxF[1]*pil[0] - (int32_t)rxF[0]*pil[1])>>15);
multadd_real_vector_complex_scalar(fmm,
ch,
ch_tmp,
16);
// SNR & RSRP estimation // SNR & RSRP estimation
rsrp += squaredMod(*((c16_t *)rxF)); rsrp += squaredMod(*rxF);
noiseFig[0] = rxF[0] - (int16_t)(((int32_t)ch[0]*pil[0] - (int32_t)ch[1]*pil[1])>>15); c16_t noiseFig = c16mulShift(ch, *pil, 15);
noiseFig[1] = rxF[1] - (int16_t)(((int32_t)ch[1]*pil[0] + (int32_t)ch[0]*pil[1])>>15); snr += 10 * log10(squaredMod(*rxF) - squaredMod(noiseFig)) - 10 * log10(squaredMod(noiseFig));
snr += 10*log10(squaredMod(*((c16_t*)rxF)) - squaredMod(*((c16_t*)noiseFig))) - 10*log10(squaredMod(*((c16_t*)noiseFig))); PRS_PRINTS;
#ifdef DEBUG_PRS_PRINTS pil++;
printf("[Rx %d] pilot %3d, SNR %+2d dB: rxF - > (%+3d, %+3d) addr %p ch -> (%+3d, %+3d), pil -> (%+d, %+d) \n", rxAnt, pIdx, snr/(pIdx+1), rxF[0],rxF[1],&rxF[0],ch[0],ch[1],pil[0],pil[1]); k = (k + prs_cfg->CombSize) % frame_params->ofdm_symbol_size;
#endif rxF = &rxdataF[rxAnt][l * frame_params->ofdm_symbol_size + k];
pil +=2; ch_tmp += 4;
k = (k+prs_cfg->CombSize) % frame_params->ofdm_symbol_size;
rxF = (int16_t *)&rxdataF[rxAnt][l*frame_params->ofdm_symbol_size + k];
ch_tmp +=8;
} }
//End pilot // End pilot
ch[0] = (int16_t)(((int32_t)rxF[0]*pil[0] + (int32_t)rxF[1]*pil[1])>>15); ch = c16mulShift(*rxF, *pil, 15);
ch[1] = (int16_t)(((int32_t)rxF[1]*pil[0] - (int32_t)rxF[0]*pil[1])>>15); multaddRealVectorComplexScalar(fmr, ch, ch_tmp, 8);
multadd_real_vector_complex_scalar(fmr,
ch,
ch_tmp,
16);
// SNR & RSRP estimation // SNR & RSRP estimation
rsrp += squaredMod(*((c16_t *)rxF)); rsrp += squaredMod(*rxF);
noiseFig[0] = rxF[0] - (int16_t)(((int32_t)ch[0]*pil[0] - (int32_t)ch[1]*pil[1])>>15); noiseFig = c16mulShift(ch, *pil, 15);
noiseFig[1] = rxF[1] - (int16_t)(((int32_t)ch[1]*pil[0] + (int32_t)ch[0]*pil[1])>>15); snr += 10 * log10(squaredMod(*rxF) - squaredMod(noiseFig)) - 10 * log10(squaredMod(noiseFig));
snr += 10*log10(squaredMod(*((c16_t*)rxF)) - squaredMod(*((c16_t*)noiseFig))) - 10*log10(squaredMod(*((c16_t*)noiseFig))); PRS_PRINTS;
#ifdef DEBUG_PRS_PRINTS pil++;
printf("[Rx %d] pilot %3d, SNR %+2d dB: rxF - > (%+3d, %+3d) addr %p ch -> (%+3d, %+3d), pil -> (%+d, %+d) \n", rxAnt, num_pilots-2, snr/(num_pilots-1), rxF[0],rxF[1],&rxF[0],ch[0],ch[1],pil[0],pil[1]); k = (k + prs_cfg->CombSize) % frame_params->ofdm_symbol_size;
#endif rxF = &rxdataF[rxAnt][l * frame_params->ofdm_symbol_size + k];
pil +=2;
k = (k+prs_cfg->CombSize) % frame_params->ofdm_symbol_size; ch = c16mulShift(*rxF, *pil, 15);
rxF = (int16_t *)&rxdataF[rxAnt][l*frame_params->ofdm_symbol_size + k]; multaddRealVectorComplexScalar(fr, ch, ch_tmp, 8);
ch[0] = (int16_t)(((int32_t)rxF[0]*pil[0] + (int32_t)rxF[1]*pil[1])>>15);
ch[1] = (int16_t)(((int32_t)rxF[1]*pil[0] - (int32_t)rxF[0]*pil[1])>>15);
multadd_real_vector_complex_scalar(fr,
ch,
ch_tmp,
16);
// SNR & RSRP estimation // SNR & RSRP estimation
rsrp += squaredMod(*((c16_t *)rxF)); rsrp += squaredMod(*rxF);
noiseFig[0] = rxF[0] - (int16_t)(((int32_t)ch[0]*pil[0] - (int32_t)ch[1]*pil[1])>>15); noiseFig = c16mulShift(ch, *pil, 15);
noiseFig[1] = rxF[1] - (int16_t)(((int32_t)ch[1]*pil[0] + (int32_t)ch[0]*pil[1])>>15); snr += 10 * log10(squaredMod(*rxF) - squaredMod(noiseFig)) - 10 * log10(squaredMod(noiseFig));
snr += 10*log10(squaredMod(*((c16_t*)rxF)) - squaredMod(*((c16_t*)noiseFig))) - 10*log10(squaredMod(*((c16_t*)noiseFig))); PRS_PRINTS;
#ifdef DEBUG_PRS_PRINTS } else {
printf("[Rx %d] pilot %3d, SNR %+2d dB: rxF - > (%+3d, %+3d) addr %p ch -> (%+3d, %+3d), pil -> (%+d, +%d) \n", rxAnt, num_pilots-1, snr/num_pilots, rxF[0],rxF[1],&rxF[0],ch[0],ch[1],pil[0],pil[1]); AssertFatal((prs_cfg->CombSize == 2) || (prs_cfg->CombSize == 4),
#endif "[%s] DL PRS CombSize other than 2 and 4 are NOT supported currently. Exiting!!!",
} __FUNCTION__);
else
{
AssertFatal((prs_cfg->CombSize == 2)||(prs_cfg->CombSize == 4), "[%s] DL PRS CombSize other than 2 and 4 are NOT supported currently. Exiting!!!", __FUNCTION__);
} }
// average out the SNR and RSRP computed // average out the SNR and RSRP computed
prs_meas[rxAnt]->snr = snr / (float)num_pilots; prs_meas[rxAnt]->snr = snr / (float)num_pilots;
prs_meas[rxAnt]->rsrp = rsrp / (float)num_pilots; prs_meas[rxAnt]->rsrp = rsrp / (float)num_pilots;
//reset channel pointer // reset channel pointer
ch_tmp = (int16_t*)ch_tmp_buf; ch_tmp = ch_tmp_buf;
} // for rxAnt } // for rxAnt
} //for l } // for l
for (rxAnt=0; rxAnt < frame_params->nb_antennas_rx; rxAnt++) for (int rxAnt = 0; rxAnt < frame_params->nb_antennas_rx; rxAnt++) {
{
// scale by averaging factor 1/NumPrsSymbols // scale by averaging factor 1/NumPrsSymbols
multadd_complex_vector_real_scalar(ch_tmp, multadd_complex_vector_real_scalar((int16_t *)ch_tmp, scale_factor, (int16_t *)ch_tmp, 1, frame_params->ofdm_symbol_size);
scale_factor,
ch_tmp,
1,
frame_params->ofdm_symbol_size);
#ifdef DEBUG_PRS_PRINTS #ifdef DEBUG_PRS_PRINTS
for (int rb = 0; rb < prs_cfg->NumRB; rb++) for (int rb = 0; rb < prs_cfg->NumRB; rb++) {
{
printf("================================================================\n"); printf("================================================================\n");
printf("\t\t\t[gNB %d][Rx %d][RB %d]\n", gNB_id, rxAnt, rb); printf("\t\t\t[gNB %d][Rx %d][RB %d]\n", gNB_id, rxAnt, rb);
printf("================================================================\n"); printf("================================================================\n");
idx = (12*rb)<<1; idx = (12 * rb) << 1;
printf("%4d %4d %4d %4d %4d %4d %4d %4d %4d %4d %4d %4d\n", ch_tmp[idx], ch_tmp[idx+1], ch_tmp[idx+2], ch_tmp[idx+3], ch_tmp[idx+4], ch_tmp[idx+5], ch_tmp[idx+6], ch_tmp[idx+7], ch_tmp[idx+8], ch_tmp[idx+9], ch_tmp[idx+10], ch_tmp[idx+11]); printf("%4d %4d %4d %4d %4d %4d %4d %4d %4d %4d %4d %4d\n",
printf("%4d %4d %4d %4d %4d %4d %4d %4d %4d %4d %4d %4d\n", ch_tmp[idx+12], ch_tmp[idx+13], ch_tmp[idx+14], ch_tmp[idx+15], ch_tmp[idx+16], ch_tmp[idx+17], ch_tmp[idx+18], ch_tmp[idx+19], ch_tmp[idx+20], ch_tmp[idx+21], ch_tmp[idx+22], ch_tmp[idx+23]); ch_tmp[idx],
ch_tmp[idx + 1],
ch_tmp[idx + 2],
ch_tmp[idx + 3],
ch_tmp[idx + 4],
ch_tmp[idx + 5],
ch_tmp[idx + 6],
ch_tmp[idx + 7],
ch_tmp[idx + 8],
ch_tmp[idx + 9],
ch_tmp[idx + 10],
ch_tmp[idx + 11]);
printf("%4d %4d %4d %4d %4d %4d %4d %4d %4d %4d %4d %4d\n",
ch_tmp[idx + 12],
ch_tmp[idx + 13],
ch_tmp[idx + 14],
ch_tmp[idx + 15],
ch_tmp[idx + 16],
ch_tmp[idx + 17],
ch_tmp[idx + 18],
ch_tmp[idx + 19],
ch_tmp[idx + 20],
ch_tmp[idx + 21],
ch_tmp[idx + 22],
ch_tmp[idx + 23]);
printf("\n"); printf("\n");
} }
#endif #endif
// Place PRS channel estimates in FFT shifted format // Place PRS channel estimates in FFT shifted format
if(first_half > 0) if(first_half > 0)
memcpy((int16_t *)&chF_interpol[rxAnt][start_offset], &ch_tmp[0], first_half * sizeof(int32_t)); memcpy(&chF_interpol[rxAnt][start_offset], ch_tmp, first_half * sizeof(c16_t));
if(second_half > 0) if(second_half > 0)
memcpy((int16_t *)&chF_interpol[rxAnt][0], &ch_tmp[first_half << 1], second_half * sizeof(int32_t)); memcpy(&chF_interpol[rxAnt][0], &ch_tmp[first_half], second_half * sizeof(c16_t));
// Convert to time domain // Convert to time domain
freq2time(NR_PRS_IDFT_OVERSAMP_FACTOR * frame_params->ofdm_symbol_size, freq2time(NR_PRS_IDFT_OVERSAMP_FACTOR * frame_params->ofdm_symbol_size,
(int16_t *)&chF_interpol[rxAnt][0], (int16_t *)chF_interpol[rxAnt],
(int16_t *)&chT_interpol[rxAnt][0]); (int16_t *)chT_interpol[rxAnt]);
// peak estimator // peak estimator
mean_val = squaredMod(((c16_t *)ch_tmp)[(prs_cfg->NumRB * 12) >> 1]); int32_t mean_val = squaredMod(ch_tmp[(prs_cfg->NumRB * 12) >> 1]);
peak_estimator(&chT_interpol[rxAnt][0], NR_PRS_IDFT_OVERSAMP_FACTOR * frame_params->ofdm_symbol_size, &prs_toa, &ch_pwr, mean_val); int32_t prs_toa;
int32_t ch_pwr =
peak_estimator(&chT_interpol[rxAnt][0], NR_PRS_IDFT_OVERSAMP_FACTOR * frame_params->ofdm_symbol_size, &prs_toa, mean_val);
// adjusting the rx_gains for channel peak power // adjusting the rx_gains for channel peak power
ch_pwr_dbm = 10 * log10(ch_pwr) + 30 - SQ15_SQUARED_NORM_FACTOR_DB - ((int)openair0_cfg[0].rx_gain[0] - (int)openair0_cfg[0].rx_gain_offset[0]) - dB_fixed(frame_params->ofdm_symbol_size); ch_pwr_dbm = 10 * log10(ch_pwr) + 30 - SQ15_SQUARED_NORM_FACTOR_DB - ((int)openair0_cfg[0].rx_gain[0] - (int)openair0_cfg[0].rx_gain_offset[0]) - dB_fixed(frame_params->ofdm_symbol_size);
prs_meas[rxAnt]->rsrp_dBm = prs_meas[rxAnt]->rsrp_dBm = 10 * log10(prs_meas[rxAnt]->rsrp) + 30 - SQ15_SQUARED_NORM_FACTOR_DB
10 * log10(prs_meas[rxAnt]->rsrp) + 30 - SQ15_SQUARED_NORM_FACTOR_DB - ((int)openair0_cfg[0].rx_gain[0] - (int)openair0_cfg[0].rx_gain_offset[0]) - dB_fixed(ue->frame_parms.ofdm_symbol_size); - ((int)openair0_cfg[0].rx_gain[0] - (int)openair0_cfg[0].rx_gain_offset[0]) - dB_fixed(symbolSz);
//prs measurements //prs measurements
prs_meas[rxAnt]->gNB_id = gNB_id; prs_meas[rxAnt]->gNB_id = gNB_id;
...@@ -567,18 +506,19 @@ c32_t nr_pbch_dmrs_correlation(const NR_DL_FRAME_PARMS *fp, ...@@ -567,18 +506,19 @@ c32_t nr_pbch_dmrs_correlation(const NR_DL_FRAME_PARMS *fp,
{ {
AssertFatal(dmrss >= 0 && dmrss < 3, "symbol %d is illegal for PBCH DM-RS \n", dmrss); AssertFatal(dmrss >= 0 && dmrss < 3, "symbol %d is illegal for PBCH DM-RS \n", dmrss);
const int symbolSz = fp->ofdm_symbol_size;
unsigned int ssb_offset = fp->first_carrier_offset + ssb_start_subcarrier; unsigned int ssb_offset = fp->first_carrier_offset + ssb_start_subcarrier;
if (ssb_offset >= fp->ofdm_symbol_size) if (ssb_offset >= symbolSz)
ssb_offset -= fp->ofdm_symbol_size; ssb_offset -= symbolSz;
int symbol_offset = fp->ofdm_symbol_size * symbol; int symbol_offset = symbolSz * symbol;
unsigned int k = Nid_cell % 4; unsigned int k = Nid_cell % 4;
DEBUG_PBCH("PBCH DMRS Correlation : gNB_id %d , OFDM size %d, Ncp=%d, k=%u symbol %d\n", DEBUG_PBCH("PBCH DMRS Correlation : gNB_id %d , OFDM size %d, Ncp=%d, k=%u symbol %d\n",
proc->gNB_id, proc->gNB_id,
ue->frame_parms.ofdm_symbol_size, symbolSz,
ue->frame_parms.Ncp, fp->Ncp,
k, k,
symbol); symbol);
...@@ -592,8 +532,8 @@ c32_t nr_pbch_dmrs_correlation(const NR_DL_FRAME_PARMS *fp, ...@@ -592,8 +532,8 @@ c32_t nr_pbch_dmrs_correlation(const NR_DL_FRAME_PARMS *fp,
c16_t *pil = pilot; c16_t *pil = pilot;
const c16_t *rxF = &rxdataF[aarx][symbol_offset + k]; const c16_t *rxF = &rxdataF[aarx][symbol_offset + k];
DEBUG_PBCH("pbch ch est pilot RB_DL %d\n", ue->frame_parms.N_RB_DL); DEBUG_PBCH("pbch ch est pilot RB_DL %d\n", fp->N_RB_DL);
DEBUG_PBCH("k %u, first_carrier %d\n", k, ue->frame_parms.first_carrier_offset); DEBUG_PBCH("k %u, first_carrier %d\n", k, fp->first_carrier_offset);
// Treat first 2 pilots specially (left edge) // Treat first 2 pilots specially (left edge)
computed_val = c32x16maddShift(*pil, rxF[re_offset], computed_val, 15); computed_val = c32x16maddShift(*pil, rxF[re_offset], computed_val, 15);
...@@ -602,42 +542,42 @@ c32_t nr_pbch_dmrs_correlation(const NR_DL_FRAME_PARMS *fp, ...@@ -602,42 +542,42 @@ c32_t nr_pbch_dmrs_correlation(const NR_DL_FRAME_PARMS *fp,
DEBUG_PBCH("pilot 0 : rxF - > (%d,%d) pil -> (%d,%d) \n", rxF[re_offset].r, rxF[re_offset].i, pil->r, pil->i); DEBUG_PBCH("pilot 0 : rxF - > (%d,%d) pil -> (%d,%d) \n", rxF[re_offset].r, rxF[re_offset].i, pil->r, pil->i);
pil++; pil++;
re_offset = (re_offset + 4) % fp->ofdm_symbol_size; re_offset = (re_offset + 4) % symbolSz;
computed_val = c32x16maddShift(*pil, rxF[re_offset], computed_val, 15); computed_val = c32x16maddShift(*pil, rxF[re_offset], computed_val, 15);
DEBUG_PBCH("pilot 1 : rxF - > (%d,%d) pil -> (%d,%d) \n", rxF[re_offset].r, rxF[re_offset].i, pil->r, pil->i); DEBUG_PBCH("pilot 1 : rxF - > (%d,%d) pil -> (%d,%d) \n", rxF[re_offset].r, rxF[re_offset].i, pil->r, pil->i);
pil++; pil++;
re_offset = (re_offset + 4) % fp->ofdm_symbol_size; re_offset = (re_offset + 4) % symbolSz;
computed_val = c32x16maddShift(*pil, rxF[re_offset], computed_val, 15); computed_val = c32x16maddShift(*pil, rxF[re_offset], computed_val, 15);
DEBUG_PBCH("pilot 2 : rxF - > (%d,%d), pil -> (%d,%d) \n", rxF[re_offset].r, rxF[re_offset].i, pil->r, pil->i); DEBUG_PBCH("pilot 2 : rxF - > (%d,%d), pil -> (%d,%d) \n", rxF[re_offset].r, rxF[re_offset].i, pil->r, pil->i);
pil++; pil++;
re_offset = (re_offset + 4) % fp->ofdm_symbol_size; re_offset = (re_offset + 4) % symbolSz;
for (int pilot_cnt = 3; pilot_cnt < (3 * 20); pilot_cnt += 3) { for (int pilot_cnt = 3; pilot_cnt < (3 * 20); pilot_cnt += 3) {
// in 2nd symbol, skip middle REs (48 with DMRS, 144 for SSS, and another 48 with DMRS) // in 2nd symbol, skip middle REs (48 with DMRS, 144 for SSS, and another 48 with DMRS)
if (dmrss == 1 && pilot_cnt == 12) { if (dmrss == 1 && pilot_cnt == 12) {
pilot_cnt=48; pilot_cnt=48;
re_offset = (re_offset + 144) % fp->ofdm_symbol_size; re_offset = (re_offset + 144) % symbolSz;
} }
computed_val = c32x16maddShift(*pil, rxF[re_offset], computed_val, 15); computed_val = c32x16maddShift(*pil, rxF[re_offset], computed_val, 15);
DEBUG_PBCH("pilot %u : rxF= (%d,%d) pil= (%d,%d) \n", pilot_cnt, rxF[re_offset].r, rxF[re_offset].i, pil->r, pil->i); DEBUG_PBCH("pilot %u : rxF= (%d,%d) pil= (%d,%d) \n", pilot_cnt, rxF[re_offset].r, rxF[re_offset].i, pil->r, pil->i);
pil++; pil++;
re_offset = (re_offset + 4) % fp->ofdm_symbol_size; re_offset = (re_offset + 4) % symbolSz;
computed_val = c32x16maddShift(*pil, rxF[re_offset], computed_val, 15); computed_val = c32x16maddShift(*pil, rxF[re_offset], computed_val, 15);
DEBUG_PBCH("pilot %u : rxF= (%d,%d) pil= (%d,%d) \n", pilot_cnt + 1, rxF[re_offset].r, rxF[re_offset].i, pil->r, pil->i); DEBUG_PBCH("pilot %u : rxF= (%d,%d) pil= (%d,%d) \n", pilot_cnt + 1, rxF[re_offset].r, rxF[re_offset].i, pil->r, pil->i);
pil++; pil++;
re_offset = (re_offset + 4) % fp->ofdm_symbol_size; re_offset = (re_offset + 4) % symbolSz;
computed_val = c32x16maddShift(*pil, rxF[re_offset], computed_val, 15); computed_val = c32x16maddShift(*pil, rxF[re_offset], computed_val, 15);
DEBUG_PBCH("pilot %u : rxF= (%d,%d) pil= (%d,%d) \n", pilot_cnt + 2, rxF[re_offset].r, rxF[re_offset].i, pil->r, pil->i); DEBUG_PBCH("pilot %u : rxF= (%d,%d) pil= (%d,%d) \n", pilot_cnt + 2, rxF[re_offset].r, rxF[re_offset].i, pil->r, pil->i);
pil++; pil++;
re_offset = (re_offset + 4) % fp->ofdm_symbol_size; re_offset = (re_offset + 4) % symbolSz;
} }
} }
return computed_val; return computed_val;
...@@ -660,7 +600,6 @@ int nr_pbch_channel_estimation(const NR_DL_FRAME_PARMS *fp, ...@@ -660,7 +600,6 @@ int nr_pbch_channel_estimation(const NR_DL_FRAME_PARMS *fp,
{ {
int Ns = proc->nr_slot_rx; int Ns = proc->nr_slot_rx;
c16_t pilot[200] __attribute__((aligned(16))); c16_t pilot[200] __attribute__((aligned(16)));
//int slot_pbch;
uint8_t nushift = 0, lastsymbol = 0, num_rbs = 0; uint8_t nushift = 0, lastsymbol = 0, num_rbs = 0;
const uint32_t *gold_seq = NULL; const uint32_t *gold_seq = NULL;
...@@ -825,7 +764,7 @@ int nr_pbch_channel_estimation(const NR_DL_FRAME_PARMS *fp, ...@@ -825,7 +764,7 @@ int nr_pbch_channel_estimation(const NR_DL_FRAME_PARMS *fp,
if (dmrss == lastsymbol) // update time statistics for last PBCH symbol if (dmrss == lastsymbol) // update time statistics for last PBCH symbol
{ {
// do ifft of channel estimate // do ifft of channel estimate
LOG_D(PHY,"Channel Impulse Computation Slot %d Symbol %d ch_offset %d\n", Ns, symbol, ch_offset); LOG_D(PHY, "Channel Impulse Computation Slot %d Symbol %d ch_offset %d\n", Ns, symbol, ch_offset);
freq2time(fp->ofdm_symbol_size, (int16_t *)&dl_ch_estimates[aarx][ch_offset], (int16_t *)&dl_ch_estimates_time[aarx]); freq2time(fp->ofdm_symbol_size, (int16_t *)&dl_ch_estimates[aarx][ch_offset], (int16_t *)&dl_ch_estimates_time[aarx]);
} }
} }
...@@ -833,6 +772,15 @@ int nr_pbch_channel_estimation(const NR_DL_FRAME_PARMS *fp, ...@@ -833,6 +772,15 @@ int nr_pbch_channel_estimation(const NR_DL_FRAME_PARMS *fp,
return(0); return(0);
} }
static inline c16_t *incrementK(c16_t *base, int *k, int max)
{
int tmp = *k + 4;
if (tmp >= max)
tmp -= max;
*k = tmp;
return base + *k + 1;
}
void nr_pdcch_channel_estimation(PHY_VARS_NR_UE *ue, void nr_pdcch_channel_estimation(PHY_VARS_NR_UE *ue,
const UE_nr_rxtx_proc_t *proc, const UE_nr_rxtx_proc_t *proc,
unsigned char symbol, unsigned char symbol,
...@@ -844,20 +792,15 @@ void nr_pdcch_channel_estimation(PHY_VARS_NR_UE *ue, ...@@ -844,20 +792,15 @@ void nr_pdcch_channel_estimation(PHY_VARS_NR_UE *ue,
c16_t rxdataF[][ue->frame_parms.samples_per_slot_wCP]) c16_t rxdataF[][ue->frame_parms.samples_per_slot_wCP])
{ {
int slot = proc->nr_slot_rx; int slot = proc->nr_slot_rx;
unsigned char aarx; const int symbolSz = ue->frame_parms.ofdm_symbol_size;
unsigned short k; const int ch_offset = symbolSz * symbol;
unsigned int pilot_cnt; const int symbol_offset = symbolSz * symbol;
int16_t ch[2],*pil,*rxF,*dl_ch;
int ch_offset,symbol_offset;
ch_offset = ue->frame_parms.ofdm_symbol_size*symbol;
symbol_offset = ue->frame_parms.ofdm_symbol_size*symbol;
int nb_rb_coreset=0; int nb_rb_coreset=0;
int coreset_start_rb=0; int coreset_start_rb=0;
get_coreset_rballoc(coreset->frequency_domain_resource,&nb_rb_coreset,&coreset_start_rb); get_coreset_rballoc(coreset->frequency_domain_resource,&nb_rb_coreset,&coreset_start_rb);
if(nb_rb_coreset==0) return; if (nb_rb_coreset == 0)
return;
#ifdef DEBUG_PDCCH #ifdef DEBUG_PDCCH
printf("pdcch_channel_estimation: first_carrier_offset %d, BWPStart %d, coreset_start_rb %d, coreset_nb_rb %d\n", printf("pdcch_channel_estimation: first_carrier_offset %d, BWPStart %d, coreset_start_rb %d, coreset_nb_rb %d\n",
...@@ -867,10 +810,10 @@ void nr_pdcch_channel_estimation(PHY_VARS_NR_UE *ue, ...@@ -867,10 +810,10 @@ void nr_pdcch_channel_estimation(PHY_VARS_NR_UE *ue,
unsigned short coreset_start_subcarrier = first_carrier_offset+(BWPStart + coreset_start_rb)*12; unsigned short coreset_start_subcarrier = first_carrier_offset+(BWPStart + coreset_start_rb)*12;
#ifdef DEBUG_PDCCH #ifdef DEBUG_PDCCH
printf("PDCCH Channel Estimation : gNB_id %d ch_offset %d, OFDM size %d, Ncp=%d, slot=%d, symbol %d\n", printf("PDCCH Channel Estimation : gNB_id %d ch_offset %d, OFDM size %d, Ncp=%d, Ns=%d, symbol %d\n",
gNB_id, gNB_id,
ch_offset, ch_offset,
ue->frame_parms.ofdm_symbol_size, symbolSz,
ue->frame_parms.Ncp, ue->frame_parms.Ncp,
slot, slot,
symbol); symbol);
...@@ -887,7 +830,7 @@ void nr_pdcch_channel_estimation(PHY_VARS_NR_UE *ue, ...@@ -887,7 +830,7 @@ void nr_pdcch_channel_estimation(PHY_VARS_NR_UE *ue,
if (coreset->CoreSetType == NFAPI_NR_CSET_CONFIG_PDCCH_CONFIG) if (coreset->CoreSetType == NFAPI_NR_CSET_CONFIG_PDCCH_CONFIG)
dmrs_ref = BWPStart; dmrs_ref = BWPStart;
// generate pilot // generate pilot
int pilot[(nb_rb_coreset + dmrs_ref) * 3] __attribute__((aligned(16))); c16_t pilot[(nb_rb_coreset + dmrs_ref) * 3] __attribute__((aligned(16)));
// Note: pilot returned by the following function is already the complex conjugate of the transmitted DMRS // Note: pilot returned by the following function is already the complex conjugate of the transmitted DMRS
nr_pdcch_dmrs_rx(ue, nr_pdcch_dmrs_rx(ue,
slot, slot,
...@@ -896,14 +839,13 @@ void nr_pdcch_channel_estimation(PHY_VARS_NR_UE *ue, ...@@ -896,14 +839,13 @@ void nr_pdcch_channel_estimation(PHY_VARS_NR_UE *ue,
2000, 2000,
(nb_rb_coreset + dmrs_ref)); (nb_rb_coreset + dmrs_ref));
for (aarx=0; aarx<ue->frame_parms.nb_antennas_rx; aarx++) { for (uint aarx = 0; aarx < ue->frame_parms.nb_antennas_rx; aarx++) {
int k = coreset_start_subcarrier;
k = coreset_start_subcarrier; c16_t *pil = pilot + dmrs_ref * 3;
pil = (int16_t *)&pilot[dmrs_ref*3]; c16_t *base = rxdataF[aarx] + symbol_offset;
rxF = (int16_t *)&rxdataF[aarx][(symbol_offset+k+1)]; c16_t *rxF = base + k + 1;
dl_ch = (int16_t *)&pdcch_dl_ch_estimates[aarx][ch_offset]; c16_t *dl_ch = pdcch_dl_ch_estimates[aarx] + ch_offset;
memset(dl_ch, 0, sizeof(*dl_ch) * symbolSz);
memset(dl_ch,0,4*(ue->frame_parms.ofdm_symbol_size));
#ifdef DEBUG_PDCCH #ifdef DEBUG_PDCCH
printf("pdcch ch est pilot addr %p RB_DL %d\n",&pilot[dmrs_ref*3], ue->frame_parms.N_RB_DL); printf("pdcch ch est pilot addr %p RB_DL %d\n",&pilot[dmrs_ref*3], ue->frame_parms.N_RB_DL);
...@@ -912,170 +854,76 @@ void nr_pdcch_channel_estimation(PHY_VARS_NR_UE *ue, ...@@ -912,170 +854,76 @@ void nr_pdcch_channel_estimation(PHY_VARS_NR_UE *ue,
printf("dl_ch addr %p\n",dl_ch); printf("dl_ch addr %p\n",dl_ch);
#endif #endif
#if CH_INTERP #if CH_INTERP
// if ((ue->frame_parms.N_RB_DL&1)==0) { // if ((ue->frame_parms.N_RB_DL&1)==0) {
// Treat first 2 pilots specially (left edge) // Treat first 2 pilots specially (left edge)
ch[0] = (int16_t)(((int32_t)pil[0]*rxF[0] - (int32_t)pil[1]*rxF[1])>>15); c16_t ch = c16mulShift(*rxF, *pil, 15);
ch[1] = (int16_t)(((int32_t)pil[0]*rxF[1] + (int32_t)pil[1]*rxF[0])>>15); DEBUG_PDCCH_IQ(0);
#ifdef DEBUG_PDCCH multaddRealVectorComplexScalar(fl, ch, dl_ch, 16);
printf("ch 0 %d\n",((int32_t)pil[0]*rxF[0] - (int32_t)pil[1]*rxF[1])); pil++;
printf("pilot 0 : rxF - > (%d,%d) addr %p ch -> (%d,%d), pil -> (%d,%d) \n",rxF[0],rxF[1],&rxF[0],ch[0],ch[1],pil[0],pil[1]); rxF = incrementK(base, &k, symbolSz);
#endif
multadd_real_vector_complex_scalar(fl,
ch,
dl_ch,
16);
pil += 2;
rxF += 8;
k += 4;
if (k >= ue->frame_parms.ofdm_symbol_size) {
k -= ue->frame_parms.ofdm_symbol_size;
rxF = (int16_t *)&rxdataF[aarx][(symbol_offset+k+1)];
}
ch[0] = (int16_t)(((int32_t)pil[0]*rxF[0] - (int32_t)pil[1]*rxF[1])>>15);
ch[1] = (int16_t)(((int32_t)pil[0]*rxF[1] + (int32_t)pil[1]*rxF[0])>>15);
#ifdef DEBUG_PDCCH
printf("pilot 1 : rxF - > (%d,%d) ch -> (%d,%d), pil -> (%d,%d) \n",rxF[0],rxF[1],ch[0],ch[1],pil[0],pil[1]);
#endif
multadd_real_vector_complex_scalar(fm,
ch,
dl_ch,
16);
pil += 2;
rxF += 8;
k += 4;
if (k >= ue->frame_parms.ofdm_symbol_size) {
k -= ue->frame_parms.ofdm_symbol_size;
rxF = (int16_t *)&rxdataF[aarx][(symbol_offset+k+1)];
}
ch[0] = (int16_t)(((int32_t)pil[0]*rxF[0] - (int32_t)pil[1]*rxF[1])>>15);
ch[1] = (int16_t)(((int32_t)pil[0]*rxF[1] + (int32_t)pil[1]*rxF[0])>>15);
#ifdef DEBUG_PDCCH ch = c16mulShift(*rxF, *pil, 15);
printf("pilot 2 : rxF - > (%d,%d) ch -> (%d,%d), pil -> (%d,%d) \n",rxF[0],rxF[1],ch[0],ch[1],pil[0],pil[1]); DEBUG_PDCCH_IQ(1);
#endif multaddRealVectorComplexScalar(fm, ch, dl_ch, 16);
pil++;
rxF = incrementK(base, &k, symbolSz);
multadd_real_vector_complex_scalar(fr, ch = c16mulShift(*rxF, *pil, 15);
ch, DEBUG_PDCCH_IQ(2);
dl_ch, multaddRealVectorComplexScalar(fr, ch, dl_ch, 16);
16);
#ifdef DEBUG_PDCCH #ifdef DEBUG_PDCCH
for (int m =0; m<12; m++) for (int m =0; m<12; m++)
printf("data : dl_ch -> (%d,%d)\n",dl_ch[0+2*m],dl_ch[1+2*m]); printf("data : dl_ch -> (%d,%d)\n",dl_ch[0+2*m],dl_ch[1+2*m]);
#endif #endif
dl_ch += 24; dl_ch += 12;
pil += 2;
rxF += 8;
k += 4;
for (pilot_cnt=3; pilot_cnt<(3*nb_rb_coreset); pilot_cnt += 3) {
if (k >= ue->frame_parms.ofdm_symbol_size) {
k -= ue->frame_parms.ofdm_symbol_size;
rxF = (int16_t *)&rxdataF[aarx][(symbol_offset+k+1)];
}
ch[0] = (int16_t)(((int32_t)pil[0]*rxF[0] - (int32_t)pil[1]*rxF[1])>>15);
ch[1] = (int16_t)(((int32_t)pil[0]*rxF[1] + (int32_t)pil[1]*rxF[0])>>15);
#ifdef DEBUG_PDCCH
printf("pilot %u : rxF - > (%d,%d) ch -> (%d,%d), pil -> (%d,%d) \n",pilot_cnt,rxF[0],rxF[1],ch[0],ch[1],pil[0],pil[1]);
#endif
multadd_real_vector_complex_scalar(fl,
ch,
dl_ch,
16);
//for (int i= 0; i<8; i++) pil++;
// printf("pilot_cnt %d dl_ch %d %d\n", pilot_cnt, dl_ch+i, *(dl_ch+i)); rxF = incrementK(base, &k, symbolSz);
pil += 2;
rxF += 8;
k += 4;
if (k >= ue->frame_parms.ofdm_symbol_size) {
k -= ue->frame_parms.ofdm_symbol_size;
rxF = (int16_t *)&rxdataF[aarx][(symbol_offset+k+1)];
}
ch[0] = (int16_t)(((int32_t)pil[0]*rxF[0] - (int32_t)pil[1]*rxF[1])>>15);
ch[1] = (int16_t)(((int32_t)pil[0]*rxF[1] + (int32_t)pil[1]*rxF[0])>>15);
#ifdef DEBUG_PDCCH
printf("pilot %u : rxF - > (%d,%d) ch -> (%d,%d), pil -> (%d,%d) \n",pilot_cnt+1,rxF[0],rxF[1],ch[0],ch[1],pil[0],pil[1]);
#endif
multadd_real_vector_complex_scalar(fm,
ch,
dl_ch,
16);
pil += 2;
rxF += 8;
k += 4;
if (k >= ue->frame_parms.ofdm_symbol_size) {
k -= ue->frame_parms.ofdm_symbol_size;
rxF = (int16_t *)&rxdataF[aarx][(symbol_offset+k+1)];
}
ch[0] = (int16_t)(((int32_t)pil[0]*rxF[0] - (int32_t)pil[1]*rxF[1])>>15); for (uint pilot_cnt = 3; pilot_cnt < (3 * nb_rb_coreset); pilot_cnt += 3) {
ch[1] = (int16_t)(((int32_t)pil[0]*rxF[1] + (int32_t)pil[1]*rxF[0])>>15); ch = c16mulShift(*rxF, *pil, 15);
DEBUG_PDCCH_IQ(pilot_cnt);
multaddRealVectorComplexScalar(fl, ch, dl_ch, 16);
pil++;
rxF = incrementK(base, &k, symbolSz);
#ifdef DEBUG_PDCCH ch = c16mulShift(*rxF, *pil, 15);
printf("pilot %u : rxF - > (%d,%d) ch -> (%d,%d), pil -> (%d,%d) \n",pilot_cnt+2,rxF[0],rxF[1],ch[0],ch[1],pil[0],pil[1]); DEBUG_PDCCH_IQ(pilot_cnt + 1);
#endif multaddRealVectorComplexScalar(fm, ch, dl_ch, 16);
pil++;
rxF = incrementK(base, &k, symbolSz);
multadd_real_vector_complex_scalar(fr, ch = c16mulShift(*rxF, *pil, 15);
ch, DEBUG_PDCCH_IQ(pilot_cnt + 2);
dl_ch, multaddRealVectorComplexScalar(fr, ch, dl_ch, 16);
16);
#ifdef DEBUG_PDCCH #ifdef DEBUG_PDCCH
for (int m =0; m<12; m++) for (int m = 0; m < 12; m++)
printf("data : dl_ch -> (%d,%d)\n",dl_ch[0+2*m],dl_ch[1+2*m]); printf("data : dl_ch -> (%d,%d)\n", dl_ch[0 + 2 * m], dl_ch[1 + 2 * m]);
#endif #endif
dl_ch += 24; dl_ch += 12;
pil++;
pil += 2; rxF = incrementK(base, &k, symbolSz);
rxF += 8;
k += 4;
} }
#else //ELSE CH_INTERP #else // ELSE CH_INTERP
int ch_sum[2] = {0, 0}; c32_t ch_sum = {0};
for (uint pilot_cnt = 0; pilot_cnt < 3 * nb_rb_coreset; pilot_cnt++) {
for (pilot_cnt = 0; pilot_cnt < 3*nb_rb_coreset; pilot_cnt++) { DEBUG_PDCCH_IQ(pilot_cnt);
if (k >= ue->frame_parms.ofdm_symbol_size) { ch_sum = c32x16maddShift(*rxF, *pil, ch_sum, 15);
k -= ue->frame_parms.ofdm_symbol_size; pil++;
rxF = (int16_t *)&rxdataF[aarx][(symbol_offset+k+1)]; rxF = incrementK(base, &k, symbolSz);
}
#ifdef DEBUG_PDCCH
printf("pilot[%u] = (%d, %d)\trxF[%d] = (%d, %d)\n", pilot_cnt, pil[0], pil[1], k+1, rxF[0], rxF[1]);
#endif
ch_sum[0] += (int16_t)(((int32_t)pil[0]*rxF[0] - (int32_t)pil[1]*rxF[1])>>15);
ch_sum[1] += (int16_t)(((int32_t)pil[0]*rxF[1] + (int32_t)pil[1]*rxF[0])>>15);
pil += 2;
rxF += 8;
k += 4;
if (pilot_cnt % 3 == 2) { if (pilot_cnt % 3 == 2) {
ch[0] = ch_sum[0] / 3; c16_t ch = {ch_sum.r / 3, ch_sum.i / 3};
ch[1] = ch_sum[1] / 3; multaddRealVectorComplexScalar((c16_t *)filt16a_1, ch, dl_ch, 16);
multadd_real_vector_complex_scalar(filt16a_1, ch, dl_ch, 16);
#ifdef DEBUG_PDCCH #ifdef DEBUG_PDCCH
for (int m =0; m<12; m++) for (int m =0; m<12; m++)
printf("data : dl_ch -> (%d,%d)\n",dl_ch[0+2*m],dl_ch[1+2*m]); printf("data : dl_ch -> (%d,%d)\n",dl_ch[0+2*m],dl_ch[1+2*m]);
#endif #endif
dl_ch += 24; dl_ch += 12;
ch_sum[0] = 0; ch_sum = (c32_t){0};
ch_sum[1] = 0;
} }
} }
#endif //END CH_INTERP #endif // END CH_INTERP
//}
} }
} }
...@@ -1419,16 +1267,16 @@ int nr_pdsch_channel_estimation(PHY_VARS_NR_UE *ue, ...@@ -1419,16 +1267,16 @@ int nr_pdsch_channel_estimation(PHY_VARS_NR_UE *ue,
unsigned short bwp_start_subcarrier, unsigned short bwp_start_subcarrier,
unsigned short nb_rb_pdsch, unsigned short nb_rb_pdsch,
uint32_t pdsch_est_size, uint32_t pdsch_est_size,
int32_t dl_ch_estimates[][pdsch_est_size], c16_t dl_ch_estimates[][pdsch_est_size],
int rxdataFsize, int rxdataFsize,
c16_t rxdataF[][rxdataFsize], c16_t rxdataF[][rxdataFsize],
uint32_t *nvar) uint32_t *nvar)
{ {
// int gNB_id = proc->gNB_id;
int slot = proc->nr_slot_rx; int slot = proc->nr_slot_rx;
NR_DL_FRAME_PARMS *fp = &ue->frame_parms; NR_DL_FRAME_PARMS * fp=&ue->frame_parms;
const int ch_offset = fp->ofdm_symbol_size * symbol; const int symbolSz = fp->ofdm_symbol_size;
const int symbol_offset = fp->ofdm_symbol_size * symbol; const int ch_offset = symbolSz * symbol;
const int symbol_offset = symbolSz * symbol;
#ifdef DEBUG_PDSCH #ifdef DEBUG_PDSCH
printf( printf(
...@@ -1437,7 +1285,7 @@ int nr_pdsch_channel_estimation(PHY_VARS_NR_UE *ue, ...@@ -1437,7 +1285,7 @@ int nr_pdsch_channel_estimation(PHY_VARS_NR_UE *ue,
gNB_id, gNB_id,
ch_offset, ch_offset,
symbol_offset, symbol_offset,
fp->ofdm_symbol_size, symbolSz,
fp->Ncp, fp->Ncp,
slot, slot,
bwp_start_subcarrier, bwp_start_subcarrier,
...@@ -1468,11 +1316,11 @@ int nr_pdsch_channel_estimation(PHY_VARS_NR_UE *ue, ...@@ -1468,11 +1316,11 @@ int nr_pdsch_channel_estimation(PHY_VARS_NR_UE *ue,
#endif #endif
c16_t *rxF = &rxdataF[aarx][symbol_offset + delta]; c16_t *rxF = &rxdataF[aarx][symbol_offset + delta];
c16_t *dl_ch = (c16_t *)&dl_ch_estimates[nl * fp->nb_antennas_rx + aarx][ch_offset]; c16_t *dl_ch = &dl_ch_estimates[nl * fp->nb_antennas_rx + aarx][ch_offset];
memset(dl_ch, 0, sizeof(*dl_ch) * fp->ofdm_symbol_size); memset(dl_ch, 0, sizeof(*dl_ch) * symbolSz);
if (config_type == NFAPI_NR_DMRS_TYPE1 && ue->chest_freq == 0) { if (config_type == NFAPI_NR_DMRS_TYPE1 && ue->chest_freq == 0) {
NFAPI_NR_DMRS_TYPE1_linear_interp(&ue->frame_parms, NFAPI_NR_DMRS_TYPE1_linear_interp(fp,
rxF, rxF,
&pilot[6 * rb_offset], &pilot[6 * rb_offset],
dl_ch, dl_ch,
...@@ -1502,7 +1350,7 @@ int nr_pdsch_channel_estimation(PHY_VARS_NR_UE *ue, ...@@ -1502,7 +1350,7 @@ int nr_pdsch_channel_estimation(PHY_VARS_NR_UE *ue,
} }
#ifdef DEBUG_PDSCH #ifdef DEBUG_PDSCH
dl_ch = (c16_t *)&dl_ch_estimates[nl * fp->nb_antennas_rx + aarx][ch_offset]; dl_ch = &dl_ch_estimates[nl * fp->nb_antennas_rx + aarx][ch_offset];
for (uint16_t idxP = 0; idxP < ceil((float)nb_rb_pdsch * 12 / 8); idxP++) { for (uint16_t idxP = 0; idxP < ceil((float)nb_rb_pdsch * 12 / 8); idxP++) {
for (uint8_t idxI = 0; idxI < 8; idxI++) { for (uint8_t idxI = 0; idxI < 8; idxI++) {
printf("%4d\t%4d\t", dl_ch[idxP * 8 + idxI].r, dl_ch[idxP * 8 + idxI].i); printf("%4d\t%4d\t", dl_ch[idxP * 8 + idxI].r, dl_ch[idxP * 8 + idxI].i);
...@@ -1545,7 +1393,7 @@ void nr_pdsch_ptrs_processing(PHY_VARS_NR_UE *ue, ...@@ -1545,7 +1393,7 @@ void nr_pdsch_ptrs_processing(PHY_VARS_NR_UE *ue,
c16_t ptrs_phase_per_slot[][14], c16_t ptrs_phase_per_slot[][14],
int32_t ptrs_re_per_slot[][14], int32_t ptrs_re_per_slot[][14],
uint32_t rx_size_symbol, uint32_t rx_size_symbol,
int32_t rxdataF_comp[][nbRx][rx_size_symbol * NR_SYMBOLS_PER_SLOT], c16_t rxdataF_comp[][nbRx][rx_size_symbol * NR_SYMBOLS_PER_SLOT],
NR_DL_FRAME_PARMS *frame_parms, NR_DL_FRAME_PARMS *frame_parms,
NR_DL_UE_HARQ_t *dlsch0_harq, NR_DL_UE_HARQ_t *dlsch0_harq,
NR_DL_UE_HARQ_t *dlsch1_harq, NR_DL_UE_HARQ_t *dlsch1_harq,
...@@ -1674,9 +1522,9 @@ void nr_pdsch_ptrs_processing(PHY_VARS_NR_UE *ue, ...@@ -1674,9 +1522,9 @@ void nr_pdsch_ptrs_processing(PHY_VARS_NR_UE *ue,
#ifdef DEBUG_DL_PTRS #ifdef DEBUG_DL_PTRS
printf("[PHY][DL][PTRS]: Rotate Symbol %2d with %d + j* %d\n", i, phase_per_symbol[i].r,phase_per_symbol[i].i); printf("[PHY][DL][PTRS]: Rotate Symbol %2d with %d + j* %d\n", i, phase_per_symbol[i].r,phase_per_symbol[i].i);
#endif #endif
rotate_cpx_vector((c16_t *)&rxdataF_comp[0][aarx][(i * (*nb_rb) * NR_NB_SC_PER_RB)], rotate_cpx_vector(&rxdataF_comp[0][aarx][(i * (*nb_rb) * NR_NB_SC_PER_RB)],
&phase_per_symbol[i], &phase_per_symbol[i],
(c16_t *)&rxdataF_comp[0][aarx][(i * (*nb_rb) * NR_NB_SC_PER_RB)], &rxdataF_comp[0][aarx][(i * (*nb_rb) * NR_NB_SC_PER_RB)],
((*nb_rb) * NR_NB_SC_PER_RB), ((*nb_rb) * NR_NB_SC_PER_RB),
15); 15);
}// if not DMRS Symbol }// if not DMRS Symbol
......
...@@ -41,9 +41,6 @@ int nr_prs_channel_estimation(uint8_t gNB_id, ...@@ -41,9 +41,6 @@ int nr_prs_channel_estimation(uint8_t gNB_id,
NR_DL_FRAME_PARMS *frame_params, NR_DL_FRAME_PARMS *frame_params,
c16_t rxdataF[][ue->frame_parms.samples_per_slot_wCP]); c16_t rxdataF[][ue->frame_parms.samples_per_slot_wCP]);
/* Generic function to find the peak of channel estimation buffer */
void peak_estimator(int32_t *buffer, int32_t buf_len, int32_t *peak_idx, int32_t *peak_val, int32_t mean_val);
/*! /*!
\brief This function performs channel estimation including frequency and temporal interpolation \brief This function performs channel estimation including frequency and temporal interpolation
*/ */
...@@ -94,7 +91,7 @@ int nr_pdsch_channel_estimation(PHY_VARS_NR_UE *ue, ...@@ -94,7 +91,7 @@ int nr_pdsch_channel_estimation(PHY_VARS_NR_UE *ue,
unsigned short bwp_start_subcarrier, unsigned short bwp_start_subcarrier,
unsigned short nb_rb_pdsch, unsigned short nb_rb_pdsch,
uint32_t pdsch_est_size, uint32_t pdsch_est_size,
int32_t dl_ch_estimates[][pdsch_est_size], c16_t dl_ch_estimates[][pdsch_est_size],
int rxdataFsize, int rxdataFsize,
c16_t rxdataF[][rxdataFsize], c16_t rxdataF[][rxdataFsize],
uint32_t *nvar); uint32_t *nvar);
...@@ -112,7 +109,7 @@ void nr_ue_measurements(PHY_VARS_NR_UE *ue, ...@@ -112,7 +109,7 @@ void nr_ue_measurements(PHY_VARS_NR_UE *ue,
const UE_nr_rxtx_proc_t *proc, const UE_nr_rxtx_proc_t *proc,
NR_UE_DLSCH_t *dlsch, NR_UE_DLSCH_t *dlsch,
uint32_t pdsch_est_size, uint32_t pdsch_est_size,
int32_t dl_ch_estimates[][pdsch_est_size]); c16_t dl_ch_estimates[][pdsch_est_size]);
void nr_ue_ssb_rsrp_measurements(PHY_VARS_NR_UE *ue, void nr_ue_ssb_rsrp_measurements(PHY_VARS_NR_UE *ue,
uint8_t gNB_index, uint8_t gNB_index,
...@@ -132,7 +129,7 @@ void nr_pdsch_ptrs_processing(PHY_VARS_NR_UE *ue, ...@@ -132,7 +129,7 @@ void nr_pdsch_ptrs_processing(PHY_VARS_NR_UE *ue,
c16_t ptrs_phase_per_slot[][14], c16_t ptrs_phase_per_slot[][14],
int32_t ptrs_re_per_slot[][14], int32_t ptrs_re_per_slot[][14],
uint32_t rx_size_symbol, uint32_t rx_size_symbol,
int32_t rxdataF_comp[][nbRx][rx_size_symbol * NR_SYMBOLS_PER_SLOT], c16_t rxdataF_comp[][nbRx][rx_size_symbol * NR_SYMBOLS_PER_SLOT],
NR_DL_FRAME_PARMS *frame_parms, NR_DL_FRAME_PARMS *frame_parms,
NR_DL_UE_HARQ_t *dlsch0_harq, NR_DL_UE_HARQ_t *dlsch0_harq,
NR_DL_UE_HARQ_t *dlsch1_harq, NR_DL_UE_HARQ_t *dlsch1_harq,
......
...@@ -78,7 +78,7 @@ void nr_ue_measurements(PHY_VARS_NR_UE *ue, ...@@ -78,7 +78,7 @@ void nr_ue_measurements(PHY_VARS_NR_UE *ue,
const UE_nr_rxtx_proc_t *proc, const UE_nr_rxtx_proc_t *proc,
NR_UE_DLSCH_t *dlsch, NR_UE_DLSCH_t *dlsch,
uint32_t pdsch_est_size, uint32_t pdsch_est_size,
int32_t dl_ch_estimates[][pdsch_est_size]) c16_t dl_ch_estimates[][pdsch_est_size])
{ {
int slot = proc->nr_slot_rx; int slot = proc->nr_slot_rx;
int aarx, aatx, gNB_id = 0; int aarx, aatx, gNB_id = 0;
...@@ -113,7 +113,7 @@ void nr_ue_measurements(PHY_VARS_NR_UE *ue, ...@@ -113,7 +113,7 @@ void nr_ue_measurements(PHY_VARS_NR_UE *ue,
ue->measurements.rx_power[gNB_id][aarx] = 0; ue->measurements.rx_power[gNB_id][aarx] = 0;
for (aatx = 0; aatx < frame_parms->nb_antenna_ports_gNB; aatx++){ for (aatx = 0; aatx < frame_parms->nb_antenna_ports_gNB; aatx++){
const int z=signal_energy_nodc(&dl_ch_estimates[gNB_id][ch_offset], N_RB_DL * NR_NB_SC_PER_RB); const int z = signal_energy_nodc((int32_t *)&dl_ch_estimates[gNB_id][ch_offset], N_RB_DL * NR_NB_SC_PER_RB);
rx_spatial_power[gNB_id][aatx][aarx] = z; rx_spatial_power[gNB_id][aatx][aarx] = z;
if (rx_spatial_power[gNB_id][aatx][aarx] < 0) if (rx_spatial_power[gNB_id][aatx][aarx] < 0)
......
...@@ -46,13 +46,13 @@ ...@@ -46,13 +46,13 @@
//#define NR_CSIRS_DEBUG //#define NR_CSIRS_DEBUG
//#define NR_CSIIM_DEBUG //#define NR_CSIIM_DEBUG
void nr_det_A_MF_2x2(int32_t *a_mf_00, static void nr_det_A_MF_2x2(c16_t *a_mf_00,
int32_t *a_mf_01, c16_t *a_mf_01,
int32_t *a_mf_10, c16_t *a_mf_10,
int32_t *a_mf_11, c16_t *a_mf_11,
int32_t *det_fin, int32_t *det_fin,
const unsigned short nb_rb) { const unsigned short nb_rb)
{
int16_t nr_conjug2[8]__attribute__((aligned(16))) = {1,-1,1,-1,1,-1,1,-1} ; int16_t nr_conjug2[8]__attribute__((aligned(16))) = {1,-1,1,-1,1,-1,1,-1} ;
simde__m128i ad_re_128, bc_re_128, det_re_128; simde__m128i ad_re_128, bc_re_128, det_re_128;
...@@ -86,13 +86,10 @@ void nr_det_A_MF_2x2(int32_t *a_mf_00, ...@@ -86,13 +86,10 @@ void nr_det_A_MF_2x2(int32_t *a_mf_00,
a_mf_10_128+=1; a_mf_10_128+=1;
a_mf_11_128+=1; a_mf_11_128+=1;
} }
simde_mm_empty();
simde_m_empty();
} }
void nr_squared_matrix_element(int32_t *a, static void nr_squared_matrix_element(c16_t *a, c16_t *a_sq, const unsigned short nb_rb)
int32_t *a_sq, {
const unsigned short nb_rb) {
simde__m128i *a_128 = (simde__m128i *)a; simde__m128i *a_128 = (simde__m128i *)a;
simde__m128i *a_sq_128 = (simde__m128i *)a_sq; simde__m128i *a_sq_128 = (simde__m128i *)a_sq;
for (int rb=0; rb<3*nb_rb; rb++) { for (int rb=0; rb<3*nb_rb; rb++) {
...@@ -100,16 +97,15 @@ void nr_squared_matrix_element(int32_t *a, ...@@ -100,16 +97,15 @@ void nr_squared_matrix_element(int32_t *a,
a_sq_128+=1; a_sq_128+=1;
a_128+=1; a_128+=1;
} }
simde_mm_empty();
simde_m_empty();
} }
void nr_numer_2x2(int32_t *a_00_sq, static void nr_numer_2x2(c16_t *a_00_sq,
int32_t *a_01_sq, c16_t *a_01_sq,
int32_t *a_10_sq, c16_t *a_10_sq,
int32_t *a_11_sq, c16_t *a_11_sq,
int32_t *num_fin, int32_t *num_fin,
const unsigned short nb_rb) { const unsigned short nb_rb)
{
simde__m128i *a_00_sq_128 = (simde__m128i *)a_00_sq; simde__m128i *a_00_sq_128 = (simde__m128i *)a_00_sq;
simde__m128i *a_01_sq_128 = (simde__m128i *)a_01_sq; simde__m128i *a_01_sq_128 = (simde__m128i *)a_01_sq;
simde__m128i *a_10_sq_128 = (simde__m128i *)a_10_sq; simde__m128i *a_10_sq_128 = (simde__m128i *)a_10_sq;
...@@ -125,8 +121,6 @@ void nr_numer_2x2(int32_t *a_00_sq, ...@@ -125,8 +121,6 @@ void nr_numer_2x2(int32_t *a_00_sq,
a_10_sq_128+=1; a_10_sq_128+=1;
a_11_sq_128+=1; a_11_sq_128+=1;
} }
simde_mm_empty();
simde_m_empty();
} }
bool is_csi_rs_in_symbol(const fapi_nr_dl_config_csirs_pdu_rel15_t csirs_config_pdu, const int symbol) { bool is_csi_rs_in_symbol(const fapi_nr_dl_config_csirs_pdu_rel15_t csirs_config_pdu, const int symbol) {
...@@ -188,11 +182,11 @@ int nr_get_csi_rs_signal(const PHY_VARS_NR_UE *ue, ...@@ -188,11 +182,11 @@ int nr_get_csi_rs_signal(const PHY_VARS_NR_UE *ue,
const uint8_t *j_cdm, const uint8_t *j_cdm,
const uint8_t *k_overline, const uint8_t *k_overline,
const uint8_t *l_overline, const uint8_t *l_overline,
int32_t csi_rs_received_signal[][ue->frame_parms.samples_per_slot_wCP], c16_t csi_rs_received_signal[][ue->frame_parms.samples_per_slot_wCP],
uint32_t *rsrp, uint32_t *rsrp,
int *rsrp_dBm, int *rsrp_dBm,
c16_t rxdataF[][ue->frame_parms.samples_per_slot_wCP]) { c16_t rxdataF[][ue->frame_parms.samples_per_slot_wCP])
{
const NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms; const NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms;
uint16_t meas_count = 0; uint16_t meas_count = 0;
uint32_t rsrp_sum = 0; uint32_t rsrp_sum = 0;
...@@ -219,19 +213,17 @@ int nr_get_csi_rs_signal(const PHY_VARS_NR_UE *ue, ...@@ -219,19 +213,17 @@ int nr_get_csi_rs_signal(const PHY_VARS_NR_UE *ue,
uint16_t symb = lp + l_overline[cdm_id]; uint16_t symb = lp + l_overline[cdm_id];
uint64_t symbol_offset = symb*frame_parms->ofdm_symbol_size; uint64_t symbol_offset = symb*frame_parms->ofdm_symbol_size;
c16_t *rx_signal = &rxdataF[ant_rx][symbol_offset]; c16_t *rx_signal = &rxdataF[ant_rx][symbol_offset];
c16_t *rx_csi_rs_signal = (c16_t*)&csi_rs_received_signal[ant_rx][symbol_offset]; c16_t *rx_csi_rs_signal = &csi_rs_received_signal[ant_rx][symbol_offset];
rx_csi_rs_signal[k].r = rx_signal[k].r; rx_csi_rs_signal[k] = rx_signal[k];
rx_csi_rs_signal[k].i = rx_signal[k].i;
rsrp_sum += (((int32_t)(rx_csi_rs_signal[k].r)*rx_csi_rs_signal[k].r) + rsrp_sum += squaredMod(rx_csi_rs_signal[k]);
((int32_t)(rx_csi_rs_signal[k].i)*rx_csi_rs_signal[k].i));
meas_count++; meas_count++;
#ifdef NR_CSIRS_DEBUG #ifdef NR_CSIRS_DEBUG
int dataF_offset = proc->nr_slot_rx*ue->frame_parms.samples_per_slot_wCP; int dataF_offset = proc->nr_slot_rx*ue->frame_parms.samples_per_slot_wCP;
uint16_t port_tx = s+j_cdm[cdm_id]*CDM_group_size; uint16_t port_tx = s+j_cdm[cdm_id]*CDM_group_size;
c16_t *tx_csi_rs_signal = (c16_t*)&nr_csi_info->csi_rs_generated_signal[port_tx][symbol_offset+dataF_offset]; c16_t *tx_csi_rs_signal = &nr_csi_info->csi_rs_generated_signal[port_tx][symbol_offset + dataF_offset];
LOG_I(NR_PHY, "l,k (%2d,%4d) |\tport_tx %d (%4d,%4d)\tant_rx %d (%4d,%4d)\n", LOG_I(NR_PHY, "l,k (%2d,%4d) |\tport_tx %d (%4d,%4d)\tant_rx %d (%4d,%4d)\n",
symb, symb,
k, k,
...@@ -277,27 +269,28 @@ uint32_t calc_power_csirs(const uint16_t *x, const fapi_nr_dl_config_csirs_pdu_r ...@@ -277,27 +269,28 @@ uint32_t calc_power_csirs(const uint16_t *x, const fapi_nr_dl_config_csirs_pdu_r
return sum_x2 / size - (sum_x / size) * (sum_x / size); return sum_x2 / size - (sum_x / size) * (sum_x / size);
} }
int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue, static int nr_csi_rs_channel_estimation(
const UE_nr_rxtx_proc_t *proc, const PHY_VARS_NR_UE *ue,
const fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu, const UE_nr_rxtx_proc_t *proc,
const nr_csi_info_t *nr_csi_info, const fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu,
const int32_t **csi_rs_generated_signal, const nr_csi_info_t *nr_csi_info,
const int32_t csi_rs_received_signal[][ue->frame_parms.samples_per_slot_wCP], c16_t **csi_rs_generated_signal,
const uint8_t N_cdm_groups, const c16_t csi_rs_received_signal[][ue->frame_parms.samples_per_slot_wCP],
const uint8_t CDM_group_size, const uint8_t N_cdm_groups,
const uint8_t k_prime, const uint8_t CDM_group_size,
const uint8_t l_prime, const uint8_t k_prime,
const uint8_t N_ports, const uint8_t l_prime,
const uint8_t *j_cdm, const uint8_t N_ports,
const uint8_t *k_overline, const uint8_t *j_cdm,
const uint8_t *l_overline, const uint8_t *k_overline,
uint8_t mem_offset, const uint8_t *l_overline,
int32_t csi_rs_ls_estimated_channel[][N_ports][ue->frame_parms.ofdm_symbol_size], uint8_t mem_offset,
int32_t csi_rs_estimated_channel_freq[][N_ports][ue->frame_parms.ofdm_symbol_size + FILTER_MARGIN], c16_t csi_rs_ls_estimated_channel[][N_ports][ue->frame_parms.ofdm_symbol_size],
int16_t *log2_re, c16_t csi_rs_estimated_channel_freq[][N_ports][ue->frame_parms.ofdm_symbol_size + FILTER_MARGIN],
int16_t *log2_maxh, int16_t *log2_re,
uint32_t *noise_power) { int16_t *log2_maxh,
uint32_t *noise_power)
{
const NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms; const NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms;
const int dataF_offset = proc->nr_slot_rx*ue->frame_parms.samples_per_slot_wCP; const int dataF_offset = proc->nr_slot_rx*ue->frame_parms.samples_per_slot_wCP;
*noise_power = 0; *noise_power = 0;
...@@ -305,15 +298,12 @@ int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue, ...@@ -305,15 +298,12 @@ int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue,
int count = 0; int count = 0;
for (int ant_rx = 0; ant_rx < frame_parms->nb_antennas_rx; ant_rx++) { for (int ant_rx = 0; ant_rx < frame_parms->nb_antennas_rx; ant_rx++) {
/// LS channel estimation /// LS channel estimation
for (uint port_tx = 0; port_tx < N_ports; port_tx++) {
for(uint16_t port_tx = 0; port_tx<N_ports; port_tx++) { memset(csi_rs_ls_estimated_channel[ant_rx][port_tx], 0, frame_parms->ofdm_symbol_size * sizeof(c16_t));
memset(csi_rs_ls_estimated_channel[ant_rx][port_tx], 0, frame_parms->ofdm_symbol_size*sizeof(int32_t));
} }
for (int rb = csirs_config_pdu->start_rb; rb < (csirs_config_pdu->start_rb+csirs_config_pdu->nr_of_rbs); rb++) { for (int rb = csirs_config_pdu->start_rb; rb < (csirs_config_pdu->start_rb + csirs_config_pdu->nr_of_rbs); rb++) {
// for freq density 0.5 checks if even or odd RB // for freq density 0.5 checks if even or odd RB
if(csirs_config_pdu->freq_density <= 1 && csirs_config_pdu->freq_density != (rb % 2)) { if(csirs_config_pdu->freq_density <= 1 && csirs_config_pdu->freq_density != (rb % 2)) {
continue; continue;
...@@ -334,17 +324,10 @@ int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue, ...@@ -334,17 +324,10 @@ int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue,
for (int lp = 0; lp <= l_prime; lp++) { for (int lp = 0; lp <= l_prime; lp++) {
uint16_t symb = lp + l_overline[cdm_id]; uint16_t symb = lp + l_overline[cdm_id];
uint64_t symbol_offset = symb*frame_parms->ofdm_symbol_size; uint64_t symbol_offset = symb*frame_parms->ofdm_symbol_size;
c16_t *tx_csi_rs_signal = (c16_t*)&csi_rs_generated_signal[port_tx][symbol_offset+dataF_offset]; const c16_t *tx_csi_rs_signal = &csi_rs_generated_signal[port_tx][symbol_offset + dataF_offset];
c16_t *rx_csi_rs_signal = (c16_t*)&csi_rs_received_signal[ant_rx][symbol_offset]; const c16_t *rx_csi_rs_signal = &csi_rs_received_signal[ant_rx][symbol_offset];
c16_t *csi_rs_ls_estimated_channel16 = (c16_t*)&csi_rs_ls_estimated_channel[ant_rx][port_tx][0]; csi_rs_ls_estimated_channel[ant_rx][port_tx][kinit] =
c16MulConjShift(tx_csi_rs_signal[k], rx_csi_rs_signal[k], nr_csi_info->csi_rs_generated_signal_bits);
int16_t csi_rs_ls_estimated_channel_re = (int16_t)(((int32_t)tx_csi_rs_signal[k].r*rx_csi_rs_signal[k].r + (int32_t)tx_csi_rs_signal[k].i*rx_csi_rs_signal[k].i)>>nr_csi_info->csi_rs_generated_signal_bits);
int16_t csi_rs_ls_estimated_channel_im = (int16_t)(((int32_t)tx_csi_rs_signal[k].r*rx_csi_rs_signal[k].i - (int32_t)tx_csi_rs_signal[k].i*rx_csi_rs_signal[k].r)>>nr_csi_info->csi_rs_generated_signal_bits);
// This is not just the LS estimation for each (k,l), but also the sum of the different contributions
// for the sake of optimizing the memory used.
csi_rs_ls_estimated_channel16[kinit].r += csi_rs_ls_estimated_channel_re;
csi_rs_ls_estimated_channel16[kinit].i += csi_rs_ls_estimated_channel_im;
} }
} }
} }
...@@ -360,9 +343,9 @@ int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue, ...@@ -360,9 +343,9 @@ int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue,
LOG_I(NR_PHY, "l,k (%2d,%4d) | ", symb, k); LOG_I(NR_PHY, "l,k (%2d,%4d) | ", symb, k);
for(uint16_t port_tx = 0; port_tx<N_ports; port_tx++) { for(uint16_t port_tx = 0; port_tx<N_ports; port_tx++) {
uint64_t symbol_offset = symb*frame_parms->ofdm_symbol_size; uint64_t symbol_offset = symb*frame_parms->ofdm_symbol_size;
c16_t *tx_csi_rs_signal = (c16_t*)&csi_rs_generated_signal[port_tx][symbol_offset+dataF_offset]; c16_t *tx_csi_rs_signal = &csi_rs_generated_signal[port_tx][symbol_offset + dataF_offset];
c16_t *rx_csi_rs_signal = (c16_t*)&csi_rs_received_signal[ant_rx][symbol_offset]; c16_t *rx_csi_rs_signal = &csi_rs_received_signal[ant_rx][symbol_offset];
c16_t *csi_rs_ls_estimated_channel16 = (c16_t*)&csi_rs_ls_estimated_channel[ant_rx][port_tx][0]; c16_t *csi_rs_ls_estimated_channel16 = csi_rs_ls_estimated_channel[ant_rx][port_tx];
printf("port_tx %d --> ant_rx %d, tx (%4d,%4d), rx (%4d,%4d), ls (%4d,%4d) | ", printf("port_tx %d --> ant_rx %d, tx (%4d,%4d), rx (%4d,%4d), ls (%4d,%4d) | ",
port_tx+3000, ant_rx, port_tx+3000, ant_rx,
tx_csi_rs_signal[k].r, tx_csi_rs_signal[k].i, tx_csi_rs_signal[k].r, tx_csi_rs_signal[k].i,
...@@ -389,18 +372,20 @@ int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue, ...@@ -389,18 +372,20 @@ int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue,
count++; count++;
uint16_t k = (frame_parms->first_carrier_offset + rb*NR_NB_SC_PER_RB) % frame_parms->ofdm_symbol_size; const uint16_t k = (frame_parms->first_carrier_offset + rb * NR_NB_SC_PER_RB) % frame_parms->ofdm_symbol_size;
uint16_t k_offset = k + mem_offset; const uint16_t k_offset = k + mem_offset;
for(uint16_t port_tx = 0; port_tx<N_ports; port_tx++) { for (uint port_tx = 0; port_tx < N_ports; port_tx++) {
int16_t *csi_rs_ls_estimated_channel16 = (int16_t*)&csi_rs_ls_estimated_channel[ant_rx][port_tx][k]; c16_t val = csi_rs_ls_estimated_channel[ant_rx][port_tx][k];
int16_t *csi_rs_estimated_channel16 = (int16_t *)&csi_rs_estimated_channel_freq[ant_rx][port_tx][k_offset]; c16_t *csi_rs_estimated_channel = &csi_rs_estimated_channel_freq[ant_rx][port_tx][k_offset];
if( (k == 0) || (k == frame_parms->first_carrier_offset) ) { // Start of OFDM symbol case or first occupied subcarrier case if (k == 0 || k == frame_parms->first_carrier_offset) { // Start of OFDM symbol case or first occupied subcarrier case
multadd_real_vector_complex_scalar(filt24_start, csi_rs_ls_estimated_channel16, csi_rs_estimated_channel16, 24); multaddRealVectorComplexScalar(filt24_start, val, csi_rs_estimated_channel, 24);
} else if( ( (k + NR_NB_SC_PER_RB) >= frame_parms->ofdm_symbol_size) || } else if ((k + NR_NB_SC_PER_RB >= frame_parms->ofdm_symbol_size)
(rb == (csirs_config_pdu->start_rb+csirs_config_pdu->nr_of_rbs-1)) ) { // End of OFDM symbol case or Last occupied subcarrier case || (rb
multadd_real_vector_complex_scalar(filt24_end, csi_rs_ls_estimated_channel16, csi_rs_estimated_channel16 - 3*sizeof(uint64_t), 24); == csirs_config_pdu->start_rb + csirs_config_pdu->nr_of_rbs
- 1)) { // End of OFDM symbol case or Last occupied subcarrier case
multaddRealVectorComplexScalar(filt24_end, val, csi_rs_estimated_channel - 3 * sizeof(c16_t), 24);
} else { // Middle case } else { // Middle case
multadd_real_vector_complex_scalar(filt24_middle, csi_rs_ls_estimated_channel16, csi_rs_estimated_channel16 - 3*sizeof(uint64_t), 24); multaddRealVectorComplexScalar(filt24_middle, val, csi_rs_estimated_channel - 3 * sizeof(c16_t), 24);
} }
} }
} }
...@@ -434,8 +419,8 @@ int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue, ...@@ -434,8 +419,8 @@ int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue,
(k + frame_parms->ofdm_symbol_size - frame_parms->first_carrier_offset)/NR_NB_SC_PER_RB; (k + frame_parms->ofdm_symbol_size - frame_parms->first_carrier_offset)/NR_NB_SC_PER_RB;
LOG_I(NR_PHY, "(k = %4d) |\t", k); LOG_I(NR_PHY, "(k = %4d) |\t", k);
for(uint16_t port_tx = 0; port_tx<N_ports; port_tx++) { for(uint16_t port_tx = 0; port_tx<N_ports; port_tx++) {
c16_t *csi_rs_ls_estimated_channel16 = (c16_t*)&csi_rs_ls_estimated_channel[ant_rx][port_tx][0]; c16_t *csi_rs_ls_estimated_channel16 = csi_rs_ls_estimated_channel[ant_rx][port_tx];
c16_t *csi_rs_estimated_channel16 = (c16_t *)&csi_rs_estimated_channel_freq[ant_rx][port_tx][mem_offset]; c16_t *csi_rs_estimated_channel16 = &csi_rs_estimated_channel_freq[ant_rx][port_tx][mem_offset];
printf("Channel port_tx %d --> ant_rx %d : ls (%4d,%4d), int (%4d,%4d), noise (%4d,%4d) | ", printf("Channel port_tx %d --> ant_rx %d : ls (%4d,%4d), int (%4d,%4d), noise (%4d,%4d) | ",
port_tx+3000, ant_rx, port_tx+3000, ant_rx,
csi_rs_ls_estimated_channel16[k].r, csi_rs_ls_estimated_channel16[k].i, csi_rs_ls_estimated_channel16[k].r, csi_rs_ls_estimated_channel16[k].i,
...@@ -446,7 +431,6 @@ int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue, ...@@ -446,7 +431,6 @@ int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue,
printf("\n"); printf("\n");
} }
#endif #endif
} }
*noise_power /= (frame_parms->nb_antennas_rx*N_ports); *noise_power /= (frame_parms->nb_antennas_rx*N_ports);
...@@ -460,15 +444,15 @@ int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue, ...@@ -460,15 +444,15 @@ int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue,
return 0; return 0;
} }
int nr_csi_rs_ri_estimation(const PHY_VARS_NR_UE *ue, static int nr_csi_rs_ri_estimation(const PHY_VARS_NR_UE *ue,
const fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu, const fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu,
const nr_csi_info_t *nr_csi_info, const nr_csi_info_t *nr_csi_info,
const uint8_t N_ports, const uint8_t N_ports,
uint8_t mem_offset, uint8_t mem_offset,
int32_t csi_rs_estimated_channel_freq[][N_ports][ue->frame_parms.ofdm_symbol_size + FILTER_MARGIN], c16_t csi_rs_estimated_channel_freq[][N_ports][ue->frame_parms.ofdm_symbol_size + FILTER_MARGIN],
const int16_t log2_maxh, const int16_t log2_maxh,
uint8_t *rank_indicator) { uint8_t *rank_indicator)
{
const NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms; const NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms;
const int16_t cond_dB_threshold = 5; const int16_t cond_dB_threshold = 5;
int count = 0; int count = 0;
...@@ -486,14 +470,15 @@ int nr_csi_rs_ri_estimation(const PHY_VARS_NR_UE *ue, ...@@ -486,14 +470,15 @@ int nr_csi_rs_ri_estimation(const PHY_VARS_NR_UE *ue,
* | conjch00 conjch10 | x | ch00 ch01 | = | conjch00*ch00+conjch10*ch10 conjch00*ch01+conjch10*ch11 | * | conjch00 conjch10 | x | ch00 ch01 | = | conjch00*ch00+conjch10*ch10 conjch00*ch01+conjch10*ch11 |
* | conjch01 conjch11 | | ch10 ch11 | | conjch01*ch00+conjch11*ch10 conjch01*ch01+conjch11*ch11 | * | conjch01 conjch11 | | ch10 ch11 | | conjch01*ch00+conjch11*ch10 conjch01*ch01+conjch11*ch11 |
*/ */
const int sZ = frame_parms->ofdm_symbol_size + FILTER_MARGIN;
c16_t csi_rs_estimated_conjch_ch[frame_parms->nb_antennas_rx][N_ports][frame_parms->nb_antennas_rx][N_ports][sZ]
__attribute__((aligned(32)));
c16_t csi_rs_estimated_A_MF[N_ports][N_ports][sZ] __attribute__((aligned(32)));
c16_t csi_rs_estimated_A_MF_sq[N_ports][N_ports][sZ] __attribute__((aligned(32)));
int32_t csi_rs_estimated_determ_fin[sZ] __attribute__((aligned(32)));
int32_t csi_rs_estimated_numer_fin[sZ] __attribute__((aligned(32)));
const uint sum_shift = 1; // log2(2x2) = 2, which is a shift of 1 bit
int32_t csi_rs_estimated_conjch_ch[frame_parms->nb_antennas_rx][N_ports][frame_parms->nb_antennas_rx][N_ports][frame_parms->ofdm_symbol_size + FILTER_MARGIN] __attribute__((aligned(32)));
int32_t csi_rs_estimated_A_MF[N_ports][N_ports][frame_parms->ofdm_symbol_size + FILTER_MARGIN] __attribute__((aligned(32)));
int32_t csi_rs_estimated_A_MF_sq[N_ports][N_ports][frame_parms->ofdm_symbol_size + FILTER_MARGIN] __attribute__((aligned(32)));
int32_t csi_rs_estimated_determ_fin[frame_parms->ofdm_symbol_size + FILTER_MARGIN] __attribute__((aligned(32)));
int32_t csi_rs_estimated_numer_fin[frame_parms->ofdm_symbol_size + FILTER_MARGIN] __attribute__((aligned(32)));
const uint8_t sum_shift = 1; // log2(2x2) = 2, which is a shift of 1 bit
for (int rb = csirs_config_pdu->start_rb; rb < (csirs_config_pdu->start_rb+csirs_config_pdu->nr_of_rbs); rb++) { for (int rb = csirs_config_pdu->start_rb; rb < (csirs_config_pdu->start_rb+csirs_config_pdu->nr_of_rbs); rb++) {
if (csirs_config_pdu->freq_density <= 1 && csirs_config_pdu->freq_density != (rb % 2)) { if (csirs_config_pdu->freq_density <= 1 && csirs_config_pdu->freq_density != (rb % 2)) {
...@@ -597,14 +582,14 @@ int nr_csi_rs_pmi_estimation(const PHY_VARS_NR_UE *ue, ...@@ -597,14 +582,14 @@ int nr_csi_rs_pmi_estimation(const PHY_VARS_NR_UE *ue,
const nr_csi_info_t *nr_csi_info, const nr_csi_info_t *nr_csi_info,
const uint8_t N_ports, const uint8_t N_ports,
uint8_t mem_offset, uint8_t mem_offset,
const int32_t csi_rs_estimated_channel_freq[][N_ports][ue->frame_parms.ofdm_symbol_size + FILTER_MARGIN], const c16_t csi_rs_estimated_channel_freq[][N_ports][ue->frame_parms.ofdm_symbol_size + FILTER_MARGIN],
const uint32_t interference_plus_noise_power, const uint32_t interference_plus_noise_power,
const uint8_t rank_indicator, const uint8_t rank_indicator,
const int16_t log2_re, const int16_t log2_re,
uint8_t *i1, uint8_t *i1,
uint8_t *i2, uint8_t *i2,
uint32_t *precoded_sinr_dB) { uint32_t *precoded_sinr_dB)
{
const NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms; const NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms;
// i1 is a three-element vector in the form of [i11 i12 i13], when CodebookType is specified as 'Type1SinglePanel'. // i1 is a three-element vector in the form of [i11 i12 i13], when CodebookType is specified as 'Type1SinglePanel'.
...@@ -621,11 +606,8 @@ int nr_csi_rs_pmi_estimation(const PHY_VARS_NR_UE *ue, ...@@ -621,11 +606,8 @@ int nr_csi_rs_pmi_estimation(const PHY_VARS_NR_UE *ue,
} }
if(rank_indicator == 0 || rank_indicator == 1) { if(rank_indicator == 0 || rank_indicator == 1) {
c32_t sum[4] = {0};
int32_t sum_re[4] = {0}; c32_t sum2[4] = {0};
int32_t sum_im[4] = {0};
int32_t sum2_re[4] = {0};
int32_t sum2_im[4] = {0};
int32_t tested_precoded_sinr[4] = {0}; int32_t tested_precoded_sinr[4] = {0};
for (int rb = csirs_config_pdu->start_rb; rb < (csirs_config_pdu->start_rb+csirs_config_pdu->nr_of_rbs); rb++) { for (int rb = csirs_config_pdu->start_rb; rb < (csirs_config_pdu->start_rb+csirs_config_pdu->nr_of_rbs); rb++) {
...@@ -636,41 +618,45 @@ int nr_csi_rs_pmi_estimation(const PHY_VARS_NR_UE *ue, ...@@ -636,41 +618,45 @@ int nr_csi_rs_pmi_estimation(const PHY_VARS_NR_UE *ue,
uint16_t k = (frame_parms->first_carrier_offset + rb * NR_NB_SC_PER_RB) % frame_parms->ofdm_symbol_size; uint16_t k = (frame_parms->first_carrier_offset + rb * NR_NB_SC_PER_RB) % frame_parms->ofdm_symbol_size;
uint16_t k_offset = k + mem_offset; uint16_t k_offset = k + mem_offset;
for (int ant_rx = 0; ant_rx < frame_parms->nb_antennas_rx; ant_rx++) { for (int ant_rx = 0; ant_rx < frame_parms->nb_antennas_rx; ant_rx++) {
c16_t *csi_rs_estimated_channel_p0 = (c16_t *) &csi_rs_estimated_channel_freq[ant_rx][0][k_offset]; const c16_t csi_rs_estimated_channel_p0 = csi_rs_estimated_channel_freq[ant_rx][0][k_offset];
c16_t *csi_rs_estimated_channel_p1 = (c16_t *) &csi_rs_estimated_channel_freq[ant_rx][1][k_offset]; const c16_t csi_rs_estimated_channel_p1 = csi_rs_estimated_channel_freq[ant_rx][1][k_offset];
// H_p0 + 1*H_p1 = (H_p0_re + H_p1_re) + 1j*(H_p0_im + H_p1_im) // H_p0 + 1*H_p1 = (H_p0_re + H_p1_re) + 1j*(H_p0_im + H_p1_im)
sum_re[0] += (csi_rs_estimated_channel_p0->r+csi_rs_estimated_channel_p1->r); c32_t tmp, tmp2;
sum_im[0] += (csi_rs_estimated_channel_p0->i+csi_rs_estimated_channel_p1->i); csum(tmp, csi_rs_estimated_channel_p0, csi_rs_estimated_channel_p1);
sum2_re[0] += ((csi_rs_estimated_channel_p0->r+csi_rs_estimated_channel_p1->r)*(csi_rs_estimated_channel_p0->r+csi_rs_estimated_channel_p1->r))>>log2_re; csum(sum[0], sum[0], tmp);
sum2_im[0] += ((csi_rs_estimated_channel_p0->i+csi_rs_estimated_channel_p1->i)*(csi_rs_estimated_channel_p0->i+csi_rs_estimated_channel_p1->i))>>log2_re; tmp2 = (c32_t){(tmp.r * tmp.r) >> log2_re, (tmp.i * tmp.i) >> log2_re};
csum(sum2[0], sum2[0], tmp2);
// H_p0 + 1j*H_p1 = (H_p0_re - H_p1_im) + 1j*(H_p0_im + H_p1_re) // H_p0 + 1j*H_p1 = (H_p0_re - H_p1_im) + 1j*(H_p0_im + H_p1_re)
sum_re[1] += (csi_rs_estimated_channel_p0->r-csi_rs_estimated_channel_p1->i); tmp = (c32_t){csi_rs_estimated_channel_p0.r - csi_rs_estimated_channel_p1.i,
sum_im[1] += (csi_rs_estimated_channel_p0->i+csi_rs_estimated_channel_p1->r); csi_rs_estimated_channel_p0.i + csi_rs_estimated_channel_p1.r};
sum2_re[1] += ((csi_rs_estimated_channel_p0->r-csi_rs_estimated_channel_p1->i)*(csi_rs_estimated_channel_p0->r-csi_rs_estimated_channel_p1->i))>>log2_re; csum(sum[1], sum[1], tmp);
sum2_im[1] += ((csi_rs_estimated_channel_p0->i+csi_rs_estimated_channel_p1->r)*(csi_rs_estimated_channel_p0->i+csi_rs_estimated_channel_p1->r))>>log2_re; tmp2 = (c32_t){(tmp.r * tmp.r) >> log2_re, (tmp.i * tmp.i) >> log2_re};
csum(sum2[1], sum2[1], tmp2);
// H_p0 - 1*H_p1 = (H_p0_re - H_p1_re) + 1j*(H_p0_im - H_p1_im) // H_p0 - 1*H_p1 = (H_p0_re - H_p1_re) + 1j*(H_p0_im - H_p1_im)
sum_re[2] += (csi_rs_estimated_channel_p0->r-csi_rs_estimated_channel_p1->r); tmp = (c32_t){csi_rs_estimated_channel_p0.r - csi_rs_estimated_channel_p1.r,
sum_im[2] += (csi_rs_estimated_channel_p0->i-csi_rs_estimated_channel_p1->i); csi_rs_estimated_channel_p0.i - csi_rs_estimated_channel_p1.i};
sum2_re[2] += ((csi_rs_estimated_channel_p0->r-csi_rs_estimated_channel_p1->r)*(csi_rs_estimated_channel_p0->r-csi_rs_estimated_channel_p1->r))>>log2_re; csum(sum[2], sum[2], tmp);
sum2_im[2] += ((csi_rs_estimated_channel_p0->i-csi_rs_estimated_channel_p1->i)*(csi_rs_estimated_channel_p0->i-csi_rs_estimated_channel_p1->i))>>log2_re; tmp2 = (c32_t){(tmp.r * tmp.r) >> log2_re, (tmp.i * tmp.i) >> log2_re};
csum(sum2[1], sum2[1], tmp2);
// H_p0 - 1j*H_p1 = (H_p0_re + H_p1_im) + 1j*(H_p0_im - H_p1_re) // H_p0 - 1j*H_p1 = (H_p0_re + H_p1_im) + 1j*(H_p0_im - H_p1_re)
sum_re[3] += (csi_rs_estimated_channel_p0->r+csi_rs_estimated_channel_p1->i); tmp = (c32_t){csi_rs_estimated_channel_p0.r + csi_rs_estimated_channel_p1.i,
sum_im[3] += (csi_rs_estimated_channel_p0->i-csi_rs_estimated_channel_p1->r); csi_rs_estimated_channel_p0.i - csi_rs_estimated_channel_p1.r};
sum2_re[3] += ((csi_rs_estimated_channel_p0->r+csi_rs_estimated_channel_p1->i)*(csi_rs_estimated_channel_p0->r+csi_rs_estimated_channel_p1->i))>>log2_re; csum(sum[2], sum[2], tmp);
sum2_im[3] += ((csi_rs_estimated_channel_p0->i-csi_rs_estimated_channel_p1->r)*(csi_rs_estimated_channel_p0->i-csi_rs_estimated_channel_p1->r))>>log2_re; tmp2 = (c32_t){(tmp.r * tmp.r) >> log2_re, (tmp.i * tmp.i) >> log2_re};
csum(sum2[2], sum2[2], tmp2);
} }
} }
// We should perform >>nr_csi_info->log2_re here for all terms, but since sum2_re and sum2_im can be high values, // We should perform >>nr_csi_info->log2_re here for all terms, but since sum2_re and sum2_im can be high values,
// we performed this above. // we performed this above.
for(int p = 0; p<4; p++) { for(int p = 0; p<4; p++) {
int32_t power_re = sum2_re[p] - (sum_re[p]>>log2_re)*(sum_re[p]>>log2_re); c32_t power = {sum2[p].r - (sum[p].r >> log2_re) * (sum[p].r >> log2_re),
int32_t power_im = sum2_im[p] - (sum_im[p]>>log2_re)*(sum_im[p]>>log2_re); sum2[p].i - (sum[p].i >> log2_re) * (sum[p].i >> log2_re)};
tested_precoded_sinr[p] = (power_re+power_im)/(int32_t)interference_plus_noise_power; tested_precoded_sinr[p] = (power.r + power.i) / (int32_t)interference_plus_noise_power;
} }
if(rank_indicator == 0) { if(rank_indicator == 0) {
...@@ -887,7 +873,7 @@ void nr_ue_csi_rs_procedures(PHY_VARS_NR_UE *ue, ...@@ -887,7 +873,7 @@ void nr_ue_csi_rs_procedures(PHY_VARS_NR_UE *ue,
} }
const NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms; const NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms;
int32_t csi_rs_received_signal[frame_parms->nb_antennas_rx][frame_parms->samples_per_slot_wCP]; c16_t csi_rs_received_signal[frame_parms->nb_antennas_rx][frame_parms->samples_per_slot_wCP];
uint8_t N_cdm_groups = 0; uint8_t N_cdm_groups = 0;
uint8_t CDM_group_size = 0; uint8_t CDM_group_size = 0;
uint8_t k_prime = 0; uint8_t k_prime = 0;
...@@ -922,8 +908,8 @@ void nr_ue_csi_rs_procedures(PHY_VARS_NR_UE *ue, ...@@ -922,8 +908,8 @@ void nr_ue_csi_rs_procedures(PHY_VARS_NR_UE *ue,
k_overline, k_overline,
l_overline); l_overline);
int32_t csi_rs_ls_estimated_channel[frame_parms->nb_antennas_rx][N_ports][frame_parms->ofdm_symbol_size]; c16_t csi_rs_ls_estimated_channel[frame_parms->nb_antennas_rx][N_ports][frame_parms->ofdm_symbol_size];
int32_t csi_rs_estimated_channel_freq[frame_parms->nb_antennas_rx][N_ports][frame_parms->ofdm_symbol_size + FILTER_MARGIN]; c16_t csi_rs_estimated_channel_freq[frame_parms->nb_antennas_rx][N_ports][frame_parms->ofdm_symbol_size + FILTER_MARGIN];
// (long)&csi_rs_estimated_channel_freq[0][0][frame_parms->first_carrier_offset] & 0x1F gives us the remainder of the integer division by 32 of the memory address // (long)&csi_rs_estimated_channel_freq[0][0][frame_parms->first_carrier_offset] & 0x1F gives us the remainder of the integer division by 32 of the memory address
// By subtracting the previous value of 32, we know how much is left to have a multiple of 32. // By subtracting the previous value of 32, we know how much is left to have a multiple of 32.
...@@ -953,7 +939,7 @@ void nr_ue_csi_rs_procedures(PHY_VARS_NR_UE *ue, ...@@ -953,7 +939,7 @@ void nr_ue_csi_rs_procedures(PHY_VARS_NR_UE *ue,
proc, proc,
csirs_config_pdu, csirs_config_pdu,
ue->nr_csi_info, ue->nr_csi_info,
(const int32_t **) ue->nr_csi_info->csi_rs_generated_signal, ue->nr_csi_info->csi_rs_generated_signal,
csi_rs_received_signal, csi_rs_received_signal,
N_cdm_groups, N_cdm_groups,
CDM_group_size, CDM_group_size,
......
...@@ -86,11 +86,11 @@ unsigned char offset_mumimo_llr_drange[29][3]={{8,8,8},{7,7,7},{7,7,7},{7,7,7},{ ...@@ -86,11 +86,11 @@ unsigned char offset_mumimo_llr_drange[29][3]={{8,8,8},{7,7,7},{7,7,7},{7,7,7},{
static void nr_dlsch_mmse(uint32_t rx_size_symbol, static void nr_dlsch_mmse(uint32_t rx_size_symbol,
unsigned char n_rx, unsigned char n_rx,
unsigned char n_tx, // number of layer unsigned char n_tx, // number of layer
int32_t rxdataF_comp[][n_rx][rx_size_symbol * NR_SYMBOLS_PER_SLOT], c16_t rxdataF_comp[][n_rx][rx_size_symbol * NR_SYMBOLS_PER_SLOT],
int32_t dl_ch_mag[][n_rx][rx_size_symbol], c16_t dl_ch_mag[][n_rx][rx_size_symbol],
int32_t dl_ch_magb[][n_rx][rx_size_symbol], c16_t dl_ch_magb[][n_rx][rx_size_symbol],
int32_t dl_ch_magr[][n_rx][rx_size_symbol], c16_t dl_ch_magr[][n_rx][rx_size_symbol],
int32_t dl_ch_estimates_ext[][rx_size_symbol], c16_t dl_ch_estimates_ext[][rx_size_symbol],
unsigned short nb_rb, unsigned short nb_rb,
unsigned char mod_order, unsigned char mod_order,
int shift, int shift,
...@@ -114,10 +114,10 @@ static int nr_dlsch_llr(uint32_t rx_size_symbol, ...@@ -114,10 +114,10 @@ static int nr_dlsch_llr(uint32_t rx_size_symbol,
uint sz, uint sz,
int16_t layer_llr[][sz], int16_t layer_llr[][sz],
NR_DL_FRAME_PARMS *frame_parms, NR_DL_FRAME_PARMS *frame_parms,
int32_t rxdataF_comp[][nbRx][rx_size_symbol * NR_SYMBOLS_PER_SLOT], c16_t rxdataF_comp[][nbRx][rx_size_symbol * NR_SYMBOLS_PER_SLOT],
int32_t dl_ch_mag[rx_size_symbol], c16_t dl_ch_mag[rx_size_symbol],
int32_t dl_ch_magb[rx_size_symbol], c16_t dl_ch_magb[rx_size_symbol],
int32_t dl_ch_magr[rx_size_symbol], c16_t dl_ch_magr[rx_size_symbol],
NR_DL_UE_HARQ_t *dlsch0_harq, NR_DL_UE_HARQ_t *dlsch0_harq,
NR_DL_UE_HARQ_t *dlsch1_harq, NR_DL_UE_HARQ_t *dlsch1_harq,
unsigned char harq_pid, unsigned char harq_pid,
...@@ -147,9 +147,9 @@ static void nr_dlsch_extract_rbs(uint32_t rxdataF_sz, ...@@ -147,9 +147,9 @@ static void nr_dlsch_extract_rbs(uint32_t rxdataF_sz,
c16_t rxdataF[][rxdataF_sz], c16_t rxdataF[][rxdataF_sz],
uint32_t rx_size_symbol, uint32_t rx_size_symbol,
uint32_t pdsch_est_size, uint32_t pdsch_est_size,
int32_t dl_ch_estimates[][pdsch_est_size], c16_t dl_ch_estimates[][pdsch_est_size],
c16_t rxdataF_ext[][rx_size_symbol], c16_t rxdataF_ext[][rx_size_symbol],
int32_t dl_ch_estimates_ext[][rx_size_symbol], c16_t dl_ch_estimates_ext[][rx_size_symbol],
unsigned char symbol, unsigned char symbol,
uint8_t pilots, uint8_t pilots,
uint8_t config_type, uint8_t config_type,
...@@ -162,7 +162,7 @@ static void nr_dlsch_extract_rbs(uint32_t rxdataF_sz, ...@@ -162,7 +162,7 @@ static void nr_dlsch_extract_rbs(uint32_t rxdataF_sz,
int chest_time_type); int chest_time_type);
static void nr_dlsch_channel_level_median(uint32_t rx_size_symbol, static void nr_dlsch_channel_level_median(uint32_t rx_size_symbol,
int32_t dl_ch_estimates_ext[][rx_size_symbol], c16_t dl_ch_estimates_ext[][rx_size_symbol],
int32_t median[MAX_ANT][MAX_ANT], int32_t median[MAX_ANT][MAX_ANT],
int n_tx, int n_tx,
int n_rx, int n_rx,
...@@ -188,11 +188,11 @@ static void nr_dlsch_channel_level_median(uint32_t rx_size_symbol, ...@@ -188,11 +188,11 @@ static void nr_dlsch_channel_level_median(uint32_t rx_size_symbol,
static void nr_dlsch_channel_compensation(uint32_t rx_size_symbol, static void nr_dlsch_channel_compensation(uint32_t rx_size_symbol,
int nbRx, int nbRx,
c16_t rxdataF_ext[][rx_size_symbol], c16_t rxdataF_ext[][rx_size_symbol],
int32_t dl_ch_estimates_ext[][rx_size_symbol], c16_t dl_ch_estimates_ext[][rx_size_symbol],
int32_t dl_ch_mag[][nbRx][rx_size_symbol], c16_t dl_ch_mag[][nbRx][rx_size_symbol],
int32_t dl_ch_magb[][nbRx][rx_size_symbol], c16_t dl_ch_magb[][nbRx][rx_size_symbol],
int32_t dl_ch_magr[][nbRx][rx_size_symbol], c16_t dl_ch_magr[][nbRx][rx_size_symbol],
int32_t rxdataF_comp[][nbRx][rx_size_symbol * NR_SYMBOLS_PER_SLOT], c16_t rxdataF_comp[][nbRx][rx_size_symbol * NR_SYMBOLS_PER_SLOT],
int ***rho, int ***rho,
NR_DL_FRAME_PARMS *frame_parms, NR_DL_FRAME_PARMS *frame_parms,
uint8_t n_layers, uint8_t n_layers,
...@@ -212,32 +212,32 @@ static void nr_dlsch_channel_compensation(uint32_t rx_size_symbol, ...@@ -212,32 +212,32 @@ static void nr_dlsch_channel_compensation(uint32_t rx_size_symbol,
@param nb_rb Number of allocated RBs @param nb_rb Number of allocated RBs
*/ */
static void nr_dlsch_channel_level(uint32_t rx_size_symbol, static void nr_dlsch_channel_level(uint32_t rx_size_symbol,
int32_t dl_ch_estimates_ext[][rx_size_symbol], c16_t dl_ch_estimates_ext[][rx_size_symbol],
uint8_t n_rx, uint8_t n_rx,
uint8_t n_tx, uint8_t n_tx,
int32_t avg[MAX_ANT][MAX_ANT], int32_t avg[MAX_ANT][MAX_ANT],
uint32_t len); uint32_t len);
void nr_dlsch_scale_channel(uint32_t rx_size_symbol, static void nr_dlsch_scale_channel(uint32_t rx_size_symbol,
int32_t dl_ch_estimates_ext[][rx_size_symbol], c16_t dl_ch_estimates_ext[][rx_size_symbol],
NR_DL_FRAME_PARMS *frame_parms, NR_DL_FRAME_PARMS *frame_parms,
uint8_t n_tx, uint8_t n_tx,
uint8_t n_rx, uint8_t n_rx,
uint8_t symbol, uint8_t symbol,
uint8_t pilots, uint8_t pilots,
uint32_t len, uint32_t len,
unsigned short nb_rb); unsigned short nb_rb);
void nr_dlsch_detection_mrc(uint32_t rx_size_symbol, static void nr_dlsch_detection_mrc(uint32_t rx_size_symbol,
short n_tx, short n_tx,
short n_rx, short n_rx,
int32_t rxdataF_comp[][n_rx][rx_size_symbol * NR_SYMBOLS_PER_SLOT], c16_t rxdataF_comp[][n_rx][rx_size_symbol * NR_SYMBOLS_PER_SLOT],
int ***rho, int ***rho,
int32_t dl_ch_mag[][n_rx][rx_size_symbol], c16_t dl_ch_mag[][n_rx][rx_size_symbol],
int32_t dl_ch_magb[][n_rx][rx_size_symbol], c16_t dl_ch_magb[][n_rx][rx_size_symbol],
int32_t dl_ch_magr[][n_rx][rx_size_symbol], c16_t dl_ch_magr[][n_rx][rx_size_symbol],
unsigned char symbol, unsigned char symbol,
unsigned short nb_rb, unsigned short nb_rb,
int length); int length);
/* Main Function */ /* Main Function */
int nr_rx_pdsch(PHY_VARS_NR_UE *ue, int nr_rx_pdsch(PHY_VARS_NR_UE *ue,
...@@ -247,7 +247,7 @@ int nr_rx_pdsch(PHY_VARS_NR_UE *ue, ...@@ -247,7 +247,7 @@ int nr_rx_pdsch(PHY_VARS_NR_UE *ue,
bool first_symbol_flag, bool first_symbol_flag,
unsigned char harq_pid, unsigned char harq_pid,
uint32_t pdsch_est_size, uint32_t pdsch_est_size,
int32_t dl_ch_estimates[][pdsch_est_size], c16_t dl_ch_estimates[][pdsch_est_size],
int16_t *llr[2], int16_t *llr[2],
uint32_t dl_valid_re[NR_SYMBOLS_PER_SLOT], uint32_t dl_valid_re[NR_SYMBOLS_PER_SLOT],
c16_t rxdataF[][ue->frame_parms.samples_per_slot_wCP], c16_t rxdataF[][ue->frame_parms.samples_per_slot_wCP],
...@@ -255,7 +255,7 @@ int nr_rx_pdsch(PHY_VARS_NR_UE *ue, ...@@ -255,7 +255,7 @@ int nr_rx_pdsch(PHY_VARS_NR_UE *ue,
int32_t *log2_maxh, int32_t *log2_maxh,
int rx_size_symbol, int rx_size_symbol,
int nbRx, int nbRx,
int32_t rxdataF_comp[][nbRx][rx_size_symbol * NR_SYMBOLS_PER_SLOT], c16_t rxdataF_comp[][nbRx][rx_size_symbol * NR_SYMBOLS_PER_SLOT],
c16_t ptrs_phase_per_slot[][NR_SYMBOLS_PER_SLOT], c16_t ptrs_phase_per_slot[][NR_SYMBOLS_PER_SLOT],
int32_t ptrs_re_per_slot[][NR_SYMBOLS_PER_SLOT], int32_t ptrs_re_per_slot[][NR_SYMBOLS_PER_SLOT],
int G, int G,
...@@ -263,17 +263,18 @@ int nr_rx_pdsch(PHY_VARS_NR_UE *ue, ...@@ -263,17 +263,18 @@ int nr_rx_pdsch(PHY_VARS_NR_UE *ue,
{ {
const int nl = dlsch[0].Nl; const int nl = dlsch[0].Nl;
const int matrixSz = ue->frame_parms.nb_antennas_rx * nl; const int matrixSz = ue->frame_parms.nb_antennas_rx * nl;
__attribute__((aligned(32))) int32_t dl_ch_estimates_ext[matrixSz][rx_size_symbol]; __attribute__((aligned(32))) c16_t dl_ch_estimates_ext[matrixSz][rx_size_symbol];
memset(dl_ch_estimates_ext, 0, sizeof(dl_ch_estimates_ext)); memset(dl_ch_estimates_ext, 0, sizeof(dl_ch_estimates_ext));
__attribute__((aligned(32))) int32_t dl_ch_mag[nl][ue->frame_parms.nb_antennas_rx][rx_size_symbol]; __attribute__((aligned(32))) c16_t dl_ch_mag[nl][ue->frame_parms.nb_antennas_rx][rx_size_symbol];
memset(dl_ch_mag, 0, sizeof(dl_ch_mag)); memset(dl_ch_mag, 0, sizeof(dl_ch_mag));
__attribute__((aligned(32))) int32_t dl_ch_magb[nl][nbRx][rx_size_symbol]; __attribute__((aligned(32))) c16_t dl_ch_magb[nl][nbRx][rx_size_symbol];
memset(dl_ch_magb, 0, sizeof(dl_ch_magb)); memset(dl_ch_magb, 0, sizeof(dl_ch_magb));
__attribute__((aligned(32))) int32_t dl_ch_magr[nl][nbRx][rx_size_symbol]; __attribute__((aligned(32))) c16_t dl_ch_magr[nl][nbRx][rx_size_symbol];
memset(dl_ch_magr, 0, sizeof(dl_ch_magr)); memset(dl_ch_magr, 0, sizeof(dl_ch_magr));
NR_UE_COMMON *common_vars = &ue->common_vars; NR_UE_COMMON *common_vars = &ue->common_vars;
NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms; NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms;
PHY_NR_MEASUREMENTS *measurements = &ue->measurements; PHY_NR_MEASUREMENTS *measurements = &ue->measurements;
...@@ -637,22 +638,28 @@ int nr_rx_pdsch(PHY_VARS_NR_UE *ue, ...@@ -637,22 +638,28 @@ int nr_rx_pdsch(PHY_VARS_NR_UE *ue,
write_output(filename, "rxdataF0", &rxdataF[0][0], NR_SYMBOLS_PER_SLOT*frame_parms->ofdm_symbol_size, 1, 1); write_output(filename, "rxdataF0", &rxdataF[0][0], NR_SYMBOLS_PER_SLOT*frame_parms->ofdm_symbol_size, 1, 1);
snprintf(filename, 50, "dl_ch_estimates0%d_symb_%d_nr_slot_rx_%d.m", aa, symbol, nr_slot_rx); snprintf(filename, 50, "dl_ch_estimates0%d_symb_%d_nr_slot_rx_%d.m", aa, symbol, nr_slot_rx);
write_output(filename, "dl_ch_estimates", &dl_ch_estimates[aa][0], NR_SYMBOLS_PER_SLOT*frame_parms->ofdm_symbol_size, 1, 1); write_output(filename, "dl_ch_estimates", dl_ch_estimates[aa], NR_SYMBOLS_PER_SLOT * frame_parms->ofdm_symbol_size, 1, 1);
snprintf(filename, 50, "rxdataF_ext0%d_symb_%d_nr_slot_rx_%d.m", aa, symbol, nr_slot_rx); snprintf(filename, 50, "rxdataF_ext0%d_symb_%d_nr_slot_rx_%d.m", aa, symbol, nr_slot_rx);
write_output(filename, "rxdataF_ext", &rxdataF_ext[aa][0], NR_SYMBOLS_PER_SLOT*frame_parms->N_RB_DL*NR_NB_SC_PER_RB, 1, 1); write_output(filename, "rxdataF_ext", rxdataF_ext[aa], NR_SYMBOLS_PER_SLOT * frame_parms->N_RB_DL * NR_NB_SC_PER_RB, 1, 1);
snprintf(filename, 50, "dl_ch_estimates_ext0%d_symb_%d_nr_slot_rx_%d.m", aa, symbol, nr_slot_rx); snprintf(filename, 50, "dl_ch_estimates_ext0%d_symb_%d_nr_slot_rx_%d.m", aa, symbol, nr_slot_rx);
write_output(filename, "dl_ch_estimates_ext00", &dl_ch_estimates_ext[aa][0], NR_SYMBOLS_PER_SLOT*frame_parms->N_RB_DL*NR_NB_SC_PER_RB, 1, 1); write_output(filename,
"dl_ch_estimates_ext00",
dl_ch_estimates_ext[aa],
NR_SYMBOLS_PER_SLOT * frame_parms->N_RB_DL * NR_NB_SC_PER_RB,
1,
1);
snprintf(filename, 50, "rxdataF_comp0%d_symb_%d_nr_slot_rx_%d.m", aa, symbol, nr_slot_rx); snprintf(filename, 50, "rxdataF_comp0%d_symb_%d_nr_slot_rx_%d.m", aa, symbol, nr_slot_rx);
write_output(filename, "rxdataF_comp00", &rxdataF_comp[aa][0], NR_SYMBOLS_PER_SLOT*frame_parms->N_RB_DL*NR_NB_SC_PER_RB, 1, 1); write_output(filename, "rxdataF_comp00", rxdataF_comp[aa], NR_SYMBOLS_PER_SLOT * frame_parms->N_RB_DL * NR_NB_SC_PER_RB, 1, 1);
/* /*
for (int i=0; i < 2; i++){ for (int i=0; i < 2; i++){
snprintf(filename, 50, "llr%d_symb_%d_nr_slot_rx_%d.m", i, symbol, nr_slot_rx); snprintf(filename, 50, "llr%d_symb_%d_nr_slot_rx_%d.m", i, symbol, nr_slot_rx);
write_output(filename,"llr", &llr[i][0], (NR_SYMBOLS_PER_SLOT*nb_rb_pdsch*NR_NB_SC_PER_RB*dlsch1_harq->Qm) - 4*(nb_rb_pdsch*4*dlsch1_harq->Qm), 1, 0); write_output(filename,"llr", &llr[i][0], (NR_SYMBOLS_PER_SLOT*nb_rb_pdsch*NR_NB_SC_PER_RB*dlsch1_harq->Qm) -
} 4*(nb_rb_pdsch*4*dlsch1_harq->Qm), 1, 0);
*/ }
*/
#endif #endif
} }
...@@ -759,11 +766,11 @@ simde__m128i nr_dlsch_a_mult_conjb(simde__m128i a, simde__m128i b, unsigned char ...@@ -759,11 +766,11 @@ simde__m128i nr_dlsch_a_mult_conjb(simde__m128i a, simde__m128i b, unsigned char
static void nr_dlsch_channel_compensation(uint32_t rx_size_symbol, static void nr_dlsch_channel_compensation(uint32_t rx_size_symbol,
int nbRx, int nbRx,
c16_t rxdataF_ext[][rx_size_symbol], c16_t rxdataF_ext[][rx_size_symbol],
int32_t dl_ch_estimates_ext[][rx_size_symbol], c16_t dl_ch_estimates_ext[][rx_size_symbol],
int32_t dl_ch_mag[][nbRx][rx_size_symbol], c16_t dl_ch_mag[][nbRx][rx_size_symbol],
int32_t dl_ch_magb[][nbRx][rx_size_symbol], c16_t dl_ch_magb[][nbRx][rx_size_symbol],
int32_t dl_ch_magr[][nbRx][rx_size_symbol], c16_t dl_ch_magr[][nbRx][rx_size_symbol],
int32_t rxdataF_comp[][nbRx][rx_size_symbol * NR_SYMBOLS_PER_SLOT], c16_t rxdataF_comp[][nbRx][rx_size_symbol * NR_SYMBOLS_PER_SLOT],
int ***rho, int ***rho,
NR_DL_FRAME_PARMS *frame_parms, NR_DL_FRAME_PARMS *frame_parms,
uint8_t n_layers, uint8_t n_layers,
...@@ -951,15 +958,15 @@ static void nr_dlsch_channel_compensation(uint32_t rx_size_symbol, ...@@ -951,15 +958,15 @@ static void nr_dlsch_channel_compensation(uint32_t rx_size_symbol,
} }
} }
void nr_dlsch_scale_channel(uint32_t rx_size_symbol, static void nr_dlsch_scale_channel(uint32_t rx_size_symbol,
int32_t dl_ch_estimates_ext[][rx_size_symbol], c16_t dl_ch_estimates_ext[][rx_size_symbol],
NR_DL_FRAME_PARMS *frame_parms, NR_DL_FRAME_PARMS *frame_parms,
uint8_t n_tx, uint8_t n_tx,
uint8_t n_rx, uint8_t n_rx,
uint8_t symbol, uint8_t symbol,
uint8_t pilots, uint8_t pilots,
uint32_t len, uint32_t len,
unsigned short nb_rb) unsigned short nb_rb)
{ {
...@@ -1012,7 +1019,7 @@ void nr_dlsch_scale_channel(uint32_t rx_size_symbol, ...@@ -1012,7 +1019,7 @@ void nr_dlsch_scale_channel(uint32_t rx_size_symbol,
@param len Number of allocated PDSCH REs @param len Number of allocated PDSCH REs
*/ */
void nr_dlsch_channel_level(uint32_t rx_size_symbol, void nr_dlsch_channel_level(uint32_t rx_size_symbol,
int32_t dl_ch_estimates_ext[][rx_size_symbol], c16_t dl_ch_estimates_ext[][rx_size_symbol],
uint8_t n_rx, uint8_t n_rx,
uint8_t n_tx, uint8_t n_tx,
int32_t avg[MAX_ANT][MAX_ANT], int32_t avg[MAX_ANT][MAX_ANT],
...@@ -1046,7 +1053,7 @@ void nr_dlsch_channel_level(uint32_t rx_size_symbol, ...@@ -1046,7 +1053,7 @@ void nr_dlsch_channel_level(uint32_t rx_size_symbol,
} }
static void nr_dlsch_channel_level_median(uint32_t rx_size_symbol, static void nr_dlsch_channel_level_median(uint32_t rx_size_symbol,
int32_t dl_ch_estimates_ext[][rx_size_symbol], c16_t dl_ch_estimates_ext[][rx_size_symbol],
int32_t median[MAX_ANT][MAX_ANT], int32_t median[MAX_ANT][MAX_ANT],
int n_tx, int n_tx,
int n_rx, int n_rx,
...@@ -1087,9 +1094,9 @@ static void nr_dlsch_extract_rbs(uint32_t rxdataF_sz, ...@@ -1087,9 +1094,9 @@ static void nr_dlsch_extract_rbs(uint32_t rxdataF_sz,
c16_t rxdataF[][rxdataF_sz], c16_t rxdataF[][rxdataF_sz],
uint32_t rx_size_symbol, uint32_t rx_size_symbol,
uint32_t pdsch_est_size, uint32_t pdsch_est_size,
int32_t dl_ch_estimates[][pdsch_est_size], c16_t dl_ch_estimates[][pdsch_est_size],
c16_t rxdataF_ext[][rx_size_symbol], c16_t rxdataF_ext[][rx_size_symbol],
int32_t dl_ch_estimates_ext[][rx_size_symbol], c16_t dl_ch_estimates_ext[][rx_size_symbol],
unsigned char symbol, unsigned char symbol,
uint8_t pilots, uint8_t pilots,
uint8_t config_type, uint8_t config_type,
...@@ -1122,9 +1129,8 @@ static void nr_dlsch_extract_rbs(uint32_t rxdataF_sz, ...@@ -1122,9 +1129,8 @@ static void nr_dlsch_extract_rbs(uint32_t rxdataF_sz,
c16_t *rxF = &rxdataF[aarx][symbol * frame_parms->ofdm_symbol_size]; c16_t *rxF = &rxdataF[aarx][symbol * frame_parms->ofdm_symbol_size];
for (unsigned char l = 0; l < Nl; l++) { for (unsigned char l = 0; l < Nl; l++) {
c16_t *dl_ch0 = &dl_ch_estimates[(l * frame_parms->nb_antennas_rx) + aarx][validDmrsEst * frame_parms->ofdm_symbol_size];
int32_t *dl_ch0 = &dl_ch_estimates[(l * frame_parms->nb_antennas_rx) + aarx][validDmrsEst * frame_parms->ofdm_symbol_size]; c16_t *dl_ch0_ext = dl_ch_estimates_ext[(l * frame_parms->nb_antennas_rx) + aarx];
int32_t *dl_ch0_ext = dl_ch_estimates_ext[(l * frame_parms->nb_antennas_rx) + aarx];
if (pilots == 0) { //data symbol only if (pilots == 0) { //data symbol only
if (l == 0) { if (l == 0) {
...@@ -1204,37 +1210,34 @@ static void nr_dlsch_extract_rbs(uint32_t rxdataF_sz, ...@@ -1204,37 +1210,34 @@ static void nr_dlsch_extract_rbs(uint32_t rxdataF_sz,
} }
} }
void nr_dlsch_detection_mrc(uint32_t rx_size_symbol, static void nr_dlsch_detection_mrc(uint32_t rx_size_symbol,
short n_tx, short n_tx,
short n_rx, short n_rx,
int32_t rxdataF_comp[][n_rx][rx_size_symbol * NR_SYMBOLS_PER_SLOT], c16_t rxdataF_comp[][n_rx][rx_size_symbol * NR_SYMBOLS_PER_SLOT],
int ***rho, int ***rho,
int32_t dl_ch_mag[][n_rx][rx_size_symbol], c16_t dl_ch_mag[][n_rx][rx_size_symbol],
int32_t dl_ch_magb[][n_rx][rx_size_symbol], c16_t dl_ch_magb[][n_rx][rx_size_symbol],
int32_t dl_ch_magr[][n_rx][rx_size_symbol], c16_t dl_ch_magr[][n_rx][rx_size_symbol],
unsigned char symbol, unsigned char symbol,
unsigned short nb_rb, unsigned short nb_rb,
int length) { int length)
unsigned char aatx, aarx; {
int i;
simde__m128i *rxdataF_comp128_0,*rxdataF_comp128_1,*dl_ch_mag128_0,*dl_ch_mag128_1,*dl_ch_mag128_0b,*dl_ch_mag128_1b,*dl_ch_mag128_0r,*dl_ch_mag128_1r;
uint32_t nb_rb_0 = length/12 + ((length%12)?1:0); uint32_t nb_rb_0 = length/12 + ((length%12)?1:0);
if (n_rx>1) { if (n_rx>1) {
for (aatx=0; aatx<n_tx; aatx++) { for (int aatx = 0; aatx < n_tx; aatx++) {
rxdataF_comp128_0 = (simde__m128i *)(rxdataF_comp[aatx][0] + symbol * nb_rb * 12); simde__m128i *rxdataF_comp128_0 = (simde__m128i *)(rxdataF_comp[aatx][0] + symbol * nb_rb * 12);
dl_ch_mag128_0 = (simde__m128i *)dl_ch_mag[aatx][0]; simde__m128i *dl_ch_mag128_0 = (simde__m128i *)dl_ch_mag[aatx][0];
dl_ch_mag128_0b = (simde__m128i *)dl_ch_magb[aatx][0]; simde__m128i *dl_ch_mag128_0b = (simde__m128i *)dl_ch_magb[aatx][0];
dl_ch_mag128_0r = (simde__m128i *)dl_ch_magr[aatx][0]; simde__m128i *dl_ch_mag128_0r = (simde__m128i *)dl_ch_magr[aatx][0];
for (aarx=1; aarx<n_rx; aarx++) { for (int aarx = 1; aarx < n_rx; aarx++) {
rxdataF_comp128_1 = (simde__m128i *)(rxdataF_comp[aatx][aarx] + symbol * nb_rb * 12); simde__m128i *rxdataF_comp128_1 = (simde__m128i *)(rxdataF_comp[aatx][aarx] + symbol * nb_rb * 12);
dl_ch_mag128_1 = (simde__m128i *)dl_ch_mag[aatx][aarx]; simde__m128i *dl_ch_mag128_1 = (simde__m128i *)dl_ch_mag[aatx][aarx];
dl_ch_mag128_1b = (simde__m128i *)dl_ch_magb[aatx][aarx]; simde__m128i *dl_ch_mag128_1b = (simde__m128i *)dl_ch_magb[aatx][aarx];
dl_ch_mag128_1r = (simde__m128i *)dl_ch_magr[aatx][aarx]; simde__m128i *dl_ch_mag128_1r = (simde__m128i *)dl_ch_magr[aatx][aarx];
// MRC on each re of rb, both on MF output and magnitude (for 16QAM/64QAM/256 llr computation) // MRC on each re of rb, both on MF output and magnitude (for 16QAM/64QAM/256 llr computation)
for (i=0; i<nb_rb_0*3; i++) { for (int i = 0; i < nb_rb_0 * 3; i++) {
rxdataF_comp128_0[i] = simde_mm_adds_epi16(rxdataF_comp128_0[i],rxdataF_comp128_1[i]); rxdataF_comp128_0[i] = simde_mm_adds_epi16(rxdataF_comp128_0[i],rxdataF_comp128_1[i]);
dl_ch_mag128_0[i] = simde_mm_adds_epi16(dl_ch_mag128_0[i],dl_ch_mag128_1[i]); dl_ch_mag128_0[i] = simde_mm_adds_epi16(dl_ch_mag128_0[i],dl_ch_mag128_1[i]);
dl_ch_mag128_0b[i] = simde_mm_adds_epi16(dl_ch_mag128_0b[i],dl_ch_mag128_1b[i]); dl_ch_mag128_0b[i] = simde_mm_adds_epi16(dl_ch_mag128_0b[i],dl_ch_mag128_1b[i]);
...@@ -1243,27 +1246,25 @@ void nr_dlsch_detection_mrc(uint32_t rx_size_symbol, ...@@ -1243,27 +1246,25 @@ void nr_dlsch_detection_mrc(uint32_t rx_size_symbol,
} }
} }
#ifdef DEBUG_DLSCH_DEMOD #ifdef DEBUG_DLSCH_DEMOD
for (i=0; i<nb_rb_0*3; i++) { for (int i = 0; i < nb_rb_0 * 3; i++) {
printf("symbol%d RB %d\n",symbol,i/3); printf("symbol%d RB %d\n", symbol, i / 3);
rxdataF_comp128_0 = (simde__m128i *)(rxdataF_comp[0][0] + symbol * nb_rb * 12); simde__m128i *rxdataF_comp128_0 = (simde__m128i *)(rxdataF_comp[0][0] + symbol * nb_rb * 12);
rxdataF_comp128_1 = (simde__m128i *)(rxdataF_comp[0][n_rx] + symbol * nb_rb * 12); simde__m128i *rxdataF_comp128_1 = (simde__m128i *)(rxdataF_comp[0][n_rx] + symbol * nb_rb * 12);
print_shorts("tx 1 mrc_re/mrc_Im:",(int16_t*)&rxdataF_comp128_0[i]); print_shorts("tx 1 mrc_re/mrc_Im:", (int16_t *)&rxdataF_comp128_0[i]);
print_shorts("tx 2 mrc_re/mrc_Im:",(int16_t*)&rxdataF_comp128_1[i]); print_shorts("tx 2 mrc_re/mrc_Im:", (int16_t *)&rxdataF_comp128_1[i]);
// printf("mrc mag0 = %d = %d \n",((int16_t*)&dl_ch_mag128_0[0])[0],((int16_t*)&dl_ch_mag128_0[0])[1]); // printf("mrc mag0 = %d = %d \n",((int16_t*)&dl_ch_mag128_0[0])[0],((int16_t*)&dl_ch_mag128_0[0])[1]);
// printf("mrc mag0b = %d = %d \n",((int16_t*)&dl_ch_mag128_0b[0])[0],((int16_t*)&dl_ch_mag128_0b[0])[1]); // printf("mrc mag0b = %d = %d \n",((int16_t*)&dl_ch_mag128_0b[0])[0],((int16_t*)&dl_ch_mag128_0b[0])[1]);
} }
#endif #endif
if (rho) { if (rho) {
/*rho128_0 = (simde__m128i *) &rho[0][symbol*frame_parms->N_RB_DL*12]; /*rho128_0 = (simde__m128i *) &rho[0][symbol*frame_parms->N_RB_DL*12];
rho128_1 = (simde__m128i *) &rho[1][symbol*frame_parms->N_RB_DL*12]; simde__m128i *rho128_1 = (simde__m128i *) &rho[1][symbol*frame_parms->N_RB_DL*12];
for (i=0; i<nb_rb_0*3; i++) { for (i=0; i<nb_rb_0*3; i++) {
// print_shorts("mrc rho0:",&rho128_0[i]); // print_shorts("mrc rho0:",&rho128_0[i]);
// print_shorts("mrc rho1:",&rho128_1[i]); // print_shorts("mrc rho1:",&rho128_1[i]);
rho128_0[i] = simde_mm_adds_epi16(simde_mm_srai_epi16(rho128_0[i],1),simde_mm_srai_epi16(rho128_1[i],1)); rho128_0[i] = simde_mm_adds_epi16(simde_mm_srai_epi16(rho128_0[i],1),simde_mm_srai_epi16(rho128_1[i],1));
}*/ }*/
} }
simde_mm_empty();
simde_m_empty();
} }
} }
...@@ -1580,47 +1581,38 @@ uint8_t nr_matrix_inverse(int32_t size, ...@@ -1580,47 +1581,38 @@ uint8_t nr_matrix_inverse(int32_t size,
* *
* *
* */ * */
void nr_conjch0_mult_ch1(int *ch0, void nr_conjch0_mult_ch1(c16_t *ch0, c16_t *ch1, c16_t *ch0conj_ch1, unsigned short nb_rb, unsigned char output_shift0)
int *ch1,
int32_t *ch0conj_ch1,
unsigned short nb_rb,
unsigned char output_shift0)
{ {
//This function is used to compute multiplications in H_hermitian * H matrix //This function is used to compute multiplications in H_hermitian * H matrix
short nr_conjugate[8]__attribute__((aligned(16))) = {-1,1,-1,1,-1,1,-1,1}; short nr_conjugate[8]__attribute__((aligned(16))) = {-1,1,-1,1,-1,1,-1,1};
unsigned short rb; unsigned short rb;
simde__m128i *dl_ch0_128,*dl_ch1_128, *ch0conj_ch1_128, mmtmpD0,mmtmpD1,mmtmpD2,mmtmpD3; simde__m128i *dl_ch0_128 = (simde__m128i *)ch0;
simde__m128i *dl_ch1_128 = (simde__m128i *)ch1;
dl_ch0_128 = (simde__m128i *)ch0; simde__m128i *ch0conj_ch1_128 = (simde__m128i *)ch0conj_ch1;
dl_ch1_128 = (simde__m128i *)ch1;
ch0conj_ch1_128 = (simde__m128i *)ch0conj_ch1;
for (rb=0; rb<3*nb_rb; rb++) { for (rb=0; rb<3*nb_rb; rb++) {
simde__m128i mmtmpD0 = simde_mm_madd_epi16(*dl_ch0_128, *dl_ch1_128);
mmtmpD0 = simde_mm_madd_epi16(dl_ch0_128[0],dl_ch1_128[0]); simde__m128i mmtmpD1 = simde_mm_shufflelo_epi16(*dl_ch0_128, SIMDE_MM_SHUFFLE(2, 3, 0, 1));
mmtmpD1 = simde_mm_shufflelo_epi16(dl_ch0_128[0],SIMDE_MM_SHUFFLE(2,3,0,1));
mmtmpD1 = simde_mm_shufflehi_epi16(mmtmpD1,SIMDE_MM_SHUFFLE(2,3,0,1)); mmtmpD1 = simde_mm_shufflehi_epi16(mmtmpD1,SIMDE_MM_SHUFFLE(2,3,0,1));
mmtmpD1 = simde_mm_sign_epi16(mmtmpD1,*(simde__m128i*)&nr_conjugate[0]); mmtmpD1 = simde_mm_sign_epi16(mmtmpD1, *(simde__m128i *)nr_conjugate);
mmtmpD1 = simde_mm_madd_epi16(mmtmpD1,dl_ch1_128[0]); mmtmpD1 = simde_mm_madd_epi16(mmtmpD1, *dl_ch1_128);
mmtmpD0 = simde_mm_srai_epi32(mmtmpD0,output_shift0); mmtmpD0 = simde_mm_srai_epi32(mmtmpD0,output_shift0);
mmtmpD1 = simde_mm_srai_epi32(mmtmpD1,output_shift0); mmtmpD1 = simde_mm_srai_epi32(mmtmpD1,output_shift0);
mmtmpD2 = simde_mm_unpacklo_epi32(mmtmpD0,mmtmpD1); simde__m128i mmtmpD2 = simde_mm_unpacklo_epi32(mmtmpD0, mmtmpD1);
mmtmpD3 = simde_mm_unpackhi_epi32(mmtmpD0,mmtmpD1); simde__m128i mmtmpD3 = simde_mm_unpackhi_epi32(mmtmpD0, mmtmpD1);
ch0conj_ch1_128[0] = simde_mm_packs_epi32(mmtmpD2,mmtmpD3); *ch0conj_ch1_128 = simde_mm_packs_epi32(mmtmpD2, mmtmpD3);
/*printf("\n Computing conjugates \n"); /*printf("\n Computing conjugates \n");
print_shorts("ch0:",(int16_t*)&dl_ch0_128[0]); print_shorts("ch0:",(int16_t*)&dl_ch0_128[0]);
print_shorts("ch1:",(int16_t*)&dl_ch1_128[0]); print_shorts("ch1:",(int16_t*)&dl_ch1_128[0]);
print_shorts("pack:",(int16_t*)&ch0conj_ch1_128[0]);*/ print_shorts("pack:",(int16_t*)&ch0conj_ch1_128[0]);*/
dl_ch0_128+=1; dl_ch0_128+=1;
dl_ch1_128+=1; dl_ch1_128+=1;
ch0conj_ch1_128+=1; ch0conj_ch1_128+=1;
} }
simde_mm_empty();
simde_m_empty();
} }
/* /*
...@@ -1629,11 +1621,11 @@ void nr_conjch0_mult_ch1(int *ch0, ...@@ -1629,11 +1621,11 @@ void nr_conjch0_mult_ch1(int *ch0,
static void nr_dlsch_mmse(uint32_t rx_size_symbol, static void nr_dlsch_mmse(uint32_t rx_size_symbol,
unsigned char n_rx, unsigned char n_rx,
unsigned char n_tx, // number of layer unsigned char n_tx, // number of layer
int32_t rxdataF_comp[][n_rx][rx_size_symbol * NR_SYMBOLS_PER_SLOT], c16_t rxdataF_comp[][n_rx][rx_size_symbol * NR_SYMBOLS_PER_SLOT],
int32_t dl_ch_mag[][n_rx][rx_size_symbol], c16_t dl_ch_mag[][n_rx][rx_size_symbol],
int32_t dl_ch_magb[][n_rx][rx_size_symbol], c16_t dl_ch_magb[][n_rx][rx_size_symbol],
int32_t dl_ch_magr[][n_rx][rx_size_symbol], c16_t dl_ch_magr[][n_rx][rx_size_symbol],
int32_t dl_ch_estimates_ext[][rx_size_symbol], c16_t dl_ch_estimates_ext[][rx_size_symbol],
unsigned short nb_rb, unsigned short nb_rb,
unsigned char mod_order, unsigned char mod_order,
int shift, int shift,
...@@ -1641,7 +1633,6 @@ static void nr_dlsch_mmse(uint32_t rx_size_symbol, ...@@ -1641,7 +1633,6 @@ static void nr_dlsch_mmse(uint32_t rx_size_symbol,
int length, int length,
uint32_t noise_var) uint32_t noise_var)
{ {
int *ch0r, *ch0c;
uint32_t nb_rb_0 = length/12 + ((length%12)?1:0); uint32_t nb_rb_0 = length/12 + ((length%12)?1:0);
c16_t determ_fin[12 * nb_rb_0] __attribute__((aligned(32))); c16_t determ_fin[12 * nb_rb_0] __attribute__((aligned(32)));
...@@ -1658,11 +1649,11 @@ static void nr_dlsch_mmse(uint32_t rx_size_symbol, ...@@ -1658,11 +1649,11 @@ static void nr_dlsch_mmse(uint32_t rx_size_symbol,
for (int rtx=0;rtx<n_tx;rtx++) {//row for (int rtx=0;rtx<n_tx;rtx++) {//row
for (int ctx=0;ctx<n_tx;ctx++) {//column for (int ctx=0;ctx<n_tx;ctx++) {//column
for (int aarx=0;aarx<n_rx;aarx++) { for (int aarx=0;aarx<n_rx;aarx++) {
ch0r = (int *)dl_ch_estimates_ext[rtx*n_rx+aarx]; c16_t *ch0r = dl_ch_estimates_ext[rtx * n_rx + aarx];
ch0c = (int *)dl_ch_estimates_ext[ctx*n_rx+aarx]; c16_t *ch0c = dl_ch_estimates_ext[ctx * n_rx + aarx];
nr_conjch0_mult_ch1(ch0r, nr_conjch0_mult_ch1(ch0r,
ch0c, ch0c,
(int32_t *)conjH_H_elements[aarx][ctx][rtx], // sic conjH_H_elements[aarx][ctx][rtx], // sic
nb_rb_0, nb_rb_0,
shift); shift);
if (aarx != 0) if (aarx != 0)
...@@ -1713,7 +1704,11 @@ static void nr_dlsch_mmse(uint32_t rx_size_symbol, ...@@ -1713,7 +1704,11 @@ static void nr_dlsch_mmse(uint32_t rx_size_symbol,
// printf("Computing r_%d c_%d\n",rtx,ctx); // printf("Computing r_%d c_%d\n",rtx,ctx);
// print_shorts(" H_h_H=",(int16_t*)&conjH_H_elements[ctx*n_tx+rtx][0][0]); // print_shorts(" H_h_H=",(int16_t*)&conjH_H_elements[ctx*n_tx+rtx][0][0]);
// print_shorts(" Inv_H_h_H=",(int16_t*)&inv_H_h_H[ctx*n_tx+rtx][0]); // print_shorts(" Inv_H_h_H=",(int16_t*)&inv_H_h_H[ctx*n_tx+rtx][0]);
nr_a_mult_b(inv_H_h_H[ctx][rtx], (c16_t *)(rxdataF_comp[ctx][0] + symbol * nb_rb * 12), outtemp, nb_rb_0, shift - (fp_flag == 1 ? 2 : 0)); nr_a_mult_b(inv_H_h_H[ctx][rtx],
rxdataF_comp[ctx][0] + symbol * nb_rb * 12,
outtemp,
nb_rb_0,
shift - (fp_flag == 1 ? 2 : 0));
nr_a_sum_b(rxdataF_zforcing[rtx], outtemp, nr_a_sum_b(rxdataF_zforcing[rtx], outtemp,
nb_rb_0); // a =a + b nb_rb_0); // a =a + b
} }
...@@ -1826,10 +1821,10 @@ static int nr_dlsch_llr(uint32_t rx_size_symbol, ...@@ -1826,10 +1821,10 @@ static int nr_dlsch_llr(uint32_t rx_size_symbol,
uint sz, uint sz,
int16_t layer_llr[][sz], int16_t layer_llr[][sz],
NR_DL_FRAME_PARMS *frame_parms, NR_DL_FRAME_PARMS *frame_parms,
int32_t rxdataF_comp[][nbRx][rx_size_symbol * NR_SYMBOLS_PER_SLOT], c16_t rxdataF_comp[][nbRx][rx_size_symbol * NR_SYMBOLS_PER_SLOT],
int32_t dl_ch_mag[rx_size_symbol], c16_t dl_ch_mag[rx_size_symbol],
int32_t dl_ch_magb[rx_size_symbol], c16_t dl_ch_magb[rx_size_symbol],
int32_t dl_ch_magr[rx_size_symbol], c16_t dl_ch_magr[rx_size_symbol],
NR_DL_UE_HARQ_t *dlsch0_harq, NR_DL_UE_HARQ_t *dlsch0_harq,
NR_DL_UE_HARQ_t *dlsch1_harq, NR_DL_UE_HARQ_t *dlsch1_harq,
unsigned char harq_pid, unsigned char harq_pid,
......
...@@ -49,15 +49,14 @@ int16_t nr_zeros[8] __attribute__((aligned(16))) = {0, 0, 0, 0, 0, 0, 0, 0}; ...@@ -49,15 +49,14 @@ int16_t nr_zeros[8] __attribute__((aligned(16))) = {0, 0, 0, 0, 0, 0, 0, 0};
//---------------------------------------------------------------------------------------------- //----------------------------------------------------------------------------------------------
int nr_dlsch_qpsk_llr(NR_DL_FRAME_PARMS *frame_parms, int nr_dlsch_qpsk_llr(NR_DL_FRAME_PARMS *frame_parms,
int32_t *rxdataF_comp, c16_t *rxdataF_comp,
int16_t *dlsch_llr, int16_t *dlsch_llr,
uint8_t symbol, uint8_t symbol,
uint32_t len, uint32_t len,
uint8_t first_symbol_flag, uint8_t first_symbol_flag,
uint16_t nb_rb) uint16_t nb_rb)
{ {
c16_t *rxF = rxdataF_comp + symbol * nb_rb * 12;
c16_t *rxF = (c16_t *)&rxdataF_comp[((int32_t)symbol*nb_rb*12)];
c16_t *llr32 = (c16_t *)dlsch_llr; c16_t *llr32 = (c16_t *)dlsch_llr;
int i; int i;
...@@ -90,38 +89,29 @@ int nr_dlsch_qpsk_llr(NR_DL_FRAME_PARMS *frame_parms, ...@@ -90,38 +89,29 @@ int nr_dlsch_qpsk_llr(NR_DL_FRAME_PARMS *frame_parms,
//---------------------------------------------------------------------------------------------- //----------------------------------------------------------------------------------------------
void nr_dlsch_16qam_llr(NR_DL_FRAME_PARMS *frame_parms, void nr_dlsch_16qam_llr(NR_DL_FRAME_PARMS *frame_parms,
int32_t *rxdataF_comp, c16_t *rxdataF_comp,
int16_t *dlsch_llr, int16_t *dlsch_llr,
int32_t *dl_ch_mag, c16_t *dl_ch_mag,
uint8_t symbol, uint8_t symbol,
uint32_t len, uint32_t len,
uint8_t first_symbol_flag, uint8_t first_symbol_flag,
uint16_t nb_rb) uint16_t nb_rb)
{ {
simde__m128i *rxF = (simde__m128i *)&rxdataF_comp[(symbol * nb_rb * 12)];
simde__m128i *rxF = (simde__m128i*)&rxdataF_comp[(symbol*nb_rb*12)];
simde__m128i *ch_mag;
simde__m128i llr128[2]; simde__m128i llr128[2];
uint32_t *llr32; uint32_t *llr32;
unsigned char len_mod4 = 0;
llr32 = (uint32_t *)dlsch_llr;
simde__m128i *ch_mag = (simde__m128i *)dl_ch_mag;
// printf("len=%d\n", len);
int i;
unsigned char len_mod4=0;
llr32 = (uint32_t*)dlsch_llr;
ch_mag = (simde__m128i *)dl_ch_mag;
// printf("len=%d\n", len);
len_mod4 = len&3; len_mod4 = len&3;
// printf("len_mod4=%d\n", len_mod4); // printf("len_mod4=%d\n", len_mod4);
len>>=2; // length in quad words (4 REs) len>>=2; // length in quad words (4 REs)
// printf("len>>=2=%d\n", len); // printf("len>>=2=%d\n", len);
len+=(len_mod4==0 ? 0 : 1); len+=(len_mod4==0 ? 0 : 1);
// printf("len+=%d\n", len); // printf("len+=%d\n", len);
for (i=0; i<len; i++) { for (int i = 0; i < len; i++) {
simde__m128i xmm0 =simde_mm_abs_epi16(rxF[i]); simde__m128i xmm0 =simde_mm_abs_epi16(rxF[i]);
xmm0 =simde_mm_subs_epi16(ch_mag[i],xmm0); xmm0 =simde_mm_subs_epi16(ch_mag[i],xmm0);
...@@ -136,12 +126,8 @@ void nr_dlsch_16qam_llr(NR_DL_FRAME_PARMS *frame_parms, ...@@ -136,12 +126,8 @@ void nr_dlsch_16qam_llr(NR_DL_FRAME_PARMS *frame_parms,
llr32[5] =simde_mm_extract_epi32(llr128[1],1); //((uint32_t *)&llr128[1])[1]; llr32[5] =simde_mm_extract_epi32(llr128[1],1); //((uint32_t *)&llr128[1])[1];
llr32[6] =simde_mm_extract_epi32(llr128[1],2); //((uint32_t *)&llr128[1])[2]; llr32[6] =simde_mm_extract_epi32(llr128[1],2); //((uint32_t *)&llr128[1])[2];
llr32[7] =simde_mm_extract_epi32(llr128[1],3); //((uint32_t *)&llr128[1])[3]; llr32[7] =simde_mm_extract_epi32(llr128[1],3); //((uint32_t *)&llr128[1])[3];
llr32+=8; llr32 += 8;
} }
simde_mm_empty();
simde_m_empty();
} }
//---------------------------------------------------------------------------------------------- //----------------------------------------------------------------------------------------------
...@@ -149,22 +135,19 @@ void nr_dlsch_16qam_llr(NR_DL_FRAME_PARMS *frame_parms, ...@@ -149,22 +135,19 @@ void nr_dlsch_16qam_llr(NR_DL_FRAME_PARMS *frame_parms,
//---------------------------------------------------------------------------------------------- //----------------------------------------------------------------------------------------------
void nr_dlsch_64qam_llr(NR_DL_FRAME_PARMS *frame_parms, void nr_dlsch_64qam_llr(NR_DL_FRAME_PARMS *frame_parms,
int32_t *rxdataF_comp, c16_t *rxdataF_comp,
int16_t *dlsch_llr, int16_t *dlsch_llr,
int32_t *dl_ch_mag, c16_t *dl_ch_mag,
int32_t *dl_ch_magb, c16_t *dl_ch_magb,
uint8_t symbol, uint8_t symbol,
uint32_t len, uint32_t len,
uint8_t first_symbol_flag, uint8_t first_symbol_flag,
uint16_t nb_rb) uint16_t nb_rb)
{ {
simde__m128i *rxF = (simde__m128i*)&rxdataF_comp[(symbol*nb_rb*12)]; simde__m128i *rxF = (simde__m128i*)&rxdataF_comp[(symbol*nb_rb*12)];
simde__m128i *ch_mag,*ch_magb; simde__m128i *ch_mag, *ch_magb;
int i,len2;
unsigned char len_mod4; unsigned char len_mod4;
int16_t *llr2; int16_t *llr2 = dlsch_llr;
llr2 = dlsch_llr;
ch_mag = (simde__m128i *)dl_ch_mag; ch_mag = (simde__m128i *)dl_ch_mag;
ch_magb = (simde__m128i *)dl_ch_magb; ch_magb = (simde__m128i *)dl_ch_magb;
...@@ -179,11 +162,11 @@ void nr_dlsch_64qam_llr(NR_DL_FRAME_PARMS *frame_parms, ...@@ -179,11 +162,11 @@ void nr_dlsch_64qam_llr(NR_DL_FRAME_PARMS *frame_parms,
pllr_symbol);*/ pllr_symbol);*/
len_mod4 =len&3; len_mod4 =len&3;
len2=len>>2; // length in quad words (4 REs) int len2 = len >> 2; // length in quad words (4 REs)
len2+=((len_mod4==0)?0:1); len2+=((len_mod4==0)?0:1);
for (i=0; i<len2; i++) { for (int i = 0; i < len2; i++) {
simde__m128i xmm1, xmm2; simde__m128i xmm1, xmm2;
xmm1 =simde_mm_abs_epi16(rxF[i]); xmm1 =simde_mm_abs_epi16(rxF[i]);
xmm1 =simde_mm_subs_epi16(ch_mag[i],xmm1); xmm1 =simde_mm_subs_epi16(ch_mag[i],xmm1);
xmm2 =simde_mm_abs_epi16(xmm1); xmm2 =simde_mm_abs_epi16(xmm1);
...@@ -231,12 +214,8 @@ void nr_dlsch_64qam_llr(NR_DL_FRAME_PARMS *frame_parms, ...@@ -231,12 +214,8 @@ void nr_dlsch_64qam_llr(NR_DL_FRAME_PARMS *frame_parms,
llr2[3] =simde_mm_extract_epi16(xmm1,7);//((short *)&xmm1)[j+1]; llr2[3] =simde_mm_extract_epi16(xmm1,7);//((short *)&xmm1)[j+1];
llr2[4] =simde_mm_extract_epi16(xmm2,6);//((short *)&xmm2)[j]; llr2[4] =simde_mm_extract_epi16(xmm2,6);//((short *)&xmm2)[j];
llr2[5] =simde_mm_extract_epi16(xmm2,7);//((short *)&xmm2)[j+1]; llr2[5] =simde_mm_extract_epi16(xmm2,7);//((short *)&xmm2)[j+1];
llr2+=6; llr2 += 6;
} }
simde_mm_empty();
simde_m_empty();
} }
//---------------------------------------------------------------------------------------------- //----------------------------------------------------------------------------------------------
...@@ -244,20 +223,19 @@ void nr_dlsch_64qam_llr(NR_DL_FRAME_PARMS *frame_parms, ...@@ -244,20 +223,19 @@ void nr_dlsch_64qam_llr(NR_DL_FRAME_PARMS *frame_parms,
//---------------------------------------------------------------------------------------------- //----------------------------------------------------------------------------------------------
void nr_dlsch_256qam_llr(NR_DL_FRAME_PARMS *frame_parms, void nr_dlsch_256qam_llr(NR_DL_FRAME_PARMS *frame_parms,
int32_t *rxdataF_comp, c16_t *rxdataF_comp,
int16_t *dlsch_llr, int16_t *dlsch_llr,
int32_t *dl_ch_mag, c16_t *dl_ch_mag,
int32_t *dl_ch_magb, c16_t *dl_ch_magb,
int32_t *dl_ch_magr, c16_t *dl_ch_magr,
uint8_t symbol, uint8_t symbol,
uint32_t len, uint32_t len,
uint8_t first_symbol_flag, uint8_t first_symbol_flag,
uint16_t nb_rb) uint16_t nb_rb)
{ {
simde__m128i *rxF = (simde__m128i*)&rxdataF_comp[(symbol*nb_rb*12)]; simde__m128i *rxF = (simde__m128i*)&rxdataF_comp[(symbol*nb_rb*12)];
simde__m128i *ch_mag,*ch_magb,*ch_magr; simde__m128i *ch_mag,*ch_magb,*ch_magr;
int i,len2;
unsigned char len_mod4; unsigned char len_mod4;
int16_t *llr2; int16_t *llr2;
...@@ -268,10 +246,10 @@ void nr_dlsch_256qam_llr(NR_DL_FRAME_PARMS *frame_parms, ...@@ -268,10 +246,10 @@ void nr_dlsch_256qam_llr(NR_DL_FRAME_PARMS *frame_parms,
ch_magr = (simde__m128i *)dl_ch_magr; ch_magr = (simde__m128i *)dl_ch_magr;
len_mod4 =len&3; len_mod4 =len&3;
len2=len>>2; // length in quad words (4 REs) int len2 = len >> 2; // length in quad words (4 REs)
len2+=((len_mod4==0)?0:1); len2+=((len_mod4==0)?0:1);
for (i=0; i<len2; i++) { for (int i = 0; i < len2; i++) {
simde__m128i xmm1 = simde_mm_abs_epi16(rxF[i]); simde__m128i xmm1 = simde_mm_abs_epi16(rxF[i]);
xmm1 = simde_mm_subs_epi16(ch_mag[i],xmm1); xmm1 = simde_mm_subs_epi16(ch_mag[i],xmm1);
simde__m128i xmm2 = simde_mm_abs_epi16(xmm1); simde__m128i xmm2 = simde_mm_abs_epi16(xmm1);
...@@ -317,12 +295,8 @@ void nr_dlsch_256qam_llr(NR_DL_FRAME_PARMS *frame_parms, ...@@ -317,12 +295,8 @@ void nr_dlsch_256qam_llr(NR_DL_FRAME_PARMS *frame_parms,
llr2[5] = simde_mm_extract_epi16(xmm2,7);//((short *)&xmm2)[j+1]; llr2[5] = simde_mm_extract_epi16(xmm2,7);//((short *)&xmm2)[j+1];
llr2[6] = simde_mm_extract_epi16(xmm3,6); llr2[6] = simde_mm_extract_epi16(xmm3,6);
llr2[7] = simde_mm_extract_epi16(xmm3,7); llr2[7] = simde_mm_extract_epi16(xmm3,7);
llr2+=8; llr2 += 8;
} }
simde_mm_empty();
simde_m_empty();
} }
//============================================================================================== //==============================================================================================
...@@ -332,23 +306,6 @@ void nr_dlsch_256qam_llr(NR_DL_FRAME_PARMS *frame_parms, ...@@ -332,23 +306,6 @@ void nr_dlsch_256qam_llr(NR_DL_FRAME_PARMS *frame_parms,
//---------------------------------------------------------------------------------------------- //----------------------------------------------------------------------------------------------
// QPSK // QPSK
//---------------------------------------------------------------------------------------------- //----------------------------------------------------------------------------------------------
simde__m128i y0r_over2 __attribute__ ((aligned(16)));
simde__m128i y0i_over2 __attribute__ ((aligned(16)));
simde__m128i y1r_over2 __attribute__ ((aligned(16)));
simde__m128i y1i_over2 __attribute__ ((aligned(16)));
simde__m128i A __attribute__ ((aligned(16)));
simde__m128i B __attribute__ ((aligned(16)));
simde__m128i C __attribute__ ((aligned(16)));
simde__m128i D __attribute__ ((aligned(16)));
simde__m128i E __attribute__ ((aligned(16)));
simde__m128i F __attribute__ ((aligned(16)));
simde__m128i G __attribute__ ((aligned(16)));
simde__m128i H __attribute__ ((aligned(16)));
void nr_qpsk_qpsk(short *stream0_in, void nr_qpsk_qpsk(short *stream0_in,
short *stream1_in, short *stream1_in,
short *stream0_out, short *stream0_out,
...@@ -373,11 +330,7 @@ void nr_qpsk_qpsk(short *stream0_in, ...@@ -373,11 +330,7 @@ void nr_qpsk_qpsk(short *stream0_in,
simde__m128i *stream1_128i_in = (simde__m128i *)stream1_in; simde__m128i *stream1_128i_in = (simde__m128i *)stream1_in;
simde__m128i *stream0_128i_out = (simde__m128i *)stream0_out; simde__m128i *stream0_128i_out = (simde__m128i *)stream0_out;
simde__m128i ONE_OVER_SQRT_8 =simde_mm_set1_epi16(23170); //round(2^16/sqrt(8)) simde__m128i ONE_OVER_SQRT_8 =simde_mm_set1_epi16(23170); //round(2^16/sqrt(8))
for (int i = 0; i < length >> 2; i += 2) {
int i;
for (i=0; i<length>>2; i+=2) {
// in each iteration, we take 8 complex samples // in each iteration, we take 8 complex samples
simde__m128i xmm0 = rho01_128i[i]; // 4 symbols simde__m128i xmm0 = rho01_128i[i]; // 4 symbols
simde__m128i xmm1 = rho01_128i[i+1]; simde__m128i xmm1 = rho01_128i[i+1];
...@@ -444,35 +397,35 @@ void nr_qpsk_qpsk(short *stream0_in, ...@@ -444,35 +397,35 @@ void nr_qpsk_qpsk(short *stream0_in,
// 1 term for numerator of LLR // 1 term for numerator of LLR
xmm3 =simde_mm_subs_epi16(y1r_over2,rho_rpi); xmm3 =simde_mm_subs_epi16(y1r_over2,rho_rpi);
A =simde_mm_abs_epi16(xmm3); // A = |y1r/2 - rho/sqrt(8)| simde__m128i A = simde_mm_abs_epi16(xmm3); // A = |y1r/2 - rho/sqrt(8)|
xmm2 =simde_mm_adds_epi16(A,y0i_over2); // = |y1r/2 - rho/sqrt(8)| + y0i/2 xmm2 =simde_mm_adds_epi16(A,y0i_over2); // = |y1r/2 - rho/sqrt(8)| + y0i/2
xmm3 =simde_mm_subs_epi16(y1i_over2,rho_rmi); xmm3 =simde_mm_subs_epi16(y1i_over2,rho_rmi);
B =simde_mm_abs_epi16(xmm3); // B = |y1i/2 - rho*/sqrt(8)| simde__m128i B = simde_mm_abs_epi16(xmm3); // B = |y1i/2 - rho*/sqrt(8)|
simde__m128i logmax_num_re0 =simde_mm_adds_epi16(B,xmm2); // = |y1r/2 - rho/sqrt(8)|+|y1i/2 - rho*/sqrt(8)| + y0i/2 simde__m128i logmax_num_re0 =simde_mm_adds_epi16(B,xmm2); // = |y1r/2 - rho/sqrt(8)|+|y1i/2 - rho*/sqrt(8)| + y0i/2
// 2 term for numerator of LLR // 2 term for numerator of LLR
xmm3 =simde_mm_subs_epi16(y1r_over2,rho_rmi); xmm3 =simde_mm_subs_epi16(y1r_over2,rho_rmi);
C =simde_mm_abs_epi16(xmm3); // C = |y1r/2 - rho*/4| simde__m128i C = simde_mm_abs_epi16(xmm3); // C = |y1r/2 - rho*/4|
xmm2 =simde_mm_subs_epi16(C,y0i_over2); // = |y1r/2 - rho*/4| - y0i/2 xmm2 =simde_mm_subs_epi16(C,y0i_over2); // = |y1r/2 - rho*/4| - y0i/2
xmm3 =simde_mm_adds_epi16(y1i_over2,rho_rpi); xmm3 =simde_mm_adds_epi16(y1i_over2,rho_rpi);
D =simde_mm_abs_epi16(xmm3); // D = |y1i/2 + rho/4| simde__m128i D = simde_mm_abs_epi16(xmm3); // D = |y1i/2 + rho/4|
xmm2 =simde_mm_adds_epi16(xmm2,D); // |y1r/2 - rho*/4| + |y1i/2 + rho/4| - y0i/2 xmm2 =simde_mm_adds_epi16(xmm2,D); // |y1r/2 - rho*/4| + |y1i/2 + rho/4| - y0i/2
logmax_num_re0 =simde_mm_max_epi16(logmax_num_re0,xmm2); // max, numerator done logmax_num_re0 =simde_mm_max_epi16(logmax_num_re0,xmm2); // max, numerator done
// 1 term for denominator of LLR // 1 term for denominator of LLR
xmm3 =simde_mm_adds_epi16(y1r_over2,rho_rmi); xmm3 =simde_mm_adds_epi16(y1r_over2,rho_rmi);
E =simde_mm_abs_epi16(xmm3); // E = |y1r/2 + rho*/4| simde__m128i E = simde_mm_abs_epi16(xmm3); // E = |y1r/2 + rho*/4|
xmm2 =simde_mm_adds_epi16(E,y0i_over2); // = |y1r/2 + rho*/4| + y0i/2 xmm2 =simde_mm_adds_epi16(E,y0i_over2); // = |y1r/2 + rho*/4| + y0i/2
xmm3 =simde_mm_subs_epi16(y1i_over2,rho_rpi); xmm3 =simde_mm_subs_epi16(y1i_over2,rho_rpi);
F =simde_mm_abs_epi16(xmm3); // F = |y1i/2 - rho/4| simde__m128i F = simde_mm_abs_epi16(xmm3); // F = |y1i/2 - rho/4|
simde__m128i logmax_den_re0 =simde_mm_adds_epi16(F,xmm2); // = |y1r/2 + rho*/4| + |y1i/2 - rho/4| + y0i/2 simde__m128i logmax_den_re0 =simde_mm_adds_epi16(F,xmm2); // = |y1r/2 + rho*/4| + |y1i/2 - rho/4| + y0i/2
// 2 term for denominator of LLR // 2 term for denominator of LLR
xmm3 =simde_mm_adds_epi16(y1r_over2,rho_rpi); xmm3 =simde_mm_adds_epi16(y1r_over2,rho_rpi);
G =simde_mm_abs_epi16(xmm3); // G = |y1r/2 + rho/4| simde__m128i G = simde_mm_abs_epi16(xmm3); // G = |y1r/2 + rho/4|
xmm2 =simde_mm_subs_epi16(G,y0i_over2); // = |y1r/2 + rho/4| - y0i/2 xmm2 =simde_mm_subs_epi16(G,y0i_over2); // = |y1r/2 + rho/4| - y0i/2
xmm3 =simde_mm_adds_epi16(y1i_over2,rho_rmi); xmm3 =simde_mm_adds_epi16(y1i_over2,rho_rmi);
H =simde_mm_abs_epi16(xmm3); // H = |y1i/2 + rho*/4| simde__m128i H = simde_mm_abs_epi16(xmm3); // H = |y1i/2 + rho*/4|
xmm2 =simde_mm_adds_epi16(xmm2,H); // = |y1r/2 + rho/4| + |y1i/2 + rho*/4| - y0i/2 xmm2 =simde_mm_adds_epi16(xmm2,H); // = |y1r/2 + rho/4| + |y1i/2 + rho*/4| - y0i/2
logmax_den_re0 =simde_mm_max_epi16(logmax_den_re0,xmm2); // max, denominator done logmax_den_re0 =simde_mm_max_epi16(logmax_den_re0,xmm2); // max, denominator done
...@@ -508,8 +461,6 @@ void nr_qpsk_qpsk(short *stream0_in, ...@@ -508,8 +461,6 @@ void nr_qpsk_qpsk(short *stream0_in,
simde_mm_storeu_si128(&stream0_128i_out[i],simde_mm_unpacklo_epi16(y0r,y0i)); // = [L1(1), L2(1), L1(2), L2(2)] simde_mm_storeu_si128(&stream0_128i_out[i],simde_mm_unpacklo_epi16(y0r,y0i)); // = [L1(1), L2(1), L1(2), L2(2)]
if (i<((length>>1) - 1)) // false if only 2 REs remain if (i<((length>>1) - 1)) // false if only 2 REs remain
simde_mm_storeu_si128(&stream0_128i_out[i+1],simde_mm_unpackhi_epi16(y0r,y0i)); simde_mm_storeu_si128(&stream0_128i_out[i + 1], simde_mm_unpackhi_epi16(y0r, y0i));
} }
} }
...@@ -98,12 +98,12 @@ int32_t nr_dlsch_qpsk_qpsk_llr(NR_DL_FRAME_PARMS *frame_parms, ...@@ -98,12 +98,12 @@ int32_t nr_dlsch_qpsk_qpsk_llr(NR_DL_FRAME_PARMS *frame_parms,
@param nb_rb number of RBs for this allocation @param nb_rb number of RBs for this allocation
*/ */
int32_t nr_dlsch_qpsk_llr(NR_DL_FRAME_PARMS *frame_parms, int32_t nr_dlsch_qpsk_llr(NR_DL_FRAME_PARMS *frame_parms,
int32_t *rxdataF_comp, c16_t *rxdataF_comp,
int16_t *dlsch_llr, int16_t *dlsch_llr,
uint8_t symbol, uint8_t symbol,
uint32_t len, uint32_t len,
uint8_t first_symbol_flag, uint8_t first_symbol_flag,
uint16_t nb_rb); uint16_t nb_rb);
/** /**
\brief This function generates log-likelihood ratios (decoder input) for single-stream 16QAM received waveforms \brief This function generates log-likelihood ratios (decoder input) for single-stream 16QAM received waveforms
...@@ -119,13 +119,13 @@ int32_t nr_dlsch_qpsk_llr(NR_DL_FRAME_PARMS *frame_parms, ...@@ -119,13 +119,13 @@ int32_t nr_dlsch_qpsk_llr(NR_DL_FRAME_PARMS *frame_parms,
*/ */
void nr_dlsch_16qam_llr(NR_DL_FRAME_PARMS *frame_parms, void nr_dlsch_16qam_llr(NR_DL_FRAME_PARMS *frame_parms,
int32_t *rxdataF_comp, c16_t *rxdataF_comp,
int16_t *dlsch_llr, int16_t *dlsch_llr,
int32_t *dl_ch_mag, c16_t *dl_ch_mag,
uint8_t symbol, uint8_t symbol,
uint32_t len, uint32_t len,
uint8_t first_symbol_flag, uint8_t first_symbol_flag,
uint16_t nb_rb); uint16_t nb_rb);
/** /**
\brief This function generates log-likelihood ratios (decoder input) for single-stream 16QAM received waveforms \brief This function generates log-likelihood ratios (decoder input) for single-stream 16QAM received waveforms
@param frame_parms Frame descriptor structure @param frame_parms Frame descriptor structure
...@@ -142,25 +142,25 @@ void nr_dlsch_16qam_llr(NR_DL_FRAME_PARMS *frame_parms, ...@@ -142,25 +142,25 @@ void nr_dlsch_16qam_llr(NR_DL_FRAME_PARMS *frame_parms,
*/ */
void nr_dlsch_64qam_llr(NR_DL_FRAME_PARMS *frame_parms, void nr_dlsch_64qam_llr(NR_DL_FRAME_PARMS *frame_parms,
int32_t *rxdataF_comp, c16_t *rxdataF_comp,
int16_t *dlsch_llr, int16_t *dlsch_llr,
int32_t *dl_ch_mag, c16_t *dl_ch_mag,
int32_t *dl_ch_magb, c16_t *dl_ch_magb,
uint8_t symbol, uint8_t symbol,
uint32_t len, uint32_t len,
uint8_t first_symbol_flag, uint8_t first_symbol_flag,
uint16_t nb_rb); uint16_t nb_rb);
void nr_dlsch_256qam_llr(NR_DL_FRAME_PARMS *frame_parms, void nr_dlsch_256qam_llr(NR_DL_FRAME_PARMS *frame_parms,
int32_t *rxdataF_comp, c16_t *rxdataF_comp,
int16_t *dlsch_llr, int16_t *dlsch_llr,
int32_t *dl_ch_mag, c16_t *dl_ch_mag,
int32_t *dl_ch_magb, c16_t *dl_ch_magb,
int32_t *dl_ch_magr, c16_t *dl_ch_magr,
uint8_t symbol, uint8_t symbol,
uint32_t len, uint32_t len,
uint8_t first_symbol_flag, uint8_t first_symbol_flag,
uint16_t nb_rb); uint16_t nb_rb);
void nr_dlsch_deinterleaving(uint8_t symbol, void nr_dlsch_deinterleaving(uint8_t symbol,
uint8_t start_symbol, uint8_t start_symbol,
...@@ -169,11 +169,7 @@ void nr_dlsch_deinterleaving(uint8_t symbol, ...@@ -169,11 +169,7 @@ void nr_dlsch_deinterleaving(uint8_t symbol,
uint16_t *llr_deint, uint16_t *llr_deint,
uint16_t nb_rb_pdsch); uint16_t nb_rb_pdsch);
void nr_conjch0_mult_ch1(int *ch0, void nr_conjch0_mult_ch1(c16_t *ch0, c16_t *ch1, c16_t *ch0conj_ch1, unsigned short nb_rb, unsigned char output_shift0);
int *ch1,
int32_t *ch0conj_ch1,
unsigned short nb_rb,
unsigned char output_shift0);
/** \brief This is the top-level entry point for DLSCH decoding in UE. It should be replicated on several /** \brief This is the top-level entry point for DLSCH decoding in UE. It should be replicated on several
threads (on multi-core machines) corresponding to different HARQ processes. The routine first threads (on multi-core machines) corresponding to different HARQ processes. The routine first
...@@ -409,7 +405,7 @@ int nr_rx_pdsch(PHY_VARS_NR_UE *ue, ...@@ -409,7 +405,7 @@ int nr_rx_pdsch(PHY_VARS_NR_UE *ue,
bool first_symbol_flag, bool first_symbol_flag,
unsigned char harq_pid, unsigned char harq_pid,
uint32_t pdsch_est_size, uint32_t pdsch_est_size,
int32_t dl_ch_estimates[][pdsch_est_size], c16_t dl_ch_estimates[][pdsch_est_size],
int16_t *llr[2], int16_t *llr[2],
uint32_t dl_valid_re[NR_SYMBOLS_PER_SLOT], uint32_t dl_valid_re[NR_SYMBOLS_PER_SLOT],
c16_t rxdataF[][ue->frame_parms.samples_per_slot_wCP], c16_t rxdataF[][ue->frame_parms.samples_per_slot_wCP],
...@@ -417,7 +413,7 @@ int nr_rx_pdsch(PHY_VARS_NR_UE *ue, ...@@ -417,7 +413,7 @@ int nr_rx_pdsch(PHY_VARS_NR_UE *ue,
int32_t *log2_maxh, int32_t *log2_maxh,
int rx_size_symbol, int rx_size_symbol,
int nbRx, int nbRx,
int32_t rxdataF_comp[][nbRx][rx_size_symbol * NR_SYMBOLS_PER_SLOT], c16_t rxdataF_comp[][nbRx][rx_size_symbol * NR_SYMBOLS_PER_SLOT],
c16_t ptrs_phase_per_slot[][NR_SYMBOLS_PER_SLOT], c16_t ptrs_phase_per_slot[][NR_SYMBOLS_PER_SLOT],
int32_t ptrs_re_per_slot[][NR_SYMBOLS_PER_SLOT], int32_t ptrs_re_per_slot[][NR_SYMBOLS_PER_SLOT],
int G, int G,
......
...@@ -123,7 +123,7 @@ typedef struct { ...@@ -123,7 +123,7 @@ typedef struct {
typedef struct { typedef struct {
uint8_t csi_rs_generated_signal_bits; uint8_t csi_rs_generated_signal_bits;
int32_t **csi_rs_generated_signal; c16_t **csi_rs_generated_signal;
bool csi_im_meas_computed; bool csi_im_meas_computed;
uint32_t interference_plus_noise_power; uint32_t interference_plus_noise_power;
} nr_csi_info_t; } nr_csi_info_t;
......
...@@ -220,7 +220,7 @@ void phy_procedures_gNB_TX(processingData_L1tx_t *msgTx, ...@@ -220,7 +220,7 @@ void phy_procedures_gNB_TX(processingData_L1tx_t *msgTx,
LOG_D(PHY, "CSI-RS generation started in frame %d.%d\n",frame,slot); LOG_D(PHY, "CSI-RS generation started in frame %d.%d\n",frame,slot);
nfapi_nr_dl_tti_csi_rs_pdu_rel15_t *csi_params = &csirs->csirs_pdu.csi_rs_pdu_rel15; nfapi_nr_dl_tti_csi_rs_pdu_rel15_t *csi_params = &csirs->csirs_pdu.csi_rs_pdu_rel15;
nr_generate_csi_rs(&gNB->frame_parms, nr_generate_csi_rs(&gNB->frame_parms,
(int32_t **)gNB->common_vars.txdataF, gNB->common_vars.txdataF,
gNB->TX_AMP, gNB->TX_AMP,
gNB->nr_csi_info, gNB->nr_csi_info,
csi_params, csi_params,
......
...@@ -303,7 +303,7 @@ void nr_ue_measurement_procedures(uint16_t l, ...@@ -303,7 +303,7 @@ void nr_ue_measurement_procedures(uint16_t l,
const UE_nr_rxtx_proc_t *proc, const UE_nr_rxtx_proc_t *proc,
NR_UE_DLSCH_t *dlsch, NR_UE_DLSCH_t *dlsch,
uint32_t pdsch_est_size, uint32_t pdsch_est_size,
int32_t dl_ch_estimates[][pdsch_est_size]) c16_t dl_ch_estimates[][pdsch_est_size])
{ {
NR_DL_FRAME_PARMS *frame_parms=&ue->frame_parms; NR_DL_FRAME_PARMS *frame_parms=&ue->frame_parms;
int nr_slot_rx = proc->nr_slot_rx; int nr_slot_rx = proc->nr_slot_rx;
...@@ -357,7 +357,7 @@ void nr_ue_measurement_procedures(uint16_t l, ...@@ -357,7 +357,7 @@ void nr_ue_measurement_procedures(uint16_t l,
static int nr_ue_pbch_procedures(PHY_VARS_NR_UE *ue, static int nr_ue_pbch_procedures(PHY_VARS_NR_UE *ue,
const UE_nr_rxtx_proc_t *proc, const UE_nr_rxtx_proc_t *proc,
int estimateSz, int estimateSz,
struct complex16 dl_ch_estimates[][estimateSz], c16_t dl_ch_estimates[][estimateSz],
c16_t rxdataF[][ue->frame_parms.samples_per_slot_wCP]) c16_t rxdataF[][ue->frame_parms.samples_per_slot_wCP])
{ {
int ret = 0; int ret = 0;
...@@ -507,8 +507,8 @@ static int nr_ue_pdsch_procedures(PHY_VARS_NR_UE *ue, ...@@ -507,8 +507,8 @@ static int nr_ue_pdsch_procedures(PHY_VARS_NR_UE *ue,
dlsch0->Nl); dlsch0->Nl);
const uint32_t pdsch_est_size = ((ue->frame_parms.symbols_per_slot * ue->frame_parms.ofdm_symbol_size + 15) / 16) * 16; const uint32_t pdsch_est_size = ((ue->frame_parms.symbols_per_slot * ue->frame_parms.ofdm_symbol_size + 15) / 16) * 16;
__attribute__((aligned(32))) int32_t pdsch_dl_ch_estimates[ue->frame_parms.nb_antennas_rx * dlsch0->Nl][pdsch_est_size]; __attribute__((aligned(32))) c16_t pdsch_dl_ch_estimates[ue->frame_parms.nb_antennas_rx * dlsch0->Nl][pdsch_est_size];
memset(pdsch_dl_ch_estimates, 0, sizeof(int32_t) * ue->frame_parms.nb_antennas_rx * dlsch0->Nl * pdsch_est_size); memset(pdsch_dl_ch_estimates, 0, sizeof(pdsch_dl_ch_estimates));
c16_t ptrs_phase_per_slot[ue->frame_parms.nb_antennas_rx][NR_SYMBOLS_PER_SLOT]; c16_t ptrs_phase_per_slot[ue->frame_parms.nb_antennas_rx][NR_SYMBOLS_PER_SLOT];
memset(ptrs_phase_per_slot, 0, sizeof(ptrs_phase_per_slot)); memset(ptrs_phase_per_slot, 0, sizeof(ptrs_phase_per_slot));
...@@ -517,7 +517,8 @@ static int nr_ue_pdsch_procedures(PHY_VARS_NR_UE *ue, ...@@ -517,7 +517,8 @@ static int nr_ue_pdsch_procedures(PHY_VARS_NR_UE *ue,
memset(ptrs_re_per_slot, 0, sizeof(ptrs_re_per_slot)); memset(ptrs_re_per_slot, 0, sizeof(ptrs_re_per_slot));
const uint32_t rx_size_symbol = dlsch[0].dlsch_config.number_rbs * NR_NB_SC_PER_RB; const uint32_t rx_size_symbol = dlsch[0].dlsch_config.number_rbs * NR_NB_SC_PER_RB;
__attribute__((aligned(32))) int32_t rxdataF_comp[dlsch[0].Nl][ue->frame_parms.nb_antennas_rx][rx_size_symbol * NR_SYMBOLS_PER_SLOT]; __attribute__((
aligned(32))) c16_t rxdataF_comp[dlsch[0].Nl][ue->frame_parms.nb_antennas_rx][rx_size_symbol * NR_SYMBOLS_PER_SLOT];
memset(rxdataF_comp, 0, sizeof(rxdataF_comp)); memset(rxdataF_comp, 0, sizeof(rxdataF_comp));
uint32_t nvar = 0; uint32_t nvar = 0;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment