diff --git a/CMakeLists.txt b/CMakeLists.txt index a21ed4fa9..d67985c49 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -371,7 +371,7 @@ if(RF_FOUND) message(STATUS "Building with srsENB") add_subdirectory(srsenb) else(ENABLE_SRSENB) - message(STATUS "srsUE build disabled") + message(STATUS "srsENB build disabled") endif(ENABLE_SRSENB) else(RF_FOUND) message(STATUS "srsUE and srsENB builds disabled due to missing RF driver") diff --git a/lib/include/srslte/radio/radio.h b/lib/include/srslte/radio/radio.h index 6ff0c5100..454f1578f 100644 --- a/lib/include/srslte/radio/radio.h +++ b/lib/include/srslte/radio/radio.h @@ -101,6 +101,7 @@ namespace srslte { void set_tx_freq(double freq); void set_rx_freq(double freq); + double get_freq_offset(); double get_tx_freq(); double get_rx_freq(); diff --git a/lib/src/phy/fec/viterbi37_neon.c b/lib/src/phy/fec/viterbi37_neon.c index 452dba567..82ed190cc 100644 --- a/lib/src/phy/fec/viterbi37_neon.c +++ b/lib/src/phy/fec/viterbi37_neon.c @@ -176,7 +176,7 @@ void print_uint8x16_t(char *s, uint8x16_t val) { printf("\n"); } -int movemask_neon(uint8x16_t movemask_low_in) +static inline int movemask_neon(uint8x16_t movemask_low_in) { uint8x8_t lo = vget_low_u8(movemask_low_in); uint8x8_t hi = vget_high_u8(movemask_low_in); diff --git a/lib/src/phy/phch/test/pdsch_pdcch_file_test.c b/lib/src/phy/phch/test/pdsch_pdcch_file_test.c index 76f48b959..baab97cea 100644 --- a/lib/src/phy/phch/test/pdsch_pdcch_file_test.c +++ b/lib/src/phy/phch/test/pdsch_pdcch_file_test.c @@ -175,6 +175,10 @@ int main(int argc, char **argv) { } uint8_t *data[] = {malloc(100000)}; + if (!data[0]) { + perror("malloc"); + exit(-1); + } ret = -1; nof_frames = 0; @@ -195,7 +199,8 @@ int main(int argc, char **argv) { } while (nof_frames <= max_frames && ret == 0); base_free(); - free(data[0]); + if (data[0]) + free(data[0]); if (ret > 0) { exit(0); } else { diff --git a/lib/src/phy/phch/test/pmch_file_test.c b/lib/src/phy/phch/test/pmch_file_test.c index 1d0715caa..fa6d04092 100644 --- a/lib/src/phy/phch/test/pmch_file_test.c +++ b/lib/src/phy/phch/test/pmch_file_test.c @@ -181,13 +181,17 @@ int main(int argc, char **argv) { exit(-1); } - uint8_t *data[] = {malloc(100000)}; + uint8_t *data = malloc(100000); + if (!data) { + perror("malloc"); + exit(-1); + } ret = -1; srslte_filesource_read(&fsrc, input_buffer[0], flen); INFO("Reading %d samples sub-frame %d\n", flen, sf_idx); - ret = srslte_ue_dl_decode_mbsfn(&ue_dl, data[0], sf_idx); + ret = srslte_ue_dl_decode_mbsfn(&ue_dl, data, sf_idx); if(ret > 0) { printf("PMCH Decoded OK!\n"); } else if (ret < 0) { @@ -195,7 +199,9 @@ int main(int argc, char **argv) { } base_free(); - free(data[0]); + if (data != NULL) { + free(data); + } if (ret > 0) { exit(0); } else { diff --git a/lib/src/phy/ue/ue_ul.c b/lib/src/phy/ue/ue_ul.c index a0accb579..5cf913bfa 100644 --- a/lib/src/phy/ue/ue_ul.c +++ b/lib/src/phy/ue/ue_ul.c @@ -626,13 +626,12 @@ int srslte_ue_ul_sr_send_tti(uint32_t I_sr, uint32_t current_tti) { } else { return SRSLTE_ERROR; } - uint32_t sfn = current_tti/10; - uint32_t subf = current_tti%10; - if ((10*sfn+subf-sr_N_offset)%sr_periodicity==0) { - return 1; - } else { - return SRSLTE_SUCCESS; + if (current_tti >= sr_N_offset) { + if ((current_tti - sr_N_offset) % sr_periodicity == 0) { + return 1; + } } + return SRSLTE_SUCCESS; } diff --git a/lib/src/radio/radio.cc b/lib/src/radio/radio.cc index f592db71f..f3baad4a5 100644 --- a/lib/src/radio/radio.cc +++ b/lib/src/radio/radio.cc @@ -313,6 +313,11 @@ double radio::get_rx_freq() return rx_freq; } +double radio::get_freq_offset() +{ + return freq_offset; +} + double radio::get_tx_freq() { return tx_freq; diff --git a/srsenb/src/mac/scheduler.cc b/srsenb/src/mac/scheduler.cc index fee1e5e5d..b7dc63898 100644 --- a/srsenb/src/mac/scheduler.cc +++ b/srsenb/src/mac/scheduler.cc @@ -864,16 +864,7 @@ int sched::ul_sched(uint32_t tti, srsenb::sched_interface::ul_sched_res_t* sched printf("SCHED: Could not schedule UL DCI rnti=0x%x, pid=%d, L=%d, sf_idx=%d\n", rnti, h->get_id(), aggr_level, sf_idx); - sched_ue::sched_dci_cce_t *loc=user->get_locations(current_cfi, sf_idx); - for (int i=0;inof_loc[aggr_level];i++) { - printf("n=%d\n", loc->cce_start[aggr_level][i]); - } - printf("used=["); - for (int i=0;ipusch[nof_dci_elems].needs_pdcch = false; + sched_result->pusch[nof_dci_elems].needs_pdcch = false; } else { sched_result->pusch[nof_dci_elems].needs_pdcch = true; } diff --git a/srsepc/user_db.csv.example b/srsepc/user_db.csv.example index 89d0dedf1..4919ed6bb 100644 --- a/srsepc/user_db.csv.example +++ b/srsepc/user_db.csv.example @@ -10,4 +10,4 @@ # # Note: Lines starting by '#' are ignored ue1,001010123456789,00112233445566778899aabbccddeeff,63BFA50EE6523365FF14C1F45F88737D,9001 -ue2,001010123456780,00112233445566778899aabbccddeeaa,63BFA50EE6523365FF14C1F45F88737D,2000 +ue2,001010123456780,00112233445566778899aabbccddeeaa,63BFA50EE6523365FF14C1F45F88737D,8000 diff --git a/srsue/hdr/mac/ul_harq.h b/srsue/hdr/mac/ul_harq.h index 7418d23bf..b98a7497a 100644 --- a/srsue/hdr/mac/ul_harq.h +++ b/srsue/hdr/mac/ul_harq.h @@ -206,7 +206,7 @@ private: { if (ack) { if (grant) { - if (grant->ndi[0] == get_ndi()) { + if (grant->ndi[0] == get_ndi() && grant->phy_grant.ul.mcs.tbs != 0) { *ack = false; } } @@ -215,7 +215,7 @@ private: // Reset HARQ process if TB has changed if (harq_feedback && has_grant() && grant) { - if (grant->n_bytes[0] != cur_grant.n_bytes[0] && cur_grant.n_bytes[0] > 0) { + if (grant->n_bytes[0] != cur_grant.n_bytes[0] && cur_grant.n_bytes[0] > 0 && grant->n_bytes[0] > 0) { Debug("UL %d: Reset due to change of grant size last_grant=%d, new_grant=%d\n", pid, cur_grant.n_bytes[0], grant->n_bytes[0]); reset(); diff --git a/srsue/hdr/phy/phch_worker.h b/srsue/hdr/phy/phch_worker.h index d73214514..c154ff514 100644 --- a/srsue/hdr/phy/phch_worker.h +++ b/srsue/hdr/phy/phch_worker.h @@ -70,6 +70,8 @@ public: void start_plot(); float get_ref_cfo(); + float get_cfo(); + float get_ul_cfo(); private: /* Inherited from thread_pool::worker. Function called every subframe to run the DL/UL processing */ diff --git a/srsue/src/phy/phch_worker.cc b/srsue/src/phy/phch_worker.cc index 9caa0102a..f7e1381f8 100644 --- a/srsue/src/phy/phch_worker.cc +++ b/srsue/src/phy/phch_worker.cc @@ -203,6 +203,25 @@ float phch_worker::get_ref_cfo() return srslte_chest_dl_get_cfo(&ue_dl.chest); } +float phch_worker::get_cfo() +{ + return cfo; +} + +float phch_worker::get_ul_cfo() { + srslte::radio *radio = phy->get_radio(); + + if (radio->get_freq_offset() != 0.0f) { + /* Compensates the radio frequency offset applied equally to DL and UL */ + const float ul_dl_ratio = (float) radio->get_tx_freq() / (float) radio->get_rx_freq(); + const float offset_hz = (float) radio->get_freq_offset() * (1.0f - ul_dl_ratio); + return cfo - offset_hz / (15000); + } else { + return cfo; + } + +} + void phch_worker::work_imp() { if (!cell_initiated) { @@ -324,7 +343,7 @@ void phch_worker::work_imp() } /* Set UL CFO before transmission */ - srslte_ue_ul_set_cfo(&ue_ul, cfo); + srslte_ue_ul_set_cfo(&ue_ul, get_ul_cfo()); /* Transmit PUSCH, PUCCH or SRS */ bool signal_ready = false; @@ -367,7 +386,7 @@ void phch_worker::work_imp() update_measurements(); if (chest_ok) { - if (phy->avg_rsrp_dbm > -130.0 && 10*log10(srslte_chest_dl_get_snr(&ue_dl.chest)) > -30.0) { + if (phy->avg_rsrp_dbm > -130.0 && phy->avg_snr_db > -30.0) { log_h->debug("SNR=%.1f dB, RSRP=%.1f dBm sync=in-sync from channel estimator\n", 10*log10(srslte_chest_dl_get_snr(&ue_dl.chest)), phy->avg_rsrp_dbm); chest_loop->in_sync(); @@ -931,7 +950,7 @@ void phch_worker::set_uci_aperiodic_cqi() int cqi_len = srslte_cqi_value_pack(&cqi_report, uci_data.uci_cqi); if (cqi_len < 0) { - Error("Error packing CQI value (Aperiodic reporting mode RM31)."); + Error("Error packing CQI value (Aperiodic reporting mode RM30)."); return; } uci_data.uci_cqi_len = (uint32_t) cqi_len; @@ -940,11 +959,16 @@ void phch_worker::set_uci_aperiodic_cqi() srslte_cqi_to_str(uci_data.uci_cqi, uci_data.uci_cqi_len, cqi_str, SRSLTE_CQI_STR_MAX_CHAR); /* Set RI = 1 */ - uci_data.uci_ri = ri; - uci_data.uci_ri_len = 1; + if (phy->config->dedicated.antenna_info_explicit_value.tx_mode == LIBLTE_RRC_TRANSMISSION_MODE_3 || + phy->config->dedicated.antenna_info_explicit_value.tx_mode == LIBLTE_RRC_TRANSMISSION_MODE_4) { + uci_data.uci_ri = ri; + uci_data.uci_ri_len = 1; + } else { + uci_data.uci_ri_len = 0; + } - Info("PUSCH: Aperiodic RM30 ri%s, CQI=%s, SNR=%.1f dB, for %d subbands\n", - (uci_data.uci_ri == 0)?"=1":"~1", cqi_str, phy->avg_snr_db, cqi_report.subband_hl.N); + Info("PUSCH: Aperiodic RM30 CQI=%s, %sSNR=%.1f dB, for %d subbands\n", + cqi_str, (uci_data.uci_ri_len)?((uci_data.uci_ri == 0)?"ri=0, ":"ri=1, "):"", phy->avg_snr_db, cqi_report.subband_hl.N); } break; case LIBLTE_RRC_CQI_REPORT_MODE_APERIODIC_RM31: @@ -1471,6 +1495,13 @@ plot_scatter_t pconst; float tmp_plot[SCATTER_PDSCH_BUFFER_LEN]; cf_t tmp_plot2[SRSLTE_SF_LEN_RE(SRSLTE_MAX_PRB, SRSLTE_CP_NORM)]; +#define CFO_PLOT_LEN 0 /* Set to non zero for enabling CFO plot */ +#if CFO_PLOT_LEN > 0 +static plot_real_t pcfo; +static uint32_t icfo = 0; +static float cfo_buffer[CFO_PLOT_LEN]; +#endif /* CFO_PLOT_LEN > 0 */ + void *plot_thread_run(void *arg) { srsue::phch_worker *worker = (srsue::phch_worker*) arg; @@ -1495,10 +1526,14 @@ void *plot_thread_run(void *arg) { plot_scatter_addToWindowGrid(&pconst, (char*)"srsue", 0, worker->get_rx_nof_antennas()); +#if CFO_PLOT_LEN > 0 + plot_real_init(&pcfo); + plot_real_setTitle(&pcfo, (char*) "CFO (Hz)"); + plot_real_setLabels(&pcfo, (char *) "Time", (char *) "Hz"); + plot_real_setYAxisScale(&pcfo, -4000, 4000); - - - + plot_scatter_addToWindowGrid(&pcfo, (char*)"srsue", 1, worker->get_rx_nof_antennas()); +#endif /* CFO_PLOT_LEN > 0 */ int n; int readed_pdsch_re=0; @@ -1522,7 +1557,14 @@ void *plot_thread_run(void *arg) { } readed_pdsch_re = 0; } - } + +#if CFO_PLOT_LEN > 0 + cfo_buffer[icfo] = worker->get_cfo() * 15000.0f; + icfo = (icfo + 1)%CFO_PLOT_LEN; + plot_real_setNewData(&pcfo, cfo_buffer, CFO_PLOT_LEN); +#endif /* CFO_PLOT_LEN > 0 */ + + } return NULL; }