mirror of https://github.com/PentHertz/srsLTE.git
commit
3adc6b5cbc
|
@ -493,6 +493,7 @@ typedef struct {
|
|||
bool rssi_sensor_enabled;
|
||||
bool sic_pss_enabled;
|
||||
float rx_gain_offset;
|
||||
bool pdsch_csi_enabled;
|
||||
} phy_args_t;
|
||||
|
||||
|
||||
|
|
|
@ -42,6 +42,9 @@
|
|||
typedef struct SRSLTE_API {
|
||||
uint32_t max_cb;
|
||||
int16_t **buffer_f;
|
||||
uint8_t **data;
|
||||
bool *cb_crc;
|
||||
bool tb_crc;
|
||||
} srslte_softbuffer_rx_t;
|
||||
|
||||
typedef struct SRSLTE_API {
|
||||
|
|
|
@ -79,6 +79,7 @@ SRSLTE_API int srslte_precoding_type(cf_t *x[SRSLTE_MAX_LAYERS],
|
|||
SRSLTE_API int srslte_predecoding_single(cf_t *y,
|
||||
cf_t *h,
|
||||
cf_t *x,
|
||||
float *csi,
|
||||
int nof_symbols,
|
||||
float scaling,
|
||||
float noise_estimate);
|
||||
|
@ -86,6 +87,7 @@ SRSLTE_API int srslte_predecoding_single(cf_t *y,
|
|||
SRSLTE_API int srslte_predecoding_single_multi(cf_t *y[SRSLTE_MAX_PORTS],
|
||||
cf_t *h[SRSLTE_MAX_PORTS],
|
||||
cf_t *x,
|
||||
float *csi,
|
||||
int nof_rxant,
|
||||
int nof_symbols,
|
||||
float scaling,
|
||||
|
@ -111,6 +113,7 @@ SRSLTE_API void srslte_predecoding_set_mimo_decoder (srslte_mimo_decoder_t _mimo
|
|||
SRSLTE_API int srslte_predecoding_type(cf_t *y[SRSLTE_MAX_PORTS],
|
||||
cf_t *h[SRSLTE_MAX_PORTS][SRSLTE_MAX_PORTS],
|
||||
cf_t *x[SRSLTE_MAX_LAYERS],
|
||||
float *csi,
|
||||
int nof_rxant,
|
||||
int nof_ports,
|
||||
int nof_layers,
|
||||
|
|
|
@ -76,6 +76,9 @@ typedef struct SRSLTE_API {
|
|||
cf_t *d[SRSLTE_MAX_CODEWORDS]; /* Modulated/Demodulated codewords */
|
||||
void *e[SRSLTE_MAX_CODEWORDS];
|
||||
|
||||
bool csi_enabled;
|
||||
float *csi[SRSLTE_MAX_CODEWORDS]; /* Channel Strengh Indicator */
|
||||
|
||||
/* tx & rx objects */
|
||||
srslte_modem_table_t mod[4];
|
||||
|
||||
|
@ -107,6 +110,9 @@ SRSLTE_API int srslte_pdsch_set_rnti(srslte_pdsch_t *q,
|
|||
SRSLTE_API void srslte_pdsch_set_power_allocation(srslte_pdsch_t *q,
|
||||
float rho_a);
|
||||
|
||||
SRSLTE_API int srslte_pdsch_enable_csi(srslte_pdsch_t *q,
|
||||
bool enable);
|
||||
|
||||
SRSLTE_API void srslte_pdsch_free_rnti(srslte_pdsch_t *q,
|
||||
uint16_t rnti);
|
||||
|
||||
|
|
|
@ -530,7 +530,7 @@ static inline simd_cf_t srslte_simd_cfi_loadu(const cf_t *ptr) {
|
|||
0x11, 0x13, 0x15, 0x17,
|
||||
0x19, 0x1B, 0x1D, 0x1F), in2);
|
||||
#else /* LV_HAVE_AVX512 */
|
||||
#ifdef LV_HAVE_AVX2
|
||||
#ifdef LV_HAVE_AVX2
|
||||
__m256 in1 = _mm256_permute_ps(_mm256_loadu_ps((float*)(ptr)), 0b11011000);
|
||||
__m256 in2 = _mm256_permute_ps(_mm256_loadu_ps((float*)(ptr + 4)), 0b11011000);
|
||||
ret.re = _mm256_unpacklo_ps(in1, in2);
|
||||
|
@ -705,6 +705,18 @@ static inline void srslte_simd_cf_storeu(float *re, float *im, simd_cf_t simdreg
|
|||
#endif /* LV_HAVE_AVX512 */
|
||||
}
|
||||
|
||||
static inline simd_f_t srslte_simd_cf_re(simd_cf_t in) {
|
||||
simd_f_t out = in.re;
|
||||
#ifndef LV_HAVE_AVX512
|
||||
#ifdef LV_HAVE_AVX2
|
||||
/* Permute for AVX registers (mis SSE registers) */
|
||||
const __m256i idx = _mm256_setr_epi32(0, 2, 4, 6, 1, 3, 5, 7);
|
||||
out = _mm256_permutevar8x32_ps(out, idx);
|
||||
#endif /* LV_HAVE_AVX2 */
|
||||
#endif /* LV_HAVE_AVX512 */
|
||||
return out;
|
||||
}
|
||||
|
||||
static inline simd_cf_t srslte_simd_cf_set1 (cf_t x) {
|
||||
simd_cf_t ret;
|
||||
#ifdef LV_HAVE_AVX512
|
||||
|
|
|
@ -173,7 +173,7 @@ int main(int argc, char **argv) {
|
|||
|
||||
gettimeofday(&t[1], NULL);
|
||||
for (int j=0;j<100;j++) {
|
||||
srslte_predecoding_single(input, ce, output, num_re, 1.0f, 0);
|
||||
srslte_predecoding_single(input, ce, output, NULL, num_re, 1.0f, 0);
|
||||
}
|
||||
gettimeofday(&t[2], NULL);
|
||||
get_time_interval(t);
|
||||
|
@ -188,7 +188,7 @@ int main(int argc, char **argv) {
|
|||
|
||||
gettimeofday(&t[1], NULL);
|
||||
for (int j=0;j<100;j++) {
|
||||
srslte_predecoding_single(input, ce, output, num_re, 1.0f, srslte_chest_dl_get_noise_estimate(&est));
|
||||
srslte_predecoding_single(input, ce, output, NULL, num_re, 1.0f, srslte_chest_dl_get_noise_estimate(&est));
|
||||
}
|
||||
gettimeofday(&t[2], NULL);
|
||||
get_time_interval(t);
|
||||
|
|
|
@ -47,32 +47,56 @@ int srslte_softbuffer_rx_init(srslte_softbuffer_rx_t *q, uint32_t nof_prb) {
|
|||
int ret = SRSLTE_ERROR_INVALID_INPUTS;
|
||||
|
||||
if (q != NULL) {
|
||||
ret = SRSLTE_ERROR;
|
||||
|
||||
bzero(q, sizeof(srslte_softbuffer_rx_t));
|
||||
|
||||
ret = srslte_ra_tbs_from_idx(26, nof_prb);
|
||||
if (ret != SRSLTE_ERROR) {
|
||||
q->max_cb = (uint32_t) ret / (SRSLTE_TCOD_MAX_LEN_CB - 24) + 1;
|
||||
ret = SRSLTE_ERROR;
|
||||
|
||||
q->buffer_f = srslte_vec_malloc(sizeof(int16_t*) * q->max_cb);
|
||||
if (!q->buffer_f) {
|
||||
perror("malloc");
|
||||
return SRSLTE_ERROR;
|
||||
goto clean_exit;
|
||||
}
|
||||
|
||||
q->data = srslte_vec_malloc(sizeof(uint8_t*) * q->max_cb);
|
||||
if (!q->data) {
|
||||
perror("malloc");
|
||||
goto clean_exit;
|
||||
}
|
||||
|
||||
q->cb_crc = srslte_vec_malloc(sizeof(bool) * q->max_cb);
|
||||
if (!q->cb_crc) {
|
||||
perror("malloc");
|
||||
goto clean_exit;
|
||||
}
|
||||
bzero(q->cb_crc, sizeof(bool) * q->max_cb);
|
||||
|
||||
// FIXME: Use HARQ buffer limitation based on UE category
|
||||
for (uint32_t i=0;i<q->max_cb;i++) {
|
||||
q->buffer_f[i] = srslte_vec_malloc(sizeof(int16_t) * SOFTBUFFER_SIZE);
|
||||
if (!q->buffer_f[i]) {
|
||||
perror("malloc");
|
||||
return SRSLTE_ERROR;
|
||||
goto clean_exit;
|
||||
}
|
||||
|
||||
q->data[i] = srslte_vec_malloc(sizeof(uint8_t) * 6144/8);
|
||||
if (!q->data[i]) {
|
||||
perror("malloc");
|
||||
goto clean_exit;
|
||||
}
|
||||
}
|
||||
//srslte_softbuffer_rx_reset(q);
|
||||
ret = SRSLTE_SUCCESS;
|
||||
}
|
||||
}
|
||||
|
||||
clean_exit:
|
||||
if (ret != SRSLTE_SUCCESS) {
|
||||
srslte_softbuffer_rx_free(q);
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
@ -86,6 +110,17 @@ void srslte_softbuffer_rx_free(srslte_softbuffer_rx_t *q) {
|
|||
}
|
||||
free(q->buffer_f);
|
||||
}
|
||||
if (q->data) {
|
||||
for (uint32_t i=0;i<q->max_cb;i++) {
|
||||
if (q->data[i]) {
|
||||
free(q->data[i]);
|
||||
}
|
||||
}
|
||||
free(q->data);
|
||||
}
|
||||
if (q->cb_crc) {
|
||||
free(q->cb_crc);
|
||||
}
|
||||
bzero(q, sizeof(srslte_softbuffer_rx_t));
|
||||
}
|
||||
}
|
||||
|
@ -110,6 +145,9 @@ void srslte_softbuffer_rx_reset_cb(srslte_softbuffer_rx_t *q, uint32_t nof_cb) {
|
|||
}
|
||||
}
|
||||
}
|
||||
if (q->cb_crc) {
|
||||
bzero(q->cb_crc, sizeof(bool) * q->max_cb);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -34,6 +34,7 @@
|
|||
#include "srslte/phy/utils/vector.h"
|
||||
#include "srslte/phy/utils/debug.h"
|
||||
#include "srslte/phy/utils/mat.h"
|
||||
#include "srslte/phy/utils/simd.h"
|
||||
|
||||
#ifdef LV_HAVE_SSE
|
||||
#include <immintrin.h>
|
||||
|
@ -252,8 +253,49 @@ int srslte_predecoding_single_gen(cf_t *y[SRSLTE_MAX_PORTS], cf_t *h[SRSLTE_MAX_
|
|||
return nof_symbols;
|
||||
}
|
||||
|
||||
int srslte_predecoding_single_csi(cf_t *y[SRSLTE_MAX_PORTS], cf_t *h[SRSLTE_MAX_PORTS], cf_t *x, float *csi, int nof_rxant, int nof_symbols, float scaling, float noise_estimate) {
|
||||
int i = 0;
|
||||
|
||||
#if SRSLTE_SIMD_CF_SIZE
|
||||
const simd_f_t _noise = srslte_simd_f_set1(noise_estimate);
|
||||
const simd_f_t _scaling = srslte_simd_f_set1(1.0f / scaling);
|
||||
|
||||
for (; i < nof_symbols - SRSLTE_SIMD_CF_SIZE + 1; i += SRSLTE_SIMD_CF_SIZE) {
|
||||
simd_cf_t _r = srslte_simd_cf_zero();
|
||||
simd_f_t _hh = srslte_simd_f_zero();
|
||||
|
||||
for (int p = 0; p < nof_rxant; p++) {
|
||||
simd_cf_t _y = srslte_simd_cfi_load(&y[p][i]);
|
||||
simd_cf_t _h = srslte_simd_cfi_load(&h[p][i]);
|
||||
|
||||
_r = srslte_simd_cf_add(_r, srslte_simd_cf_conjprod(_y, _h));
|
||||
_hh = srslte_simd_f_add(_hh, srslte_simd_cf_re(srslte_simd_cf_conjprod(_h, _h)));
|
||||
}
|
||||
|
||||
simd_f_t _csi = srslte_simd_f_add(_hh, _noise);
|
||||
simd_cf_t _x = srslte_simd_cf_mul(srslte_simd_cf_mul(_r, _scaling), srslte_simd_f_rcp(_csi));
|
||||
|
||||
srslte_simd_f_store(&csi[i], _csi);
|
||||
srslte_simd_cfi_store(&x[i], _x);
|
||||
}
|
||||
#endif
|
||||
|
||||
for (; i < nof_symbols; i++) {
|
||||
cf_t r = 0;
|
||||
float hh = 0;
|
||||
float _scaling = 1.0f / scaling;
|
||||
for (int p = 0; p < nof_rxant; p++) {
|
||||
r += y[p][i] * conj(h[p][i]);
|
||||
hh += (__real__ h[p][i] * __real__ h[p][i]) + (__imag__ h[p][i] * __imag__ h[p][i]);
|
||||
}
|
||||
csi[i] = hh + noise_estimate;
|
||||
x[i] = r * _scaling / csi[i];
|
||||
}
|
||||
return nof_symbols;
|
||||
}
|
||||
|
||||
/* ZF/MMSE SISO equalizer x=y(h'h+no)^(-1)h' (ZF if n0=0.0)*/
|
||||
int srslte_predecoding_single(cf_t *y_, cf_t *h_, cf_t *x, int nof_symbols, float scaling, float noise_estimate) {
|
||||
int srslte_predecoding_single(cf_t *y_, cf_t *h_, cf_t *x, float *csi, int nof_symbols, float scaling, float noise_estimate) {
|
||||
|
||||
cf_t *y[SRSLTE_MAX_PORTS];
|
||||
cf_t *h[SRSLTE_MAX_PORTS];
|
||||
|
@ -261,6 +303,10 @@ int srslte_predecoding_single(cf_t *y_, cf_t *h_, cf_t *x, int nof_symbols, floa
|
|||
h[0] = h_;
|
||||
int nof_rxant = 1;
|
||||
|
||||
if (csi) {
|
||||
return srslte_predecoding_single_csi(y, h, x, csi, nof_rxant, nof_symbols, scaling, noise_estimate);
|
||||
}
|
||||
|
||||
#ifdef LV_HAVE_AVX
|
||||
if (nof_symbols > 32 && nof_rxant <= 2) {
|
||||
return srslte_predecoding_single_avx(y, h, x, nof_rxant, nof_symbols, scaling, noise_estimate);
|
||||
|
@ -281,8 +327,12 @@ int srslte_predecoding_single(cf_t *y_, cf_t *h_, cf_t *x, int nof_symbols, floa
|
|||
}
|
||||
|
||||
/* ZF/MMSE SISO equalizer x=y(h'h+no)^(-1)h' (ZF if n0=0.0)*/
|
||||
int srslte_predecoding_single_multi(cf_t *y[SRSLTE_MAX_PORTS], cf_t *h[SRSLTE_MAX_PORTS], cf_t *x,
|
||||
int srslte_predecoding_single_multi(cf_t *y[SRSLTE_MAX_PORTS], cf_t *h[SRSLTE_MAX_PORTS], cf_t *x, float *csi,
|
||||
int nof_rxant, int nof_symbols, float scaling, float noise_estimate) {
|
||||
if (csi) {
|
||||
return srslte_predecoding_single_csi(y, h, x, csi, nof_rxant, nof_symbols, scaling, noise_estimate);
|
||||
}
|
||||
|
||||
#ifdef LV_HAVE_AVX
|
||||
if (nof_symbols > 32) {
|
||||
return srslte_predecoding_single_avx(y, h, x, nof_rxant, nof_symbols, scaling, noise_estimate);
|
||||
|
@ -1418,7 +1468,7 @@ void srslte_predecoding_set_mimo_decoder (srslte_mimo_decoder_t _mimo_decoder) {
|
|||
|
||||
/* 36.211 v10.3.0 Section 6.3.4 */
|
||||
int srslte_predecoding_type(cf_t *y[SRSLTE_MAX_PORTS], cf_t *h[SRSLTE_MAX_PORTS][SRSLTE_MAX_PORTS],
|
||||
cf_t *x[SRSLTE_MAX_LAYERS], int nof_rxant, int nof_ports, int nof_layers,
|
||||
cf_t *x[SRSLTE_MAX_LAYERS], float *csi, int nof_rxant, int nof_ports, int nof_layers,
|
||||
int codebook_idx, int nof_symbols, srslte_mimo_type_t type, float scaling,
|
||||
float noise_estimate) {
|
||||
|
||||
|
@ -1451,7 +1501,7 @@ int srslte_predecoding_type(cf_t *y[SRSLTE_MAX_PORTS], cf_t *h[SRSLTE_MAX_PORTS]
|
|||
return -1;
|
||||
case SRSLTE_MIMO_TYPE_SINGLE_ANTENNA:
|
||||
if (nof_ports == 1 && nof_layers == 1) {
|
||||
return srslte_predecoding_single_multi(y, h[0], x[0], nof_rxant, nof_symbols, scaling, noise_estimate);
|
||||
return srslte_predecoding_single_multi(y, h[0], x[0], csi, nof_rxant, nof_symbols, scaling, noise_estimate);
|
||||
} else {
|
||||
fprintf(stderr,
|
||||
"Number of ports and layers must be 1 for transmission on single antenna ports (%d, %d)\n", nof_ports, nof_layers);
|
||||
|
|
|
@ -291,7 +291,7 @@ int main(int argc, char **argv) {
|
|||
/* predecoding / equalization */
|
||||
struct timeval t[3];
|
||||
gettimeofday(&t[1], NULL);
|
||||
srslte_predecoding_type(r, h, xr, nof_rx_ports, nof_tx_ports, nof_layers,
|
||||
srslte_predecoding_type(r, h, xr, NULL, nof_rx_ports, nof_tx_ports, nof_layers,
|
||||
codebook_idx, nof_re, type, scaling, powf(10, -snr_db / 10));
|
||||
gettimeofday(&t[2], NULL);
|
||||
get_time_interval(t);
|
||||
|
|
|
@ -497,7 +497,7 @@ int srslte_pbch_decode(srslte_pbch_t *q, cf_t *slot1_symbols, cf_t *ce_slot1[SRS
|
|||
/* in control channels, only diversity is supported */
|
||||
if (nant == 1) {
|
||||
/* no need for layer demapping */
|
||||
srslte_predecoding_single(q->symbols[0], q->ce[0], q->d, q->nof_symbols, 1.0f, noise_estimate);
|
||||
srslte_predecoding_single(q->symbols[0], q->ce[0], q->d, NULL, q->nof_symbols, 1.0f, noise_estimate);
|
||||
} else {
|
||||
srslte_predecoding_diversity(q->symbols[0], q->ce, x, nant,
|
||||
q->nof_symbols, 1.0f);
|
||||
|
|
|
@ -219,7 +219,7 @@ int srslte_pcfich_decode_multi(srslte_pcfich_t *q, cf_t *sf_symbols[SRSLTE_MAX_P
|
|||
/* in control channels, only diversity is supported */
|
||||
if (q->cell.nof_ports == 1) {
|
||||
/* no need for layer demapping */
|
||||
srslte_predecoding_single_multi(q_symbols, q_ce[0], q->d, q->nof_rx_antennas, q->nof_symbols, 1.0f, noise_estimate);
|
||||
srslte_predecoding_single_multi(q_symbols, q_ce[0], q->d, NULL, q->nof_rx_antennas, q->nof_symbols, 1.0f, noise_estimate);
|
||||
} else {
|
||||
srslte_predecoding_diversity_multi(q_symbols, q_ce, x, q->nof_rx_antennas, q->cell.nof_ports, q->nof_symbols, 1.0f);
|
||||
srslte_layerdemap_diversity(x, q->d, q->cell.nof_ports, q->nof_symbols / q->cell.nof_ports);
|
||||
|
|
|
@ -490,7 +490,7 @@ int srslte_pdcch_extract_llr_multi(srslte_pdcch_t *q, cf_t *sf_symbols[SRSLTE_MA
|
|||
/* in control channels, only diversity is supported */
|
||||
if (q->cell.nof_ports == 1) {
|
||||
/* no need for layer demapping */
|
||||
srslte_predecoding_single_multi(q->symbols, q->ce[0], q->d, q->nof_rx_antennas, nof_symbols, 1.0f, noise_estimate/2);
|
||||
srslte_predecoding_single_multi(q->symbols, q->ce[0], q->d, NULL, q->nof_rx_antennas, nof_symbols, 1.0f, noise_estimate/2);
|
||||
} else {
|
||||
srslte_predecoding_diversity_multi(q->symbols, q->ce, x, q->nof_rx_antennas, q->cell.nof_ports, nof_symbols, 1.0f);
|
||||
srslte_layerdemap_diversity(x, q->d, q->cell.nof_ports, nof_symbols / q->cell.nof_ports);
|
||||
|
|
|
@ -294,6 +294,10 @@ void srslte_pdsch_free(srslte_pdsch_t *q) {
|
|||
if (q->d[i]) {
|
||||
free(q->d[i]);
|
||||
}
|
||||
|
||||
if (q->csi[i]) {
|
||||
free(q->csi[i]);
|
||||
}
|
||||
}
|
||||
|
||||
/* Free sch objects */
|
||||
|
@ -394,6 +398,22 @@ void srslte_pdsch_set_power_allocation(srslte_pdsch_t *q, float rho_a) {
|
|||
}
|
||||
}
|
||||
|
||||
int srslte_pdsch_enable_csi(srslte_pdsch_t *q, bool enable) {
|
||||
if (enable) {
|
||||
for (int i = 0; i < SRSLTE_MAX_CODEWORDS; i++) {
|
||||
if (!q->csi[i]) {
|
||||
q->csi[i] = srslte_vec_malloc(sizeof(float) * q->max_re);
|
||||
if (!q->csi[i]) {
|
||||
return SRSLTE_ERROR;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
q->csi_enabled = enable;
|
||||
|
||||
return SRSLTE_SUCCESS;
|
||||
}
|
||||
|
||||
void srslte_pdsch_free_rnti(srslte_pdsch_t* q, uint16_t rnti)
|
||||
{
|
||||
uint32_t rnti_idx = q->is_ue?0:rnti;
|
||||
|
@ -617,6 +637,41 @@ static int srslte_pdsch_codeword_decode(srslte_pdsch_t *q, srslte_pdsch_cfg_t *c
|
|||
/* Bit scrambling */
|
||||
srslte_scrambling_s_offset(seq, q->e[codeword_idx], 0, nbits->nof_bits);
|
||||
|
||||
uint32_t qm = nbits->nof_bits/nbits->nof_re;
|
||||
switch(cfg->grant.mcs[tb_idx].mod) {
|
||||
|
||||
case SRSLTE_MOD_BPSK:
|
||||
qm = 1;
|
||||
break;
|
||||
case SRSLTE_MOD_QPSK:
|
||||
qm = 2;
|
||||
break;
|
||||
case SRSLTE_MOD_16QAM:
|
||||
qm = 4;
|
||||
break;
|
||||
case SRSLTE_MOD_64QAM:
|
||||
qm = 6;
|
||||
break;
|
||||
default:
|
||||
ERROR("No modulation");
|
||||
}
|
||||
|
||||
int16_t *e = q->e[codeword_idx];
|
||||
|
||||
if (q->csi_enabled) {
|
||||
const uint32_t csi_max_idx = srslte_vec_max_fi(q->csi[codeword_idx], nbits->nof_bits / qm);
|
||||
float csi_max = 1.0f;
|
||||
if (csi_max_idx < nbits->nof_bits / qm) {
|
||||
csi_max = q->csi[codeword_idx][csi_max_idx];
|
||||
}
|
||||
for (int i = 0; i < nbits->nof_bits / qm; i++) {
|
||||
const float csi = q->csi[codeword_idx][i] / csi_max;
|
||||
for (int k = 0; k < qm; k++) {
|
||||
e[qm * i + k] = (int16_t) ((float) e[qm * i + k] * csi);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Return */
|
||||
ret = srslte_dlsch_decode2(&q->dl_sch, cfg, softbuffer, q->e[codeword_idx], data, tb_idx);
|
||||
|
||||
|
@ -702,7 +757,7 @@ int srslte_pdsch_decode(srslte_pdsch_t *q,
|
|||
}
|
||||
|
||||
// Pre-decoder
|
||||
if (srslte_predecoding_type(q->symbols, q->ce, x, q->nof_rx_antennas, q->cell.nof_ports, cfg->nof_layers,
|
||||
if (srslte_predecoding_type(q->symbols, q->ce, x, q->csi[0], q->nof_rx_antennas, q->cell.nof_ports, cfg->nof_layers,
|
||||
cfg->codebook_idx, cfg->nbits[0].nof_re, cfg->mimo_type, pdsch_scaling, noise_estimate)<0) {
|
||||
DEBUG("Error predecoding\n");
|
||||
return SRSLTE_ERROR;
|
||||
|
|
|
@ -239,7 +239,7 @@ int srslte_phich_decode(srslte_phich_t *q, cf_t *sf_symbols[SRSLTE_MAX_PORTS],
|
|||
/* in control channels, only diversity is supported */
|
||||
if (q->cell.nof_ports == 1) {
|
||||
/* no need for layer demapping */
|
||||
srslte_predecoding_single_multi(q_sf_symbols, q_ce[0], q->d0, q->nof_rx_antennas, SRSLTE_PHICH_MAX_NSYMB, 1.0f, noise_estimate);
|
||||
srslte_predecoding_single_multi(q_sf_symbols, q_ce[0], q->d0, NULL, q->nof_rx_antennas, SRSLTE_PHICH_MAX_NSYMB, 1.0f, noise_estimate);
|
||||
} else {
|
||||
srslte_predecoding_diversity_multi(q_sf_symbols, q_ce, x, q->nof_rx_antennas, q->cell.nof_ports, SRSLTE_PHICH_MAX_NSYMB, 1.0f);
|
||||
srslte_layerdemap_diversity(x, q->d0, q->cell.nof_ports, SRSLTE_PHICH_MAX_NSYMB / q->cell.nof_ports);
|
||||
|
|
|
@ -377,7 +377,7 @@ int srslte_pmch_decode_multi(srslte_pmch_t *q,
|
|||
}
|
||||
|
||||
// No tx diversity in MBSFN
|
||||
srslte_predecoding_single_multi(q->symbols, q->ce[0], q->d, q->nof_rx_antennas, cfg->nbits[0].nof_re, 1.0f, noise_estimate);
|
||||
srslte_predecoding_single_multi(q->symbols, q->ce[0], q->d, NULL, q->nof_rx_antennas, cfg->nbits[0].nof_re, 1.0f, noise_estimate);
|
||||
|
||||
if (SRSLTE_VERBOSE_ISDEBUG()) {
|
||||
DEBUG("SAVED FILE subframe.dat: received subframe symbols\n");
|
||||
|
|
|
@ -787,7 +787,7 @@ int srslte_pucch_decode(srslte_pucch_t* q, srslte_pucch_format_t format,
|
|||
}
|
||||
|
||||
// Equalization
|
||||
srslte_predecoding_single(q->z_tmp, q->ce, q->z, nof_re, 1.0f, noise_estimate);
|
||||
srslte_predecoding_single(q->z_tmp, q->ce, q->z, NULL, nof_re, 1.0f, noise_estimate);
|
||||
|
||||
// Perform ML-decoding
|
||||
float corr=0, corr_max=-1e9;
|
||||
|
|
|
@ -596,7 +596,7 @@ int srslte_pusch_decode(srslte_pusch_t *q,
|
|||
}
|
||||
|
||||
// Equalization
|
||||
srslte_predecoding_single(q->d, q->ce, q->z, cfg->nbits.nof_re, 1.0f, noise_estimate);
|
||||
srslte_predecoding_single(q->d, q->ce, q->z, NULL, cfg->nbits.nof_re, 1.0f, noise_estimate);
|
||||
|
||||
// DFT predecoding
|
||||
srslte_dft_precoding(&q->dft_precoding, q->z, q->d, cfg->grant.L_prb, cfg->nbits.nof_symb);
|
||||
|
|
|
@ -336,14 +336,17 @@ bool decode_tb_cb(srslte_sch_t *q,
|
|||
decoder_input[i] = NULL;
|
||||
}
|
||||
|
||||
uint32_t remaining_cb = 0;
|
||||
for (int i=0;i<nof_cb;i++) {
|
||||
cb_map[i] = false;
|
||||
/* Do not process blocks with CRC Ok */
|
||||
cb_map[i] = softbuffer->cb_crc[i];
|
||||
if (softbuffer->cb_crc[i] == false) {
|
||||
remaining_cb ++;
|
||||
}
|
||||
}
|
||||
|
||||
srslte_tdec_reset(&q->decoder, cb_len);
|
||||
|
||||
uint32_t remaining_cb = nof_cb;
|
||||
|
||||
q->nof_iterations = 0;
|
||||
|
||||
while(remaining_cb>0) {
|
||||
|
@ -401,7 +404,8 @@ bool decode_tb_cb(srslte_sch_t *q,
|
|||
// CRC is OK
|
||||
if (!srslte_crc_checksum_byte(crc_ptr, q->cb_in, len_crc)) {
|
||||
|
||||
memcpy(&data[(cb_idx[i]*rlen)/8], q->cb_in, rlen/8 * sizeof(uint8_t));
|
||||
memcpy(softbuffer->data[cb_idx[i]], q->cb_in, rlen/8 * sizeof(uint8_t));
|
||||
softbuffer->cb_crc[cb_idx[i]] = true;
|
||||
|
||||
q->nof_iterations += srslte_tdec_get_nof_iterations_cb(&q->decoder, i);
|
||||
|
||||
|
@ -418,15 +422,28 @@ bool decode_tb_cb(srslte_sch_t *q,
|
|||
cb_idx[i], remaining_cb, i, first_cb, nof_cb);
|
||||
|
||||
q->nof_iterations += q->max_iterations;
|
||||
q->nof_iterations /= (nof_cb-remaining_cb+1);
|
||||
return false;
|
||||
srslte_tdec_reset_cb(&q->decoder, i);
|
||||
remaining_cb--;
|
||||
decoder_input[i] = NULL;
|
||||
cb_idx[i] = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
softbuffer->tb_crc = true;
|
||||
for (int i = 0; i < nof_cb && softbuffer->tb_crc; i++) {
|
||||
/* If one CB failed return false */
|
||||
softbuffer->tb_crc = softbuffer->cb_crc[i];
|
||||
}
|
||||
if (softbuffer->tb_crc) {
|
||||
for (int i = 0; i < nof_cb; i++) {
|
||||
memcpy(&data[i * rlen / 8], softbuffer->data[i], rlen/8 * sizeof(uint8_t));
|
||||
}
|
||||
}
|
||||
|
||||
q->nof_iterations /= nof_cb;
|
||||
return true;
|
||||
return softbuffer->tb_crc;
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -270,6 +270,9 @@ void parse_args(all_args_t *args, int argc, char *argv[]) {
|
|||
bpo::value<float>(&args->expert.phy.estimator_fil_w)->default_value(0.1),
|
||||
"Chooses the coefficients for the 3-tap channel estimator centered filter.")
|
||||
|
||||
("expert.pdsch_csi_enabled",
|
||||
bpo::value<bool>(&args->expert.phy.pdsch_csi_enabled)->default_value(false),
|
||||
"Stores the Channel State Information and uses it for weightening the softbits. It is only compatible with TM1.")
|
||||
|
||||
("rf_calibration.tx_corr_dc_gain", bpo::value<float>(&args->rf_cal.tx_corr_dc_gain)->default_value(0.0),
|
||||
"TX DC offset gain correction")
|
||||
|
|
|
@ -137,6 +137,7 @@ bool phch_worker::init(uint32_t max_prb, srslte::log *log_h, srslte::log *log_ph
|
|||
srslte_chest_dl_cfo_estimate_enable(&ue_dl.chest, phy->args->cfo_ref_mask!=0, phy->args->cfo_ref_mask);
|
||||
srslte_ue_ul_set_normalization(&ue_ul, true);
|
||||
srslte_ue_ul_set_cfo_enable(&ue_ul, true);
|
||||
srslte_pdsch_enable_csi(&ue_dl.pdsch, phy->args->pdsch_csi_enabled);
|
||||
|
||||
mem_initiated = true;
|
||||
|
||||
|
|
|
@ -182,6 +182,9 @@ enable = false
|
|||
# cfo_loop_pss_timeout: After the PSS estimation is below cfo_loop_pss_tol for cfo_loop_pss_timeout times consecutively,
|
||||
# RS adjustments are allowed.
|
||||
#
|
||||
# pdsch_csi_enabled: Stores the Channel State Information and uses it for weightening the softbits. It is only
|
||||
# compatible with TM1. It is False by default.
|
||||
#
|
||||
#####################################################################
|
||||
[expert]
|
||||
#ip_netmask = 255.255.255.0
|
||||
|
@ -205,6 +208,7 @@ enable = false
|
|||
#pregenerate_signals = false
|
||||
#metrics_csv_enable = false
|
||||
#metrics_csv_filename = /tmp/ue_metrics.csv
|
||||
#pdsch_csi_enabled = true # Caution! Only TM1 supported!
|
||||
|
||||
# CFO related values
|
||||
#cfo_integer_enabled = false
|
||||
|
|
Loading…
Reference in New Issue