Commit 6efc8e17 authored by Sakthivel Velumani's avatar Sakthivel Velumani

Enabled multi-threading for gNB L1 tx

A second thread message is created for L1 tx processing and pushed into the threaPool.
The message contain the nfapi rel15 PDUs for SSB, PDCCH and PDSCH. The memory of these PDUs are reused for subsequent slots.
Need to fix the nfapi mode VNF PNF implementation to adapt to this memory scheme.
parent 5de12198
...@@ -113,15 +113,25 @@ time_stats_t softmodem_stats_rx_sf; // total rx time ...@@ -113,15 +113,25 @@ time_stats_t softmodem_stats_rx_sf; // total rx time
void tx_func(void *param) { void tx_func(void *param) {
processingData_L1_t *info = (processingData_L1_t *) param; processingData_L1tx_t *info = (processingData_L1tx_t *) param;
PHY_VARS_gNB *gNB = info->gNB; PHY_VARS_gNB *gNB = info->gNB;
int frame_tx = info->frame_tx; int frame_tx = info->frame_tx;
int slot_tx = info->slot_tx; int slot_tx = info->slot_tx;
phy_procedures_gNB_TX(gNB, frame_tx,slot_tx, 1); phy_procedures_gNB_TX(info,
frame_tx,
slot_tx,
1);
if ((frame_tx&127) == 0) dump_pdsch_stats(gNB);
// start FH TX processing // If the later of the 2 L1 tx thread finishes first,
// we wait for the earlier one to finish and start the RU thread
// to avoid realtime issues with USRP
notifiedFIFO_elt_t *res; notifiedFIFO_elt_t *res;
res = pullTpool(gNB->resp_L1_tx, gNB->threadPool);
pushNotifiedFIFO(gNB->resp_L1_tx,res);
// Start RU TX processing.
res = pullTpool(gNB->resp_RU_tx, gNB->threadPool); res = pullTpool(gNB->resp_RU_tx, gNB->threadPool);
processingData_RU_t *syncMsg = (processingData_RU_t *)NotifiedFifoData(res); processingData_RU_t *syncMsg = (processingData_RU_t *)NotifiedFifoData(res);
syncMsg->frame_tx = frame_tx; syncMsg->frame_tx = frame_tx;
...@@ -257,7 +267,6 @@ void rx_func(void *param) { ...@@ -257,7 +267,6 @@ void rx_func(void *param) {
LOG_D(PHY,"%s() Exit proc[rx:%d%d tx:%d%d]\n", __FUNCTION__, frame_rx, slot_rx, frame_tx, slot_tx); LOG_D(PHY,"%s() Exit proc[rx:%d%d tx:%d%d]\n", __FUNCTION__, frame_rx, slot_rx, frame_tx, slot_tx);
// Call the scheduler // Call the scheduler
start_meas(&gNB->ul_indication_stats); start_meas(&gNB->ul_indication_stats);
pthread_mutex_lock(&gNB->UL_INFO_mutex); pthread_mutex_lock(&gNB->UL_INFO_mutex);
gNB->UL_INFO.frame = frame_rx; gNB->UL_INFO.frame = frame_rx;
...@@ -269,10 +278,9 @@ void rx_func(void *param) { ...@@ -269,10 +278,9 @@ void rx_func(void *param) {
stop_meas(&gNB->ul_indication_stats); stop_meas(&gNB->ul_indication_stats);
notifiedFIFO_elt_t *res; notifiedFIFO_elt_t *res;
if (tx_slot_type == NR_DOWNLINK_SLOT || tx_slot_type == NR_MIXED_SLOT) { if (tx_slot_type == NR_DOWNLINK_SLOT || tx_slot_type == NR_MIXED_SLOT) {
res = pullTpool(gNB->resp_L1_tx, gNB->threadPool); res = pullTpool(gNB->resp_L1_tx, gNB->threadPool);
processingData_L1_t *syncMsg = (processingData_L1_t *)NotifiedFifoData(res); processingData_L1tx_t *syncMsg = (processingData_L1tx_t *)NotifiedFifoData(res);
syncMsg->gNB = gNB; syncMsg->gNB = gNB;
syncMsg->frame_rx = frame_rx; syncMsg->frame_rx = frame_rx;
syncMsg->slot_rx = slot_rx; syncMsg->slot_rx = slot_rx;
...@@ -327,7 +335,6 @@ static void *process_stats_thread(void *param) { ...@@ -327,7 +335,6 @@ static void *process_stats_thread(void *param) {
PHY_VARS_gNB *gNB = (PHY_VARS_gNB *)param; PHY_VARS_gNB *gNB = (PHY_VARS_gNB *)param;
reset_meas(&gNB->phy_proc_tx);
reset_meas(&gNB->dlsch_encoding_stats); reset_meas(&gNB->dlsch_encoding_stats);
reset_meas(&gNB->phy_proc_rx); reset_meas(&gNB->phy_proc_rx);
reset_meas(&gNB->ul_indication_stats); reset_meas(&gNB->ul_indication_stats);
...@@ -339,7 +346,8 @@ static void *process_stats_thread(void *param) { ...@@ -339,7 +346,8 @@ static void *process_stats_thread(void *param) {
while(!oai_exit) while(!oai_exit)
{ {
sleep(1); sleep(1);
print_meas(&gNB->phy_proc_tx, "L1 Tx processing", NULL, NULL); print_meas(gNB->phy_proc_tx_0, "L1 Tx processing thread 0", NULL, NULL);
print_meas(gNB->phy_proc_tx_1, "L1 Tx processing thread 1", NULL, NULL);
print_meas(&gNB->dlsch_encoding_stats, "DLSCH encoding", NULL, NULL); print_meas(&gNB->dlsch_encoding_stats, "DLSCH encoding", NULL, NULL);
print_meas(&gNB->phy_proc_rx, "L1 Rx processing", NULL, NULL); print_meas(&gNB->phy_proc_rx, "L1 Rx processing", NULL, NULL);
print_meas(&gNB->ul_indication_stats, "UL Indication", NULL, NULL); print_meas(&gNB->ul_indication_stats, "UL Indication", NULL, NULL);
......
...@@ -1258,12 +1258,27 @@ void *ru_thread( void *param ) { ...@@ -1258,12 +1258,27 @@ void *ru_thread( void *param ) {
wait_sync("ru_thread"); wait_sync("ru_thread");
notifiedFIFO_elt_t *msg = newNotifiedFIFO_elt(sizeof(processingData_L1_t),0,gNB->resp_L1,rx_func); notifiedFIFO_elt_t *msg = newNotifiedFIFO_elt(sizeof(processingData_L1_t),0,gNB->resp_L1,rx_func);
notifiedFIFO_elt_t *msgL1Tx = newNotifiedFIFO_elt(sizeof(processingData_L1_t),0,gNB->resp_L1_tx,tx_func);
notifiedFIFO_elt_t *msgRUTx = newNotifiedFIFO_elt(sizeof(processingData_L1_t),0,gNB->resp_RU_tx,ru_tx_func);
processingData_L1_t *syncMsg;
notifiedFIFO_elt_t *res;
pushNotifiedFIFO(gNB->resp_L1,msg); // to unblock the process in the beginning pushNotifiedFIFO(gNB->resp_L1,msg); // to unblock the process in the beginning
// we create 2 threads for L1 tx processing
notifiedFIFO_elt_t *msgL1Tx = newNotifiedFIFO_elt(sizeof(processingData_L1tx_t),0,gNB->resp_L1_tx,tx_func);
processingData_L1tx_t *msgDataTx = (processingData_L1tx_t *)NotifiedFifoData(msgL1Tx);
init_DLSCH_struct(gNB, msgDataTx);
reset_meas(&msgDataTx->phy_proc_tx);
gNB->phy_proc_tx_0 = &msgDataTx->phy_proc_tx;
pushNotifiedFIFO(gNB->resp_L1_tx,msgL1Tx); // to unblock the process in the beginning
msgL1Tx = newNotifiedFIFO_elt(sizeof(processingData_L1tx_t),0,gNB->resp_L1_tx,tx_func);
msgDataTx = (processingData_L1tx_t *)NotifiedFifoData(msgL1Tx);
init_DLSCH_struct(gNB, msgDataTx);
reset_meas(&msgTx->phy_proc_tx);
gNB->phy_proc_tx_1 = &msgDataTx->phy_proc_tx;
pushNotifiedFIFO(gNB->resp_L1_tx,msgL1Tx); // to unblock the process in the beginning pushNotifiedFIFO(gNB->resp_L1_tx,msgL1Tx); // to unblock the process in the beginning
processingData_L1_t *syncMsg;
notifiedFIFO_elt_t *res;
notifiedFIFO_elt_t *msgRUTx = newNotifiedFIFO_elt(sizeof(processingData_L1_t),0,gNB->resp_RU_tx,ru_tx_func);
pushNotifiedFIFO(gNB->resp_RU_tx,msgRUTx); // to unblock the process in the beginning pushNotifiedFIFO(gNB->resp_RU_tx,msgRUTx); // to unblock the process in the beginning
if(!emulate_rf) { if(!emulate_rf) {
......
...@@ -548,6 +548,20 @@ void nr_phy_config_request(NR_PHY_Config_t *phy_config) { ...@@ -548,6 +548,20 @@ void nr_phy_config_request(NR_PHY_Config_t *phy_config) {
LOG_I(PHY,"gNB %d configured\n",Mod_id); LOG_I(PHY,"gNB %d configured\n",Mod_id);
} }
void init_DLSCH_struct(PHY_VARS_gNB *gNB, processingData_L1tx_t *msg) {
NR_DL_FRAME_PARMS *fp = &msg->gNB->frame_parms;
nfapi_nr_config_request_scf_t *cfg = &msg->gNB->gNB_config;
uint16_t grid_size = cfg->carrier_config.dl_grid_size[fp->numerology_index].value;
memset(msg->num_pdsch_rnti, 0, sizeof(uint16_t)*80);
for (i=0; i<NUMBER_OF_NR_DLSCH_MAX; i++) {
LOG_I(PHY,"Allocating Transport Channel Buffers for DLSCH %d/%d\n",i,NUMBER_OF_NR_DLSCH_MAX);
for (j=0; j<2; j++) {
msg->dlsch[i][j] = new_gNB_dlsch(fp,1,16,NSOFT,0,grid_size);
AssertFatal(msg->dlsch[i][j]!=NULL,"Can't initialize dlsch %d \n", i);
}
}
}
void init_nr_transport(PHY_VARS_gNB *gNB) { void init_nr_transport(PHY_VARS_gNB *gNB) {
int i; int i;
...@@ -572,16 +586,6 @@ void init_nr_transport(PHY_VARS_gNB *gNB) { ...@@ -572,16 +586,6 @@ void init_nr_transport(PHY_VARS_gNB *gNB) {
AssertFatal(gNB->pucch[i]!=NULL,"Can't initialize pucch %d \n", i); AssertFatal(gNB->pucch[i]!=NULL,"Can't initialize pucch %d \n", i);
} }
for (i=0; i<gNB->number_of_nr_dlsch_max; i++) {
LOG_I(PHY,"Allocating Transport Channel Buffers for DLSCH %d/%d\n",i,gNB->number_of_nr_dlsch_max);
for (j=0; j<2; j++) {
gNB->dlsch[i][j] = new_gNB_dlsch(fp,1,16,NSOFT,0,grid_size);
AssertFatal(gNB->dlsch[i][j]!=NULL,"Can't initialize dlsch %d \n", i);
}
}
for (i=0; i<gNB->number_of_nr_ulsch_max; i++) { for (i=0; i<gNB->number_of_nr_ulsch_max; i++) {
LOG_I(PHY,"Allocating Transport Channel Buffer for ULSCH %d/%d\n",i,gNB->number_of_nr_ulsch_max); LOG_I(PHY,"Allocating Transport Channel Buffer for ULSCH %d/%d\n",i,gNB->number_of_nr_ulsch_max);
......
...@@ -111,10 +111,11 @@ void nr_pdsch_codeword_scrambling_optim(uint8_t *in, ...@@ -111,10 +111,11 @@ void nr_pdsch_codeword_scrambling_optim(uint8_t *in,
} }
uint8_t nr_generate_pdsch(PHY_VARS_gNB *gNB, uint8_t nr_generate_pdsch(processingData_L1tx_t *msgTx,
int frame, int frame,
int slot) { int slot) {
PHY_VARS_gNB *gNB = msgTx->gNB;
NR_gNB_DLSCH_t *dlsch; NR_gNB_DLSCH_t *dlsch;
uint32_t ***pdsch_dmrs = gNB->nr_gold_pdsch_dmrs[slot]; uint32_t ***pdsch_dmrs = gNB->nr_gold_pdsch_dmrs[slot];
int32_t** txdataF = gNB->common_vars.txdataF; int32_t** txdataF = gNB->common_vars.txdataF;
...@@ -132,9 +133,8 @@ uint8_t nr_generate_pdsch(PHY_VARS_gNB *gNB, ...@@ -132,9 +133,8 @@ uint8_t nr_generate_pdsch(PHY_VARS_gNB *gNB,
time_stats_t *dlsch_interleaving_stats=&gNB->dlsch_interleaving_stats; time_stats_t *dlsch_interleaving_stats=&gNB->dlsch_interleaving_stats;
time_stats_t *dlsch_segmentation_stats=&gNB->dlsch_segmentation_stats; time_stats_t *dlsch_segmentation_stats=&gNB->dlsch_segmentation_stats;
for (int dlsch_id=0;dlsch_id<gNB->number_of_nr_dlsch_max;dlsch_id++) { for (int dlsch_id=0; dlsch_id<msgTx->num_pdsch_slot; dlsch_id++) {
dlsch = gNB->dlsch[dlsch_id][0]; dlsch = msgTx->dlsch[dlsch_id][0];
if (dlsch->slot_tx[slot] == 0) continue;
NR_DL_gNB_HARQ_t *harq = &dlsch->harq_process; NR_DL_gNB_HARQ_t *harq = &dlsch->harq_process;
nfapi_nr_dl_tti_pdsch_pdu_rel15_t *rel15 = &harq->pdsch_pdu.pdsch_pdu_rel15; nfapi_nr_dl_tti_pdsch_pdu_rel15_t *rel15 = &harq->pdsch_pdu.pdsch_pdu_rel15;
......
...@@ -63,9 +63,7 @@ void nr_pdsch_codeword_scrambling(uint8_t *in, ...@@ -63,9 +63,7 @@ void nr_pdsch_codeword_scrambling(uint8_t *in,
uint32_t n_RNTI, uint32_t n_RNTI,
uint32_t* out); uint32_t* out);
void nr_fill_dlsch(PHY_VARS_gNB *gNB, void nr_fill_dlsch(processingData_L1tx_t *msgTx,
int frame,
int slot,
nfapi_nr_dl_tti_pdsch_pdu *pdsch_pdu, nfapi_nr_dl_tti_pdsch_pdu *pdsch_pdu,
unsigned char *sdu); unsigned char *sdu);
......
...@@ -254,48 +254,20 @@ void nr_emulate_dlsch_payload(uint8_t* pdu, uint16_t size) { ...@@ -254,48 +254,20 @@ void nr_emulate_dlsch_payload(uint8_t* pdu, uint16_t size) {
*(pdu+i) = (uint8_t)rand(); *(pdu+i) = (uint8_t)rand();
} }
int16_t find_nr_dlsch(uint16_t rnti, PHY_VARS_gNB *gNB,find_type_t type) { void nr_fill_dlsch(processingData_L1tx_t *msgTx,
uint16_t i;
int16_t first_free_index=-1;
AssertFatal(gNB!=NULL,"gNB is null\n");
for (i=0; i<gNB->number_of_nr_dlsch_max; i++) {
AssertFatal(gNB->dlsch[i]!=NULL,"gNB->dlsch[%d] is null\n",i);
AssertFatal(gNB->dlsch[i][0]!=NULL,"gNB->dlsch[%d][0] is null\n",i);
LOG_D(PHY,"searching for rnti %x : dlsch_index %d=> harq_mask %x, rnti %x, first_free_index %d\n", rnti,i,
gNB->dlsch[i][0]->harq_mask,gNB->dlsch[i][0]->rnti,first_free_index);
if ((gNB->dlsch[i][0]->harq_mask >0) &&
(gNB->dlsch[i][0]->rnti==rnti)) return i;
else if ((gNB->dlsch[i][0]->harq_mask == 0) && (first_free_index==-1)) first_free_index=i;
}
if (type == SEARCH_EXIST) return -1;
if (first_free_index != -1)
gNB->dlsch[first_free_index][0]->rnti = 0;
return first_free_index;
}
void nr_fill_dlsch(PHY_VARS_gNB *gNB,
int frame,
int slot,
nfapi_nr_dl_tti_pdsch_pdu *pdsch_pdu, nfapi_nr_dl_tti_pdsch_pdu *pdsch_pdu,
uint8_t *sdu) { uint8_t *sdu) {
nfapi_nr_dl_tti_pdsch_pdu_rel15_t *rel15 = &pdsch_pdu->pdsch_pdu_rel15; nfapi_nr_dl_tti_pdsch_pdu_rel15_t *rel15 = &pdsch_pdu->pdsch_pdu_rel15;
int dlsch_id = find_nr_dlsch(rel15->rnti,gNB,SEARCH_EXIST); AssertFatal(msgTx->num_pdsch_slot < NUMBER_OF_NR_DLSCH_MAX,
AssertFatal( (dlsch_id>=0) && (dlsch_id<gNB->number_of_nr_dlsch_max), "Number of PDSCH PDUs %d exceeded the limit\n",msgTx->num_pdsch_slot);
"illegal or no dlsch_id found!!! rnti %04x dlsch_id %d\n",rel15->rnti,dlsch_id); NR_gNB_DLSCH_t *dlsch = msgTx->dlsch[msgTx->num_pdsch_slot][0];
NR_gNB_DLSCH_t *dlsch = gNB->dlsch[dlsch_id][0];
NR_DL_gNB_HARQ_t *harq = &dlsch->harq_process; NR_DL_gNB_HARQ_t *harq = &dlsch->harq_process;
/// DLSCH struct /// DLSCH struct
memcpy((void*)&harq->pdsch_pdu, (void*)pdsch_pdu, sizeof(nfapi_nr_dl_tti_pdsch_pdu)); memcpy((void*)&harq->pdsch_pdu, (void*)pdsch_pdu, sizeof(nfapi_nr_dl_tti_pdsch_pdu));
gNB->num_pdsch_rnti[slot]++; msgTx->num_pdsch_slot++;
AssertFatal(sdu!=NULL,"sdu is null\n"); AssertFatal(sdu!=NULL,"sdu is null\n");
harq->pdu = sdu; harq->pdu = sdu;
} }
...@@ -752,16 +752,12 @@ typedef struct PHY_VARS_gNB_s { ...@@ -752,16 +752,12 @@ typedef struct PHY_VARS_gNB_s {
// nfapi_nr_dl_tti_pdcch_pdu *pdcch_pdu; // nfapi_nr_dl_tti_pdcch_pdu *pdcch_pdu;
// nfapi_nr_ul_dci_request_pdus_t *ul_dci_pdu; // nfapi_nr_ul_dci_request_pdus_t *ul_dci_pdu;
uint16_t num_pdsch_rnti[80]; uint16_t num_pdsch_rnti[80];
NR_gNB_SSB_t ssb[64];
NR_gNB_PBCH pbch; NR_gNB_PBCH pbch;
nr_cce_t cce_list[MAX_DCI_CORESET][NR_MAX_PDCCH_AGG_LEVEL]; nr_cce_t cce_list[MAX_DCI_CORESET][NR_MAX_PDCCH_AGG_LEVEL];
NR_gNB_COMMON common_vars; NR_gNB_COMMON common_vars;
NR_gNB_PRACH prach_vars; NR_gNB_PRACH prach_vars;
NR_gNB_PUSCH *pusch_vars[NUMBER_OF_NR_ULSCH_MAX]; NR_gNB_PUSCH *pusch_vars[NUMBER_OF_NR_ULSCH_MAX];
NR_gNB_PUCCH_t *pucch[NUMBER_OF_NR_PUCCH_MAX]; NR_gNB_PUCCH_t *pucch[NUMBER_OF_NR_PUCCH_MAX];
NR_gNB_PDCCH_t pdcch_pdu[NUMBER_OF_NR_PDCCH_MAX];
NR_gNB_UL_PDCCH_t ul_pdcch_pdu[NUMBER_OF_NR_PDCCH_MAX];
NR_gNB_DLSCH_t *dlsch[NUMBER_OF_NR_DLSCH_MAX][2]; // Nusers times two spatial streams
NR_gNB_ULSCH_t *ulsch[NUMBER_OF_NR_ULSCH_MAX][2]; // [Nusers times][2 codewords] NR_gNB_ULSCH_t *ulsch[NUMBER_OF_NR_ULSCH_MAX][2]; // [Nusers times][2 codewords]
NR_gNB_DLSCH_t *dlsch_SI,*dlsch_ra,*dlsch_p; NR_gNB_DLSCH_t *dlsch_SI,*dlsch_ra,*dlsch_p;
NR_gNB_DLSCH_t *dlsch_PCH; NR_gNB_DLSCH_t *dlsch_PCH;
...@@ -842,7 +838,8 @@ typedef struct PHY_VARS_gNB_s { ...@@ -842,7 +838,8 @@ typedef struct PHY_VARS_gNB_s {
/* /*
time_stats_t phy_proc; time_stats_t phy_proc;
*/ */
time_stats_t phy_proc_tx; time_stats_t *phy_proc_tx_0;
time_stats_t *phy_proc_tx_1;
time_stats_t phy_proc_rx; time_stats_t phy_proc_rx;
time_stats_t rx_prach; time_stats_t rx_prach;
/* /*
...@@ -932,6 +929,21 @@ typedef struct processingData_L1 { ...@@ -932,6 +929,21 @@ typedef struct processingData_L1 {
int slot_tx; int slot_tx;
openair0_timestamp timestamp_tx; openair0_timestamp timestamp_tx;
PHY_VARS_gNB *gNB; PHY_VARS_gNB *gNB;
} processingData_L1_t; };
typedef struct processingData_L1tx {
int frame_rx;
int frame_tx;
int slot_rx;
int slot_tx;
openair0_timestamp timestamp_tx;
PHY_VARS_gNB *gNB;
nfapi_nr_dl_tti_pdcch_pdu pdcch_pdu;
nfapi_nr_ul_dci_request_pdus_t ul_pdcch_pdu;
NR_gNB_DLSCH_t *dlsch[NUMBER_OF_NR_DLSCH_MAX][2];
NR_gNB_SSB_t ssb[64];
uint16_t num_pdsch_slot;
time_stats_t phy_proc_tx;
} processingData_L1tx_t;
#endif #endif
...@@ -43,7 +43,7 @@ extern int oai_nfapi_ul_tti_req(nfapi_nr_ul_tti_request_t *ul_tti_req); ...@@ -43,7 +43,7 @@ extern int oai_nfapi_ul_tti_req(nfapi_nr_ul_tti_request_t *ul_tti_req);
extern uint8_t nfapi_mode; extern uint8_t nfapi_mode;
void handle_nr_nfapi_ssb_pdu(PHY_VARS_gNB *gNB,int frame,int slot, void handle_nr_nfapi_ssb_pdu(processingData_L1tx_t *msgTx,int frame,int slot,
nfapi_nr_dl_tti_request_pdu_t *dl_tti_pdu) nfapi_nr_dl_tti_request_pdu_t *dl_tti_pdu)
{ {
...@@ -53,11 +53,11 @@ void handle_nr_nfapi_ssb_pdu(PHY_VARS_gNB *gNB,int frame,int slot, ...@@ -53,11 +53,11 @@ void handle_nr_nfapi_ssb_pdu(PHY_VARS_gNB *gNB,int frame,int slot,
uint8_t i_ssb = dl_tti_pdu->ssb_pdu.ssb_pdu_rel15.SsbBlockIndex; uint8_t i_ssb = dl_tti_pdu->ssb_pdu.ssb_pdu_rel15.SsbBlockIndex;
LOG_D(PHY,"%d.%d : ssb index %d pbch_pdu: %x\n",frame,slot,i_ssb,dl_tti_pdu->ssb_pdu.ssb_pdu_rel15.bchPayload); LOG_D(PHY,"%d.%d : ssb index %d pbch_pdu: %x\n",frame,slot,i_ssb,dl_tti_pdu->ssb_pdu.ssb_pdu_rel15.bchPayload);
if (gNB->ssb[i_ssb].active) if (msgTx->ssb[i_ssb].active)
AssertFatal(1==0,"SSB PDU with index %d already active\n",i_ssb); AssertFatal(1==0,"SSB PDU with index %d already active\n",i_ssb);
else { else {
gNB->ssb[i_ssb].active = true; msgTx->ssb[i_ssb].active = true;
memcpy((void*)&gNB->ssb[i_ssb].ssb_pdu,&dl_tti_pdu->ssb_pdu,sizeof(dl_tti_pdu->ssb_pdu)); memcpy((void*)&msgTx->ssb[i_ssb].ssb_pdu,&dl_tti_pdu->ssb_pdu,sizeof(dl_tti_pdu->ssb_pdu));
} }
} }
...@@ -128,13 +128,13 @@ void handle_nfapi_nr_ul_dci_pdu(PHY_VARS_gNB *gNB, ...@@ -128,13 +128,13 @@ void handle_nfapi_nr_ul_dci_pdu(PHY_VARS_gNB *gNB,
} }
void handle_nr_nfapi_pdsch_pdu(PHY_VARS_gNB *gNB,int frame,int slot, void handle_nr_nfapi_pdsch_pdu(processingData_L1tx_t *msgTx,
nfapi_nr_dl_tti_pdsch_pdu *pdsch_pdu, nfapi_nr_dl_tti_pdsch_pdu *pdsch_pdu,
uint8_t *sdu) uint8_t *sdu)
{ {
nr_fill_dlsch(gNB,frame,slot,pdsch_pdu,sdu); nr_fill_dlsch(msgTx,pdsch_pdu,sdu);
} }
...@@ -155,12 +155,9 @@ void nr_schedule_response(NR_Sched_Rsp_t *Sched_INFO){ ...@@ -155,12 +155,9 @@ void nr_schedule_response(NR_Sched_Rsp_t *Sched_INFO){
gNB = RC.gNB[Mod_id]; gNB = RC.gNB[Mod_id];
// we wait for the L1 Tx processing to finish before copying MAC PDUs to PHY
{
notifiedFIFO_elt_t *res; notifiedFIFO_elt_t *res;
res = pullTpool(gNB->resp_L1_tx, gNB->threadPool); res = pullTpool(gNB->resp_L1_tx, gNB->threadPool);
pushNotifiedFIFO(gNB->resp_L1_tx,res); processingData_L1tx_t *msgTx = (processingData_L1tx_t *)NotifiedFifoData(res);
}
uint8_t number_dl_pdu = (DL_req==NULL) ? 0 : DL_req->dl_tti_request_body.nPDUs; uint8_t number_dl_pdu = (DL_req==NULL) ? 0 : DL_req->dl_tti_request_body.nPDUs;
uint8_t number_ul_dci_pdu = (UL_dci_req==NULL) ? 0 : UL_dci_req->numPdus; uint8_t number_ul_dci_pdu = (UL_dci_req==NULL) ? 0 : UL_dci_req->numPdus;
...@@ -174,11 +171,7 @@ void nr_schedule_response(NR_Sched_Rsp_t *Sched_INFO){ ...@@ -174,11 +171,7 @@ void nr_schedule_response(NR_Sched_Rsp_t *Sched_INFO){
number_ul_dci_pdu,number_ul_tti_pdu); number_ul_dci_pdu,number_ul_tti_pdu);
int pdcch_received=0; int pdcch_received=0;
gNB->num_pdsch_rnti[slot]=0; msgTx->num_pdsch_slot=0;
for (int i=0; i<gNB->number_of_nr_dlsch_max; i++) {
gNB->dlsch[i][0]->rnti=0;
gNB->dlsch[i][0]->harq_mask=0;
}
for (int i=0;i<number_dl_pdu;i++) { for (int i=0;i<number_dl_pdu;i++) {
nfapi_nr_dl_tti_request_pdu_t *dl_tti_pdu = &DL_req->dl_tti_request_body.dl_tti_pdu_list[i]; nfapi_nr_dl_tti_request_pdu_t *dl_tti_pdu = &DL_req->dl_tti_request_body.dl_tti_pdu_list[i];
...@@ -187,7 +180,7 @@ void nr_schedule_response(NR_Sched_Rsp_t *Sched_INFO){ ...@@ -187,7 +180,7 @@ void nr_schedule_response(NR_Sched_Rsp_t *Sched_INFO){
case NFAPI_NR_DL_TTI_SSB_PDU_TYPE: case NFAPI_NR_DL_TTI_SSB_PDU_TYPE:
if(NFAPI_MODE != NFAPI_MODE_VNF) if(NFAPI_MODE != NFAPI_MODE_VNF)
handle_nr_nfapi_ssb_pdu(gNB,frame,slot, handle_nr_nfapi_ssb_pdu(msgTx,frame,slot,
dl_tti_pdu); dl_tti_pdu);
break; break;
...@@ -195,9 +188,7 @@ void nr_schedule_response(NR_Sched_Rsp_t *Sched_INFO){ ...@@ -195,9 +188,7 @@ void nr_schedule_response(NR_Sched_Rsp_t *Sched_INFO){
case NFAPI_NR_DL_TTI_PDCCH_PDU_TYPE: case NFAPI_NR_DL_TTI_PDCCH_PDU_TYPE:
AssertFatal(pdcch_received == 0, "pdcch_received is not 0, we can only handle one PDCCH PDU per slot\n"); AssertFatal(pdcch_received == 0, "pdcch_received is not 0, we can only handle one PDCCH PDU per slot\n");
if(NFAPI_MODE != NFAPI_MODE_VNF) if(NFAPI_MODE != NFAPI_MODE_VNF)
handle_nfapi_nr_pdcch_pdu(gNB, msgTx->pdcch_pdu = dl_tti_pdu->pdcch_pdu;
frame, slot,
&dl_tti_pdu->pdcch_pdu);
pdcch_received = 1; pdcch_received = 1;
...@@ -212,16 +203,15 @@ void nr_schedule_response(NR_Sched_Rsp_t *Sched_INFO){ ...@@ -212,16 +203,15 @@ void nr_schedule_response(NR_Sched_Rsp_t *Sched_INFO){
pduIndex,TX_req->pdu_list[pduIndex].num_TLV); pduIndex,TX_req->pdu_list[pduIndex].num_TLV);
uint8_t *sdu = (uint8_t *)TX_req->pdu_list[pduIndex].TLVs[0].value.direct; uint8_t *sdu = (uint8_t *)TX_req->pdu_list[pduIndex].TLVs[0].value.direct;
if(NFAPI_MODE != NFAPI_MODE_VNF) if(NFAPI_MODE != NFAPI_MODE_VNF)
handle_nr_nfapi_pdsch_pdu(gNB,frame,slot,&dl_tti_pdu->pdsch_pdu, sdu); handle_nr_nfapi_pdsch_pdu(msgTx,&dl_tti_pdu->pdsch_pdu, sdu);
} }
} }
} }
// if (UL_tti_req!=NULL) memcpy(&gNB->UL_tti_req,UL_tti_req,sizeof(nfapi_nr_ul_tti_request_t));
if(NFAPI_MODE != NFAPI_MODE_VNF) if(NFAPI_MODE != NFAPI_MODE_VNF)
for (int i=0;i<number_ul_dci_pdu;i++) { msgTx->ul_pdcch_pdu = UL_dci_req->ul_dci_pdu_list[number_ul_dci_pdu-1]; // copy the last pdu
handle_nfapi_nr_ul_dci_pdu(gNB, frame, slot, &UL_dci_req->ul_dci_pdu_list[i]);
} pushNotifiedFIFO(gNB->resp_L1_tx,res);
if(NFAPI_MODE != NFAPI_MODE_VNF) if(NFAPI_MODE != NFAPI_MODE_VNF)
for (int i = 0; i < number_ul_tti_pdu; i++) { for (int i = 0; i < number_ul_tti_pdu; i++) {
......
...@@ -37,7 +37,7 @@ ...@@ -37,7 +37,7 @@
#include "nfapi_nr_interface_scf.h" #include "nfapi_nr_interface_scf.h"
// added // added
void handle_nr_nfapi_ssb_pdu(PHY_VARS_gNB *gNB, void handle_nr_nfapi_ssb_pdu(processingData_L1tx_t *msgTx,
int frame,int slot, int frame,int slot,
nfapi_nr_dl_tti_request_pdu_t *dl_tti_pdu); nfapi_nr_dl_tti_request_pdu_t *dl_tti_pdu);
...@@ -47,7 +47,7 @@ void handle_nfapi_nr_pdcch_pdu(PHY_VARS_gNB *gNB, ...@@ -47,7 +47,7 @@ void handle_nfapi_nr_pdcch_pdu(PHY_VARS_gNB *gNB,
int frame, int subframe, int frame, int subframe,
nfapi_nr_dl_tti_pdcch_pdu *dcl_dl_pdu); nfapi_nr_dl_tti_pdcch_pdu *dcl_dl_pdu);
void handle_nr_nfapi_pdsch_pdu(PHY_VARS_gNB *gNB,int frame,int slot, void handle_nr_nfapi_pdsch_pdu(processingData_L1tx_t *msgTx,
nfapi_nr_dl_tti_pdsch_pdu *pdsch_pdu, nfapi_nr_dl_tti_pdsch_pdu *pdsch_pdu,
uint8_t *sdu); uint8_t *sdu);
......
...@@ -124,10 +124,12 @@ void nr_common_signal_procedures (PHY_VARS_gNB *gNB,int frame,int slot,nfapi_nr_ ...@@ -124,10 +124,12 @@ void nr_common_signal_procedures (PHY_VARS_gNB *gNB,int frame,int slot,nfapi_nr_
} }
void phy_procedures_gNB_TX(PHY_VARS_gNB *gNB, void phy_procedures_gNB_TX(processingData_L1tx_t *msgTx,
int frame,int slot, int frame,
int slot,
int do_meas) { int do_meas) {
int aa; int aa;
PHY_VARS_gNB *gNB = msgTx->gNB,
NR_DL_FRAME_PARMS *fp=&gNB->frame_parms; NR_DL_FRAME_PARMS *fp=&gNB->frame_parms;
nfapi_nr_config_request_scf_t *cfg = &gNB->gNB_config; nfapi_nr_config_request_scf_t *cfg = &gNB->gNB_config;
int offset = gNB->CC_id; int offset = gNB->CC_id;
...@@ -138,7 +140,7 @@ void phy_procedures_gNB_TX(PHY_VARS_gNB *gNB, ...@@ -138,7 +140,7 @@ void phy_procedures_gNB_TX(PHY_VARS_gNB *gNB,
VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_PROCEDURES_gNB_TX+offset,1); VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_PROCEDURES_gNB_TX+offset,1);
if (do_meas==1) start_meas(&gNB->phy_proc_tx); if (do_meas==1) start_meas(gNB->phy_proc_tx);
// clear the transmit data array and beam index for the current slot // clear the transmit data array and beam index for the current slot
for (aa=0; aa<cfg->carrier_config.num_tx_ant.value; aa++) { for (aa=0; aa<cfg->carrier_config.num_tx_ant.value; aa++) {
...@@ -149,54 +151,44 @@ void phy_procedures_gNB_TX(PHY_VARS_gNB *gNB, ...@@ -149,54 +151,44 @@ void phy_procedures_gNB_TX(PHY_VARS_gNB *gNB,
VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_PROCEDURES_gNB_COMMON_TX,1); VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_PROCEDURES_gNB_COMMON_TX,1);
if (NFAPI_MODE == NFAPI_MONOLITHIC || NFAPI_MODE == NFAPI_MODE_PNF) { if (NFAPI_MODE == NFAPI_MONOLITHIC || NFAPI_MODE == NFAPI_MODE_PNF) {
for (int i=0; i<fp->Lmax; i++) { for (int i=0; i<fp->Lmax; i++) {
if (gNB->ssb[i].active) { if (msgTx->ssb[i].active) {
nr_common_signal_procedures(gNB,frame,slot,gNB->ssb[i].ssb_pdu); nr_common_signal_procedures(gNB,frame,slot,msgTx->ssb[i].ssb_pdu);
gNB->ssb[i].active = false; msgTx->ssb[i].active = false;
} }
} }
} }
VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_PROCEDURES_gNB_COMMON_TX,0); VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_PROCEDURES_gNB_COMMON_TX,0);
int pdcch_pdu_id=find_nr_pdcch(frame,slot,gNB,SEARCH_EXIST);
int ul_pdcch_pdu_id=find_nr_ul_dci(frame,slot,gNB,SEARCH_EXIST);
LOG_D(PHY,"[gNB %d] Frame %d slot %d, pdcch_pdu_id %d, ul_pdcch_pdu_id %d\n", LOG_D(PHY,"[gNB %d] Frame %d slot %d, pdcch_pdu_id %d, ul_pdcch_pdu_id %d\n",
gNB->Mod_id,frame,slot,pdcch_pdu_id,ul_pdcch_pdu_id); gNB->Mod_id,frame,slot,pdcch_pdu_id,ul_pdcch_pdu_id);
int num_ul_dci = msgTx->ul_pdcch_pdu.pdcch_pdu.pdcch_pdu.pdcch_pdu_rel15.numDlDci;
int num_dl_dci = msgTx->pdcch_pdu.pdcch_pdu.pdcch_pdu_rel15.numDlDci;
if (pdcch_pdu_id >= 0 || ul_pdcch_pdu_id >= 0) { if (pdcch_pdu_id >= 0 || ul_pdcch_pdu_id >= 0) {
LOG_D(PHY, "[gNB %d] Frame %d slot %d Calling nr_generate_dci_top (number of UL/DL DCI %d/%d)\n", LOG_D(PHY, "[gNB %d] Frame %d slot %d Calling nr_generate_dci_top (number of UL/DL DCI %d/%d)\n",
gNB->Mod_id, frame, slot, gNB->Mod_id, frame, slot, num_dl_dci, num_ul_dci);
gNB->ul_pdcch_pdu[ul_pdcch_pdu_id].pdcch_pdu.pdcch_pdu.pdcch_pdu_rel15.numDlDci,
gNB->pdcch_pdu[pdcch_pdu_id].pdcch_pdu.pdcch_pdu_rel15.numDlDci);
VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_gNB_PDCCH_TX,1); VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_gNB_PDCCH_TX,1);
nr_generate_dci_top(gNB, nr_generate_dci_top(gNB,
pdcch_pdu_id>=0 ? &gNB->pdcch_pdu[pdcch_pdu_id].pdcch_pdu : NULL, num_dl_dci > 0 ? &msgTx->pdcch_pdu.pdcch_pdu : NULL,
ul_pdcch_pdu_id>=0 ? &gNB->ul_pdcch_pdu[ul_pdcch_pdu_id].pdcch_pdu.pdcch_pdu : NULL, num_ul_dci > 0 ? &msgTx->ul_pdcch_pdu.pdcch_pdu.pdcch_pdu : NULL,
gNB->nr_gold_pdcch_dmrs[slot], gNB->nr_gold_pdcch_dmrs[slot],
&gNB->common_vars.txdataF[0][txdataF_offset], &gNB->common_vars.txdataF[0][txdataF_offset],
AMP, *fp); AMP, *fp);
// free up entry in pdcch tables
if (pdcch_pdu_id>=0) gNB->pdcch_pdu[pdcch_pdu_id].frame = -1;
if (ul_pdcch_pdu_id>=0) gNB->ul_pdcch_pdu[ul_pdcch_pdu_id].frame = -1;
VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_gNB_PDCCH_TX,0); VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_gNB_PDCCH_TX,0);
if (pdcch_pdu_id >= 0) gNB->pdcch_pdu[pdcch_pdu_id].frame = -1;
if (ul_pdcch_pdu_id >= 0) gNB->ul_pdcch_pdu[ul_pdcch_pdu_id].frame = -1;
} }
for (int i=0; i<gNB->num_pdsch_rnti[slot]; i++) { for (int i=0; i<msgTx->num_pdsch_slot; i++) {
VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_GENERATE_DLSCH,1); VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_GENERATE_DLSCH,1);
LOG_D(PHY, "PDSCH generation started (%d) in frame %d.%d\n", gNB->num_pdsch_rnti[slot],frame,slot); LOG_D(PHY, "PDSCH generation started (%d) in frame %d.%d\n", msgTx->num_pdsch_slot,frame,slot);
nr_generate_pdsch(gNB,frame, slot); nr_generate_pdsch(msgTx, frame, slot);
VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_GENERATE_DLSCH,0); VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_GENERATE_DLSCH,0);
} }
if (do_meas==1) stop_meas(&gNB->phy_proc_tx); if (do_meas==1) stop_meas(gNB->phy_proc_tx);
if ((frame&127) == 0) dump_pdsch_stats(gNB);
//apply the OFDM symbol rotation here //apply the OFDM symbol rotation here
for (aa=0; aa<cfg->carrier_config.num_tx_ant.value; aa++) { for (aa=0; aa<cfg->carrier_config.num_tx_ant.value; aa++) {
......
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