reworking response to MSG3 with DCCH/DTCH
This commit is contained in:
@@ -799,7 +799,7 @@ int main(int argc, char **argv)
|
|||||||
N_RB_DL = gNB->frame_parms.N_RB_DL;
|
N_RB_DL = gNB->frame_parms.N_RB_DL;
|
||||||
NR_UE_info_t *UE_info = RC.nrmac[0]->UE_info.list[0];
|
NR_UE_info_t *UE_info = RC.nrmac[0]->UE_info.list[0];
|
||||||
|
|
||||||
configure_UE_BWP(RC.nrmac[0], scc, &UE_info->UE_sched_ctrl, NULL, UE_info);
|
configure_UE_BWP(RC.nrmac[0], scc, &UE_info->UE_sched_ctrl, NULL, UE_info, -1, -1);
|
||||||
|
|
||||||
// stub to configure frame_parms
|
// stub to configure frame_parms
|
||||||
// nr_phy_config_request_sim(gNB,N_RB_DL,N_RB_DL,mu,Nid_cell,SSB_positions);
|
// nr_phy_config_request_sim(gNB,N_RB_DL,N_RB_DL,mu,Nid_cell,SSB_positions);
|
||||||
|
|||||||
@@ -547,7 +547,6 @@ int rrc_mac_config_req_gNB(module_id_t Mod_idP,
|
|||||||
RC.nrmac[Mod_idP]->sib1_tda = sib1_tda;
|
RC.nrmac[Mod_idP]->sib1_tda = sib1_tda;
|
||||||
for (int n=0;n<NR_NB_RA_PROC_MAX;n++ ) {
|
for (int n=0;n<NR_NB_RA_PROC_MAX;n++ ) {
|
||||||
cc->ra[n].cfra = false;
|
cc->ra[n].cfra = false;
|
||||||
cc->ra[n].msg3_dcch_dtch = false;
|
|
||||||
cc->ra[n].rnti = 0;
|
cc->ra[n].rnti = 0;
|
||||||
cc->ra[n].preambles.num_preambles = MAX_NUM_NR_PRACH_PREAMBLES;
|
cc->ra[n].preambles.num_preambles = MAX_NUM_NR_PRACH_PREAMBLES;
|
||||||
cc->ra[n].preambles.preamble_list = (uint8_t *) malloc(MAX_NUM_NR_PRACH_PREAMBLES*sizeof(uint8_t));
|
cc->ra[n].preambles.preamble_list = (uint8_t *) malloc(MAX_NUM_NR_PRACH_PREAMBLES*sizeof(uint8_t));
|
||||||
@@ -613,7 +612,6 @@ int rrc_mac_config_req_gNB(module_id_t Mod_idP,
|
|||||||
for (int i = 0; i < MAX_NUM_NR_PRACH_PREAMBLES; i++)
|
for (int i = 0; i < MAX_NUM_NR_PRACH_PREAMBLES; i++)
|
||||||
ra->preambles.preamble_list[i] = i;
|
ra->preambles.preamble_list[i] = i;
|
||||||
}
|
}
|
||||||
ra->msg3_dcch_dtch = false;
|
|
||||||
LOG_I(NR_MAC,"Added new RA process for UE RNTI %04x with initial CellGroup\n", rnti);
|
LOG_I(NR_MAC,"Added new RA process for UE RNTI %04x with initial CellGroup\n", rnti);
|
||||||
} else { // CellGroup has been updated
|
} else { // CellGroup has been updated
|
||||||
NR_UE_info_t *UE = find_nr_UE(&RC.nrmac[Mod_idP]->UE_info, rnti);
|
NR_UE_info_t *UE = find_nr_UE(&RC.nrmac[Mod_idP]->UE_info, rnti);
|
||||||
|
|||||||
@@ -571,7 +571,7 @@ void nr_initiate_ra_proc(module_id_t module_idP,
|
|||||||
ra_rnti = 1 + symbol + (slotP * 14) + (freq_index * 14 * 80) + (ul_carrier_id * 14 * 80 * 8);
|
ra_rnti = 1 + symbol + (slotP * 14) + (freq_index * 14 * 80) + (ul_carrier_id * 14 * 80 * 8);
|
||||||
|
|
||||||
// Configure RA BWP
|
// Configure RA BWP
|
||||||
configure_UE_BWP(nr_mac, scc, NULL, ra, NULL);
|
configure_UE_BWP(nr_mac, scc, NULL, ra, NULL, -1, -1);
|
||||||
|
|
||||||
VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_INITIATE_RA_PROC, 1);
|
VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_INITIATE_RA_PROC, 1);
|
||||||
|
|
||||||
@@ -680,6 +680,8 @@ void nr_schedule_RA(module_id_t module_idP, frame_t frameP, sub_frame_t slotP) {
|
|||||||
case Msg3_retransmission:
|
case Msg3_retransmission:
|
||||||
nr_generate_Msg3_retransmission(module_idP, CC_id, frameP, slotP, ra);
|
nr_generate_Msg3_retransmission(module_idP, CC_id, frameP, slotP, ra);
|
||||||
break;
|
break;
|
||||||
|
case Msg3_dcch_dtch:
|
||||||
|
nr_generate_Msg3_dcch_dtch_response(module_idP, CC_id, frameP, slotP, ra);
|
||||||
case Msg4:
|
case Msg4:
|
||||||
nr_generate_Msg4(module_idP, CC_id, frameP, slotP, ra);
|
nr_generate_Msg4(module_idP, CC_id, frameP, slotP, ra);
|
||||||
break;
|
break;
|
||||||
@@ -1400,8 +1402,374 @@ void nr_generate_Msg2(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void nr_generate_Msg4(module_id_t module_idP, int CC_id, frame_t frameP, sub_frame_t slotP, NR_RA_t *ra) {
|
void prepare_dl_pdus(gNB_MAC_INST *nr_mac,
|
||||||
|
NR_RA_t *ra,
|
||||||
|
NR_UE_DL_BWP_t *dl_bwp,
|
||||||
|
nfapi_nr_dl_tti_request_body_t *dl_req,
|
||||||
|
NR_sched_pucch_t *pucch,
|
||||||
|
NR_pdsch_dmrs_t dmrs_info,
|
||||||
|
NR_tda_info_t tda,
|
||||||
|
int aggregation_level,
|
||||||
|
int CCEIndex,
|
||||||
|
int tb_size, int ndi,
|
||||||
|
int tpc, int delta_PRI,
|
||||||
|
int current_harq_pid,
|
||||||
|
int time_domain_assignment,
|
||||||
|
int CC_id, int rnti, int round,
|
||||||
|
int mcsIndex, int tb_scaling,
|
||||||
|
int pduindex, int rbStart, int rbSize)
|
||||||
|
{
|
||||||
|
// look up the PDCCH PDU for this CC, BWP, and CORESET. If it does not exist, create it. This is especially
|
||||||
|
// important if we have multiple RAs, and the DLSCH has to reuse them, so we need to mark them
|
||||||
|
NR_ControlResourceSet_t *coreset = ra->coreset;
|
||||||
|
const int coresetid = coreset->controlResourceSetId;
|
||||||
|
nfapi_nr_dl_tti_pdcch_pdu_rel15_t *pdcch_pdu_rel15 = nr_mac->pdcch_pdu_idx[CC_id][coresetid];
|
||||||
|
if (!pdcch_pdu_rel15) {
|
||||||
|
nfapi_nr_dl_tti_request_pdu_t *dl_tti_pdcch_pdu = &dl_req->dl_tti_pdu_list[dl_req->nPDUs];
|
||||||
|
memset(dl_tti_pdcch_pdu, 0, sizeof(nfapi_nr_dl_tti_request_pdu_t));
|
||||||
|
dl_tti_pdcch_pdu->PDUType = NFAPI_NR_DL_TTI_PDCCH_PDU_TYPE;
|
||||||
|
dl_tti_pdcch_pdu->PDUSize = (uint8_t)(2 + sizeof(nfapi_nr_dl_tti_pdcch_pdu));
|
||||||
|
dl_req->nPDUs += 1;
|
||||||
|
pdcch_pdu_rel15 = &dl_tti_pdcch_pdu->pdcch_pdu.pdcch_pdu_rel15;
|
||||||
|
nr_configure_pdcch(pdcch_pdu_rel15, coreset, false, &ra->sched_pdcch);
|
||||||
|
nr_mac->pdcch_pdu_idx[CC_id][coresetid] = pdcch_pdu_rel15;
|
||||||
|
}
|
||||||
|
|
||||||
|
nfapi_nr_dl_tti_request_pdu_t *dl_tti_pdsch_pdu = &dl_req->dl_tti_pdu_list[dl_req->nPDUs];
|
||||||
|
memset((void *)dl_tti_pdsch_pdu,0,sizeof(nfapi_nr_dl_tti_request_pdu_t));
|
||||||
|
dl_tti_pdsch_pdu->PDUType = NFAPI_NR_DL_TTI_PDSCH_PDU_TYPE;
|
||||||
|
dl_tti_pdsch_pdu->PDUSize = (uint8_t)(2+sizeof(nfapi_nr_dl_tti_pdsch_pdu));
|
||||||
|
dl_req->nPDUs+=1;
|
||||||
|
nfapi_nr_dl_tti_pdsch_pdu_rel15_t *pdsch_pdu_rel15 = &dl_tti_pdsch_pdu->pdsch_pdu.pdsch_pdu_rel15;
|
||||||
|
|
||||||
|
NR_COMMON_channels_t *cc = &nr_mac->common_channels[CC_id];
|
||||||
|
NR_ServingCellConfigCommon_t *scc = cc->ServingCellConfigCommon;
|
||||||
|
|
||||||
|
long BWPStart = 0;
|
||||||
|
long BWPSize = 0;
|
||||||
|
NR_Type0_PDCCH_CSS_config_t *type0_PDCCH_CSS_config = NULL;
|
||||||
|
NR_SearchSpace_t *ss = ra->ra_ss;
|
||||||
|
if(*ss->controlResourceSetId!=0) {
|
||||||
|
BWPStart = dl_bwp->BWPStart;
|
||||||
|
BWPSize = dl_bwp->BWPSize;
|
||||||
|
} else {
|
||||||
|
type0_PDCCH_CSS_config = &nr_mac->type0_PDCCH_CSS_config[ra->beam_id];
|
||||||
|
BWPStart = type0_PDCCH_CSS_config->cset_start_rb;
|
||||||
|
BWPSize = type0_PDCCH_CSS_config->num_rbs;
|
||||||
|
}
|
||||||
|
|
||||||
|
int mcsTableIdx = dl_bwp->mcsTableIdx;
|
||||||
|
|
||||||
|
pdsch_pdu_rel15->pduBitmap = 0;
|
||||||
|
pdsch_pdu_rel15->rnti = rnti;
|
||||||
|
pdsch_pdu_rel15->pduIndex = pduindex;
|
||||||
|
pdsch_pdu_rel15->BWPSize = BWPSize;
|
||||||
|
pdsch_pdu_rel15->BWPStart = BWPStart;
|
||||||
|
pdsch_pdu_rel15->SubcarrierSpacing = dl_bwp->scs;
|
||||||
|
pdsch_pdu_rel15->CyclicPrefix = 0;
|
||||||
|
pdsch_pdu_rel15->NrOfCodewords = 1;
|
||||||
|
int R = nr_get_code_rate_dl(mcsIndex,mcsTableIdx);
|
||||||
|
pdsch_pdu_rel15->targetCodeRate[0] = R;
|
||||||
|
int Qm = nr_get_Qm_dl(mcsIndex, mcsTableIdx);
|
||||||
|
pdsch_pdu_rel15->qamModOrder[0] = Qm;
|
||||||
|
pdsch_pdu_rel15->mcsIndex[0] = mcsIndex;
|
||||||
|
pdsch_pdu_rel15->mcsTable[0] = mcsTableIdx;
|
||||||
|
pdsch_pdu_rel15->rvIndex[0] = nr_rv_round_map[round % 4];
|
||||||
|
pdsch_pdu_rel15->dataScramblingId = *scc->physCellId;
|
||||||
|
pdsch_pdu_rel15->nrOfLayers = 1;
|
||||||
|
pdsch_pdu_rel15->transmissionScheme = 0;
|
||||||
|
pdsch_pdu_rel15->refPoint = 0;
|
||||||
|
pdsch_pdu_rel15->dmrsConfigType = dmrs_info.dmrsConfigType;
|
||||||
|
pdsch_pdu_rel15->dlDmrsScramblingId = *scc->physCellId;
|
||||||
|
pdsch_pdu_rel15->SCID = 0;
|
||||||
|
pdsch_pdu_rel15->numDmrsCdmGrpsNoData = dmrs_info.numDmrsCdmGrpsNoData;
|
||||||
|
pdsch_pdu_rel15->dmrsPorts = 1;
|
||||||
|
pdsch_pdu_rel15->resourceAlloc = 1;
|
||||||
|
pdsch_pdu_rel15->rbStart = rbStart;
|
||||||
|
pdsch_pdu_rel15->rbSize = rbSize;
|
||||||
|
pdsch_pdu_rel15->VRBtoPRBMapping = 0;
|
||||||
|
pdsch_pdu_rel15->StartSymbolIndex = tda.startSymbolIndex;
|
||||||
|
pdsch_pdu_rel15->NrOfSymbols = tda.nrOfSymbols;
|
||||||
|
pdsch_pdu_rel15->dlDmrsSymbPos = dmrs_info.dl_dmrs_symb_pos;
|
||||||
|
|
||||||
|
int x_Overhead = 0;
|
||||||
|
nr_get_tbs_dl(&dl_tti_pdsch_pdu->pdsch_pdu, x_Overhead, pdsch_pdu_rel15->numDmrsCdmGrpsNoData, tb_scaling);
|
||||||
|
|
||||||
|
int bw_tbslbrm = get_dlbw_tbslbrm(dl_bwp->initial_BWPSize, ra->CellGroup);
|
||||||
|
pdsch_pdu_rel15->maintenance_parms_v3.tbSizeLbrmBytes = nr_compute_tbslbrm(mcsTableIdx,
|
||||||
|
bw_tbslbrm,
|
||||||
|
1);
|
||||||
|
pdsch_pdu_rel15->maintenance_parms_v3.ldpcBaseGraph = get_BG(tb_size<<3,R);
|
||||||
|
|
||||||
|
pdsch_pdu_rel15->precodingAndBeamforming.num_prgs=1;
|
||||||
|
pdsch_pdu_rel15->precodingAndBeamforming.prg_size=275;
|
||||||
|
pdsch_pdu_rel15->precodingAndBeamforming.dig_bf_interfaces=1;
|
||||||
|
pdsch_pdu_rel15->precodingAndBeamforming.prgs_list[0].pm_idx = 0;
|
||||||
|
pdsch_pdu_rel15->precodingAndBeamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx = ra->beam_id;
|
||||||
|
|
||||||
|
/* Fill PDCCH DL DCI PDU */
|
||||||
|
nfapi_nr_dl_dci_pdu_t *dci_pdu = &pdcch_pdu_rel15->dci_pdu[pdcch_pdu_rel15->numDlDci];
|
||||||
|
pdcch_pdu_rel15->numDlDci++;
|
||||||
|
dci_pdu->RNTI = rnti;
|
||||||
|
dci_pdu->ScramblingId = *scc->physCellId;
|
||||||
|
dci_pdu->ScramblingRNTI = 0;
|
||||||
|
dci_pdu->AggregationLevel = aggregation_level;
|
||||||
|
dci_pdu->CceIndex = CCEIndex;
|
||||||
|
dci_pdu->beta_PDCCH_1_0 = 0;
|
||||||
|
dci_pdu->powerControlOffsetSS = 1;
|
||||||
|
|
||||||
|
dci_pdu_rel15_t dci_payload;
|
||||||
|
dci_payload.frequency_domain_assignment.val = PRBalloc_to_locationandbandwidth0(pdsch_pdu_rel15->rbSize,
|
||||||
|
pdsch_pdu_rel15->rbStart,
|
||||||
|
BWPSize);
|
||||||
|
|
||||||
|
dci_payload.format_indicator = 1;
|
||||||
|
dci_payload.time_domain_assignment.val = time_domain_assignment;
|
||||||
|
dci_payload.vrb_to_prb_mapping.val = 0;
|
||||||
|
dci_payload.mcs = pdsch_pdu_rel15->mcsIndex[0];
|
||||||
|
dci_payload.tb_scaling = tb_scaling;
|
||||||
|
dci_payload.rv = pdsch_pdu_rel15->rvIndex[0];
|
||||||
|
dci_payload.harq_pid = current_harq_pid;
|
||||||
|
dci_payload.ndi = ndi;
|
||||||
|
dci_payload.dai[0].val = pucch ? (pucch->dai_c-1) & 3 : 0;
|
||||||
|
dci_payload.tpc = tpc; // TPC for PUCCH: table 7.2.1-1 in 38.213
|
||||||
|
dci_payload.pucch_resource_indicator = delta_PRI; // This is delta_PRI from 9.2.1 in 38.213
|
||||||
|
dci_payload.pdsch_to_harq_feedback_timing_indicator.val = pucch ? pucch->timing_indicator : 0;
|
||||||
|
|
||||||
|
LOG_D(NR_MAC,
|
||||||
|
"[RAPROC] DCI 1_0 payload: freq_alloc %d (%d,%d,%d), time_alloc %d, vrb to prb %d, mcs %d tb_scaling %d pucchres %d harqtiming %d\n",
|
||||||
|
dci_payload.frequency_domain_assignment.val,
|
||||||
|
pdsch_pdu_rel15->rbStart,
|
||||||
|
pdsch_pdu_rel15->rbSize,
|
||||||
|
pdsch_pdu_rel15->BWPSize,
|
||||||
|
dci_payload.time_domain_assignment.val,
|
||||||
|
dci_payload.vrb_to_prb_mapping.val,
|
||||||
|
dci_payload.mcs,
|
||||||
|
dci_payload.tb_scaling,
|
||||||
|
dci_payload.pucch_resource_indicator,
|
||||||
|
dci_payload.pdsch_to_harq_feedback_timing_indicator.val);
|
||||||
|
|
||||||
|
LOG_D(NR_MAC,
|
||||||
|
"[RAPROC] DCI params: rnti 0x%x, rnti_type %d, dci_format %d coreset params: FreqDomainResource %llx, start_symbol %d n_symb %d, BWPsize %d\n",
|
||||||
|
pdcch_pdu_rel15->dci_pdu[0].RNTI,
|
||||||
|
NR_RNTI_TC,
|
||||||
|
NR_DL_DCI_FORMAT_1_0,
|
||||||
|
(unsigned long long)pdcch_pdu_rel15->FreqDomainResource,
|
||||||
|
pdcch_pdu_rel15->StartSymbolIndex,
|
||||||
|
pdcch_pdu_rel15->DurationSymbols,
|
||||||
|
pdsch_pdu_rel15->BWPSize);
|
||||||
|
|
||||||
|
fill_dci_pdu_rel15(scc,
|
||||||
|
ra->CellGroup,
|
||||||
|
dl_bwp,
|
||||||
|
&ra->UL_BWP,
|
||||||
|
&pdcch_pdu_rel15->dci_pdu[pdcch_pdu_rel15->numDlDci - 1],
|
||||||
|
&dci_payload,
|
||||||
|
NR_DL_DCI_FORMAT_1_0,
|
||||||
|
NR_RNTI_TC,
|
||||||
|
dl_bwp->bwp_id,
|
||||||
|
ss,
|
||||||
|
coreset,
|
||||||
|
nr_mac->cset0_bwp_size);
|
||||||
|
|
||||||
|
LOG_D(NR_MAC,"BWPSize: %i\n", pdcch_pdu_rel15->BWPSize);
|
||||||
|
LOG_D(NR_MAC,"BWPStart: %i\n", pdcch_pdu_rel15->BWPStart);
|
||||||
|
LOG_D(NR_MAC,"SubcarrierSpacing: %i\n", pdcch_pdu_rel15->SubcarrierSpacing);
|
||||||
|
LOG_D(NR_MAC,"CyclicPrefix: %i\n", pdcch_pdu_rel15->CyclicPrefix);
|
||||||
|
LOG_D(NR_MAC,"StartSymbolIndex: %i\n", pdcch_pdu_rel15->StartSymbolIndex);
|
||||||
|
LOG_D(NR_MAC,"DurationSymbols: %i\n", pdcch_pdu_rel15->DurationSymbols);
|
||||||
|
for(int n=0;n<6;n++) LOG_D(NR_MAC,"FreqDomainResource[%i]: %x\n",n, pdcch_pdu_rel15->FreqDomainResource[n]);
|
||||||
|
LOG_D(NR_MAC,"CceRegMappingType: %i\n", pdcch_pdu_rel15->CceRegMappingType);
|
||||||
|
LOG_D(NR_MAC,"RegBundleSize: %i\n", pdcch_pdu_rel15->RegBundleSize);
|
||||||
|
LOG_D(NR_MAC,"InterleaverSize: %i\n", pdcch_pdu_rel15->InterleaverSize);
|
||||||
|
LOG_D(NR_MAC,"CoreSetType: %i\n", pdcch_pdu_rel15->CoreSetType);
|
||||||
|
LOG_D(NR_MAC,"ShiftIndex: %i\n", pdcch_pdu_rel15->ShiftIndex);
|
||||||
|
LOG_D(NR_MAC,"precoderGranularity: %i\n", pdcch_pdu_rel15->precoderGranularity);
|
||||||
|
LOG_D(NR_MAC,"numDlDci: %i\n", pdcch_pdu_rel15->numDlDci);
|
||||||
|
}
|
||||||
|
|
||||||
|
void nr_generate_Msg3_dcch_dtch_response(module_id_t module_idP, int CC_id, frame_t frameP, sub_frame_t slotP, NR_RA_t *ra)
|
||||||
|
{
|
||||||
|
gNB_MAC_INST *nr_mac = RC.nrmac[module_idP];
|
||||||
|
|
||||||
|
// proceed only if it is a DL slot
|
||||||
|
if (!is_xlsch_in_slot(nr_mac->dlsch_slot_bitmap[slotP / 64], slotP))
|
||||||
|
return;
|
||||||
|
|
||||||
|
// UE is known by the network, C-RNTI to be used instead of TC-RNTI
|
||||||
|
int rnti = ra->crnti;
|
||||||
|
|
||||||
|
NR_UE_info_t *UE = find_nr_UE(&nr_mac->UE_info, rnti);
|
||||||
|
if (!UE) {
|
||||||
|
LOG_E(NR_MAC, "Received Msg3 with C-RNTI but rnti %04x not in the table\n", rnti);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
NR_COMMON_channels_t *cc = &nr_mac->common_channels[CC_id];
|
||||||
|
NR_ServingCellConfigCommon_t *scc = cc->ServingCellConfigCommon;
|
||||||
|
NR_SearchSpace_t *ss = ra->ra_ss;
|
||||||
|
|
||||||
|
NR_ControlResourceSet_t *coreset = ra->coreset;
|
||||||
|
AssertFatal(coreset!=NULL,"Coreset cannot be null for RA-Msg4\n");
|
||||||
|
|
||||||
|
// Only need to schedule DCI with and empty DL
|
||||||
|
NR_UE_DL_BWP_t *dl_bwp = &ra->DL_BWP;
|
||||||
|
long BWPStart = 0;
|
||||||
|
long BWPSize = 0;
|
||||||
|
NR_Type0_PDCCH_CSS_config_t *type0_PDCCH_CSS_config = NULL;
|
||||||
|
if(*ss->controlResourceSetId!=0) {
|
||||||
|
BWPStart = dl_bwp->BWPStart;
|
||||||
|
BWPSize = dl_bwp->BWPSize;
|
||||||
|
} else {
|
||||||
|
type0_PDCCH_CSS_config = &nr_mac->type0_PDCCH_CSS_config[ra->beam_id];
|
||||||
|
BWPStart = type0_PDCCH_CSS_config->cset_start_rb;
|
||||||
|
BWPSize = type0_PDCCH_CSS_config->num_rbs;
|
||||||
|
}
|
||||||
|
|
||||||
|
// get CCEindex, needed also for PUCCH and then later for PDCCH
|
||||||
|
uint8_t aggregation_level;
|
||||||
|
int CCEIndex = get_cce_index(nr_mac,
|
||||||
|
CC_id, slotP, 0,
|
||||||
|
&aggregation_level,
|
||||||
|
ss,
|
||||||
|
coreset,
|
||||||
|
&ra->sched_pdcch,
|
||||||
|
true);
|
||||||
|
|
||||||
|
if (CCEIndex < 0) {
|
||||||
|
LOG_E(NR_MAC, "%s(): cannot find free CCE for RA RNTI 0x%04x!\n", __func__, rnti);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Checking if the DCI allocation is feasible in current subframe
|
||||||
|
nfapi_nr_dl_tti_request_body_t *dl_req = &nr_mac->DL_req[CC_id].dl_tti_request_body;
|
||||||
|
if (dl_req->nPDUs > NFAPI_NR_MAX_DL_TTI_PDUS - 2) {
|
||||||
|
LOG_I(NR_MAC, "[RAPROC] Subframe %d: FAPI DL structure is full, skip scheduling UE %d\n", slotP, rnti);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
uint8_t time_domain_assignment = get_dl_tda(nr_mac, scc, slotP);
|
||||||
|
int mux_pattern = type0_PDCCH_CSS_config ? type0_PDCCH_CSS_config->type0_pdcch_ss_mux_pattern : 1;
|
||||||
|
NR_tda_info_t tda = get_dl_tda_info(dl_bwp, ss->searchSpaceType->present, time_domain_assignment,
|
||||||
|
scc->dmrs_TypeA_Position, mux_pattern, NR_RNTI_C, coreset->controlResourceSetId, false);
|
||||||
|
|
||||||
|
NR_pdsch_dmrs_t dmrs_info = get_dl_dmrs_params(scc,
|
||||||
|
dl_bwp,
|
||||||
|
&tda,
|
||||||
|
1);
|
||||||
|
|
||||||
|
int subheader_len = sizeof(NR_MAC_SUBHEADER_SHORT);
|
||||||
|
int pdu_length = subheader_len + 7; // 7 is contetion resolution length
|
||||||
|
|
||||||
|
int mcsTableIdx = dl_bwp->mcsTableIdx;
|
||||||
|
int mcsIndex = 0;
|
||||||
|
int rbStart = 0;
|
||||||
|
int rbSize = 0;
|
||||||
|
int tb_scaling = 0;
|
||||||
|
uint32_t tb_size = 0;
|
||||||
|
|
||||||
|
// increase PRBs until we get to BWPSize or TBS is bigger than MAC PDU size
|
||||||
|
do {
|
||||||
|
if(rbSize < BWPSize)
|
||||||
|
rbSize++;
|
||||||
|
else
|
||||||
|
mcsIndex++;
|
||||||
|
LOG_D(NR_MAC,"Calling nr_compute_tbs with N_PRB_DMRS %d, N_DMRS_SLOT %d\n",dmrs_info.N_PRB_DMRS,dmrs_info.N_DMRS_SLOT);
|
||||||
|
tb_size = nr_compute_tbs(nr_get_Qm_dl(mcsIndex, mcsTableIdx),
|
||||||
|
nr_get_code_rate_dl(mcsIndex, mcsTableIdx),
|
||||||
|
rbSize, tda.nrOfSymbols, dmrs_info.N_PRB_DMRS * dmrs_info.N_DMRS_SLOT, 0, tb_scaling,1) >> 3;
|
||||||
|
} while (tb_size < pdu_length && mcsIndex<=28);
|
||||||
|
|
||||||
|
AssertFatal(tb_size >= pdu_length,"Cannot allocate response to MSG3 with DCCH\n");
|
||||||
|
|
||||||
|
int i = 0;
|
||||||
|
uint16_t *vrb_map = cc[CC_id].vrb_map;
|
||||||
|
while ((i < rbSize) && (rbStart + rbSize <= BWPSize)) {
|
||||||
|
if (vrb_map[BWPStart + rbStart + i]&SL_to_bitmap(tda.startSymbolIndex, tda.nrOfSymbols)) {
|
||||||
|
rbStart += i+1;
|
||||||
|
i = 0;
|
||||||
|
} else {
|
||||||
|
i++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (rbStart > (BWPSize - rbSize)) {
|
||||||
|
LOG_E(NR_MAC, "%s(): cannot find free vrb_map for RNTI %04x!\n", __func__, rnti);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Remove UE associated to TC-RNTI
|
||||||
|
mac_remove_nr_ue(nr_mac, ra->rnti);
|
||||||
|
|
||||||
|
|
||||||
|
// If the UE used MSG3 to transfer a DCCH or DTCH message, then contention resolution is successful if the UE receives a PDCCH transmission which has its CRC bits scrambled by the C-RNTI
|
||||||
|
// Just send padding LCID
|
||||||
|
uint8_t buf[tb_size];
|
||||||
|
NR_MAC_SUBHEADER_FIXED *padding = (NR_MAC_SUBHEADER_FIXED *) &buf[0];
|
||||||
|
padding->R = 0;
|
||||||
|
padding->LCID = DL_SCH_LCID_PADDING;
|
||||||
|
for(int k = 1; k < tb_size; k++)
|
||||||
|
buf[k] = 0;
|
||||||
|
|
||||||
|
T(T_GNB_MAC_DL_PDU_WITH_DATA, T_INT(module_idP), T_INT(CC_id), T_INT(ra->rnti),
|
||||||
|
T_INT(frameP), T_INT(slotP), T_INT(0), T_BUFFER(buf, tb_size));
|
||||||
|
|
||||||
|
// SCF222: PDU index incremented for each PDSCH PDU sent in TX control message. This is used to associate control
|
||||||
|
// information to data and is reset every slot.
|
||||||
|
const int pduindex = nr_mac->pdu_index[CC_id]++;
|
||||||
|
|
||||||
|
prepare_dl_pdus(nr_mac, ra, dl_bwp, dl_req, NULL, dmrs_info, tda, aggregation_level, CCEIndex, tb_size, 0, 0, 0,
|
||||||
|
0, time_domain_assignment, CC_id, rnti, 0, mcsIndex, tb_scaling, pduindex, rbStart, rbSize);
|
||||||
|
|
||||||
|
// DL TX request
|
||||||
|
nfapi_nr_pdu_t *tx_req = &nr_mac->TX_req[CC_id].pdu_list[nr_mac->TX_req[CC_id].Number_of_PDUs];
|
||||||
|
memcpy(tx_req->TLVs[0].value.direct, buf, sizeof(uint8_t) * tb_size);
|
||||||
|
tx_req->PDU_length = tb_size;
|
||||||
|
tx_req->PDU_index = pduindex;
|
||||||
|
tx_req->num_TLV = 1;
|
||||||
|
tx_req->TLVs[0].length = tb_size + 2;
|
||||||
|
nr_mac->TX_req[CC_id].SFN = frameP;
|
||||||
|
nr_mac->TX_req[CC_id].Number_of_PDUs++;
|
||||||
|
nr_mac->TX_req[CC_id].Slot = slotP;
|
||||||
|
|
||||||
|
// Mark the corresponding symbols and RBs as used
|
||||||
|
fill_pdcch_vrb_map(nr_mac,
|
||||||
|
CC_id,
|
||||||
|
&ra->sched_pdcch,
|
||||||
|
CCEIndex,
|
||||||
|
aggregation_level);
|
||||||
|
for (int rb = 0; rb < rbSize; rb++)
|
||||||
|
vrb_map[BWPStart + rb + rbStart] |= SL_to_bitmap(tda.startSymbolIndex, tda.nrOfSymbols);
|
||||||
|
|
||||||
|
|
||||||
|
// If the UE used MSG3 to transfer a DCCH or DTCH message, then contention resolution is successful upon transmission of PDCCH
|
||||||
|
LOG_A(NR_MAC, "(ue rnti 0x%04x) CBRA procedure succeeded!\n", ra->rnti);
|
||||||
|
nr_clear_ra_proc(module_idP, CC_id, frameP, ra);
|
||||||
|
UE->Msg4_ACKed = true;
|
||||||
|
UE->ra_timer = 0;
|
||||||
|
|
||||||
|
if(!UE->CellGroup) {
|
||||||
|
// In the specific scenario where UE correctly received MSG4 (assuming it decoded RRCsetup with CellGroup) and gNB didn't correctly received an ACK,
|
||||||
|
// the UE would already have CG but the UE-dedicated gNB structure wouldn't (because RA didn't complete on gNB side).
|
||||||
|
uper_decode(NULL,
|
||||||
|
&asn_DEF_NR_CellGroupConfig, //might be added prefix later
|
||||||
|
(void **)&UE->CellGroup,
|
||||||
|
(uint8_t *)UE->cg_buf,
|
||||||
|
(UE->enc_rval.encoded+7)/8, 0, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
|
||||||
|
process_CellGroup(UE->CellGroup, sched_ctrl);
|
||||||
|
// switching to initial BWP
|
||||||
|
configure_UE_BWP(nr_mac, scc, sched_ctrl, NULL, UE, 0, 0);
|
||||||
|
|
||||||
|
// Reset uplink failure flags/counters/timers at MAC so gNB will resume again scheduling resources for this UE
|
||||||
|
sched_ctrl->pusch_consecutive_dtx_cnt = 0;
|
||||||
|
sched_ctrl->ul_failure = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
void nr_generate_Msg4(module_id_t module_idP, int CC_id, frame_t frameP, sub_frame_t slotP, NR_RA_t *ra)
|
||||||
|
{
|
||||||
gNB_MAC_INST *nr_mac = RC.nrmac[module_idP];
|
gNB_MAC_INST *nr_mac = RC.nrmac[module_idP];
|
||||||
NR_COMMON_channels_t *cc = &nr_mac->common_channels[CC_id];
|
NR_COMMON_channels_t *cc = &nr_mac->common_channels[CC_id];
|
||||||
NR_UE_DL_BWP_t *dl_bwp = &ra->DL_BWP;
|
NR_UE_DL_BWP_t *dl_bwp = &ra->DL_BWP;
|
||||||
@@ -1418,12 +1786,6 @@ void nr_generate_Msg4(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
|
|||||||
|
|
||||||
uint16_t mac_sdu_length = 0;
|
uint16_t mac_sdu_length = 0;
|
||||||
|
|
||||||
// If UE is known by the network, C-RNTI to be used instead of TC-RNTI
|
|
||||||
rnti_t tc_rnti = ra->rnti;
|
|
||||||
if (ra->msg3_dcch_dtch) {
|
|
||||||
ra->rnti = ra->crnti;
|
|
||||||
}
|
|
||||||
|
|
||||||
NR_UE_info_t *UE = find_nr_UE(&nr_mac->UE_info, ra->rnti);
|
NR_UE_info_t *UE = find_nr_UE(&nr_mac->UE_info, ra->rnti);
|
||||||
if (!UE) {
|
if (!UE) {
|
||||||
LOG_E(NR_MAC, "want to generate Msg4, but rnti %04x not in the table\n", ra->rnti);
|
LOG_E(NR_MAC, "want to generate Msg4, but rnti %04x not in the table\n", ra->rnti);
|
||||||
@@ -1435,7 +1797,7 @@ void nr_generate_Msg4(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
|
|||||||
int current_harq_pid = sched_ctrl->retrans_dl_harq.head;
|
int current_harq_pid = sched_ctrl->retrans_dl_harq.head;
|
||||||
|
|
||||||
logical_chan_id_t lcid = DL_SCH_LCID_CCCH;
|
logical_chan_id_t lcid = DL_SCH_LCID_CCCH;
|
||||||
if (ra->msg3_dcch_dtch == false && current_harq_pid < 0) {
|
if (current_harq_pid < 0) {
|
||||||
// Check for data on SRB0 (RRCSetup)
|
// Check for data on SRB0 (RRCSetup)
|
||||||
mac_rlc_status_resp_t srb_status = mac_rlc_status_ind(module_idP, ra->rnti, module_idP, frameP, slotP, ENB_FLAG_YES, MBMS_FLAG_NO, lcid, 0, 0);
|
mac_rlc_status_resp_t srb_status = mac_rlc_status_ind(module_idP, ra->rnti, module_idP, frameP, slotP, ENB_FLAG_YES, MBMS_FLAG_NO, lcid, 0, 0);
|
||||||
|
|
||||||
@@ -1543,7 +1905,7 @@ void nr_generate_Msg4(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
const int delta_PRI=0;
|
const int delta_PRI = 0;
|
||||||
int r_pucch = nr_get_pucch_resource(coreset, ra->UL_BWP.pucch_Config, CCEIndex);
|
int r_pucch = nr_get_pucch_resource(coreset, ra->UL_BWP.pucch_Config, CCEIndex);
|
||||||
|
|
||||||
LOG_D(NR_MAC,"[RAPROC] Msg4 r_pucch %d (CCEIndex %d, delta_PRI %d)\n", r_pucch, CCEIndex, delta_PRI);
|
LOG_D(NR_MAC,"[RAPROC] Msg4 r_pucch %d (CCEIndex %d, delta_PRI %d)\n", r_pucch, CCEIndex, delta_PRI);
|
||||||
@@ -1569,11 +1931,6 @@ void nr_generate_Msg4(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
|
|||||||
harq->is_waiting = true;
|
harq->is_waiting = true;
|
||||||
ra->harq_pid = current_harq_pid;
|
ra->harq_pid = current_harq_pid;
|
||||||
|
|
||||||
// Remove UE associated to TC-RNTI
|
|
||||||
if(harq->round==0 && ra->msg3_dcch_dtch) {
|
|
||||||
mac_remove_nr_ue(nr_mac, tc_rnti);
|
|
||||||
}
|
|
||||||
|
|
||||||
NR_sched_pucch_t *pucch = &sched_ctrl->sched_pucch[alloc];
|
NR_sched_pucch_t *pucch = &sched_ctrl->sched_pucch[alloc];
|
||||||
harq->feedback_slot = pucch->ul_slot;
|
harq->feedback_slot = pucch->ul_slot;
|
||||||
harq->feedback_frame = pucch->frame;
|
harq->feedback_frame = pucch->frame;
|
||||||
@@ -1582,187 +1939,45 @@ void nr_generate_Msg4(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
|
|||||||
uint8_t *buf = (uint8_t *) harq->transportBlock;
|
uint8_t *buf = (uint8_t *) harq->transportBlock;
|
||||||
// Bytes to be transmitted
|
// Bytes to be transmitted
|
||||||
if (harq->round == 0) {
|
if (harq->round == 0) {
|
||||||
if (ra->msg3_dcch_dtch) {
|
// UE Contention Resolution Identity MAC CE
|
||||||
// If the UE used MSG3 to transfer a DCCH or DTCH message, then contention resolution is successful if the UE receives a PDCCH transmission which has its CRC bits scrambled by the C-RNTI
|
uint16_t mac_pdu_length = nr_write_ce_dlsch_pdu(module_idP, nr_mac->sched_ctrlCommon, buf, 255, ra->cont_res_id);
|
||||||
// Just send padding LCID
|
LOG_D(NR_MAC,"Encoded contention resolution mac_pdu_length %d\n",mac_pdu_length);
|
||||||
ra->mac_pdu_length = 0;
|
uint8_t buffer[CCCH_SDU_SIZE];
|
||||||
|
uint8_t mac_subheader_len = sizeof(NR_MAC_SUBHEADER_SHORT);
|
||||||
|
// Get RLC data on the SRB (RRCSetup, RRCReestablishment)
|
||||||
|
mac_sdu_length = mac_rlc_data_req(module_idP,
|
||||||
|
ra->rnti,
|
||||||
|
module_idP,
|
||||||
|
frameP,
|
||||||
|
ENB_FLAG_YES,
|
||||||
|
MBMS_FLAG_NO,
|
||||||
|
lcid,
|
||||||
|
CCCH_SDU_SIZE,
|
||||||
|
(char *)buffer,
|
||||||
|
0,
|
||||||
|
0);
|
||||||
|
|
||||||
|
if (mac_sdu_length < 256) {
|
||||||
|
((NR_MAC_SUBHEADER_SHORT *)&buf[mac_pdu_length])->R = 0;
|
||||||
|
((NR_MAC_SUBHEADER_SHORT *)&buf[mac_pdu_length])->F = 0;
|
||||||
|
((NR_MAC_SUBHEADER_SHORT *)&buf[mac_pdu_length])->LCID = lcid;
|
||||||
|
((NR_MAC_SUBHEADER_SHORT *)&buf[mac_pdu_length])->L = mac_sdu_length;
|
||||||
|
ra->mac_pdu_length = mac_pdu_length + mac_sdu_length + sizeof(NR_MAC_SUBHEADER_SHORT);
|
||||||
} else {
|
} else {
|
||||||
// UE Contention Resolution Identity MAC CE
|
mac_subheader_len = sizeof(NR_MAC_SUBHEADER_LONG);
|
||||||
uint16_t mac_pdu_length = nr_write_ce_dlsch_pdu(module_idP, nr_mac->sched_ctrlCommon, buf, 255, ra->cont_res_id);
|
((NR_MAC_SUBHEADER_LONG *)&buf[mac_pdu_length])->R = 0;
|
||||||
LOG_D(NR_MAC,"Encoded contention resolution mac_pdu_length %d\n",mac_pdu_length);
|
((NR_MAC_SUBHEADER_LONG *)&buf[mac_pdu_length])->F = 1;
|
||||||
uint8_t buffer[CCCH_SDU_SIZE];
|
((NR_MAC_SUBHEADER_LONG *)&buf[mac_pdu_length])->LCID = lcid;
|
||||||
uint8_t mac_subheader_len = sizeof(NR_MAC_SUBHEADER_SHORT);
|
((NR_MAC_SUBHEADER_LONG *)&buf[mac_pdu_length])->L = htons(mac_sdu_length);
|
||||||
// Get RLC data on the SRB (RRCSetup, RRCReestablishment)
|
ra->mac_pdu_length = mac_pdu_length + mac_sdu_length + sizeof(NR_MAC_SUBHEADER_LONG);
|
||||||
mac_sdu_length = mac_rlc_data_req(module_idP,
|
|
||||||
ra->rnti,
|
|
||||||
module_idP,
|
|
||||||
frameP,
|
|
||||||
ENB_FLAG_YES,
|
|
||||||
MBMS_FLAG_NO,
|
|
||||||
lcid,
|
|
||||||
CCCH_SDU_SIZE,
|
|
||||||
(char *)buffer,
|
|
||||||
0,
|
|
||||||
0);
|
|
||||||
|
|
||||||
if (mac_sdu_length < 256) {
|
|
||||||
((NR_MAC_SUBHEADER_SHORT *)&buf[mac_pdu_length])->R = 0;
|
|
||||||
((NR_MAC_SUBHEADER_SHORT *)&buf[mac_pdu_length])->F = 0;
|
|
||||||
((NR_MAC_SUBHEADER_SHORT *)&buf[mac_pdu_length])->LCID = lcid;
|
|
||||||
((NR_MAC_SUBHEADER_SHORT *)&buf[mac_pdu_length])->L = mac_sdu_length;
|
|
||||||
ra->mac_pdu_length = mac_pdu_length + mac_sdu_length + sizeof(NR_MAC_SUBHEADER_SHORT);
|
|
||||||
} else {
|
|
||||||
mac_subheader_len = sizeof(NR_MAC_SUBHEADER_LONG);
|
|
||||||
((NR_MAC_SUBHEADER_LONG *)&buf[mac_pdu_length])->R = 0;
|
|
||||||
((NR_MAC_SUBHEADER_LONG *)&buf[mac_pdu_length])->F = 1;
|
|
||||||
((NR_MAC_SUBHEADER_LONG *)&buf[mac_pdu_length])->LCID = lcid;
|
|
||||||
((NR_MAC_SUBHEADER_LONG *)&buf[mac_pdu_length])->L = htons(mac_sdu_length);
|
|
||||||
ra->mac_pdu_length = mac_pdu_length + mac_sdu_length + sizeof(NR_MAC_SUBHEADER_LONG);
|
|
||||||
}
|
|
||||||
LOG_I(NR_MAC,"Encoded RRCSetup Piggyback (%d + %d bytes), mac_pdu_length %d\n", mac_sdu_length, mac_subheader_len, ra->mac_pdu_length);
|
|
||||||
memcpy(&buf[mac_pdu_length + mac_subheader_len], buffer, mac_sdu_length);
|
|
||||||
}
|
}
|
||||||
|
LOG_I(NR_MAC,"Encoded RRCSetup Piggyback (%d + %d bytes), mac_pdu_length %d\n", mac_sdu_length, mac_subheader_len, ra->mac_pdu_length);
|
||||||
|
memcpy(&buf[mac_pdu_length + mac_subheader_len], buffer, mac_sdu_length);
|
||||||
}
|
}
|
||||||
|
|
||||||
// look up the PDCCH PDU for this CC, BWP, and CORESET. If it does not exist, create it. This is especially
|
|
||||||
// important if we have multiple RAs, and the DLSCH has to reuse them, so we need to mark them
|
|
||||||
const int coresetid = coreset->controlResourceSetId;
|
|
||||||
nfapi_nr_dl_tti_pdcch_pdu_rel15_t *pdcch_pdu_rel15 = nr_mac->pdcch_pdu_idx[CC_id][coresetid];
|
|
||||||
if (!pdcch_pdu_rel15) {
|
|
||||||
nfapi_nr_dl_tti_request_pdu_t *dl_tti_pdcch_pdu = &dl_req->dl_tti_pdu_list[dl_req->nPDUs];
|
|
||||||
memset(dl_tti_pdcch_pdu, 0, sizeof(nfapi_nr_dl_tti_request_pdu_t));
|
|
||||||
dl_tti_pdcch_pdu->PDUType = NFAPI_NR_DL_TTI_PDCCH_PDU_TYPE;
|
|
||||||
dl_tti_pdcch_pdu->PDUSize = (uint8_t)(2 + sizeof(nfapi_nr_dl_tti_pdcch_pdu));
|
|
||||||
dl_req->nPDUs += 1;
|
|
||||||
pdcch_pdu_rel15 = &dl_tti_pdcch_pdu->pdcch_pdu.pdcch_pdu_rel15;
|
|
||||||
nr_configure_pdcch(pdcch_pdu_rel15, coreset, false, &ra->sched_pdcch);
|
|
||||||
nr_mac->pdcch_pdu_idx[CC_id][coresetid] = pdcch_pdu_rel15;
|
|
||||||
}
|
|
||||||
|
|
||||||
nfapi_nr_dl_tti_request_pdu_t *dl_tti_pdsch_pdu = &dl_req->dl_tti_pdu_list[dl_req->nPDUs];
|
|
||||||
memset((void *)dl_tti_pdsch_pdu,0,sizeof(nfapi_nr_dl_tti_request_pdu_t));
|
|
||||||
dl_tti_pdsch_pdu->PDUType = NFAPI_NR_DL_TTI_PDSCH_PDU_TYPE;
|
|
||||||
dl_tti_pdsch_pdu->PDUSize = (uint8_t)(2+sizeof(nfapi_nr_dl_tti_pdsch_pdu));
|
|
||||||
dl_req->nPDUs+=1;
|
|
||||||
nfapi_nr_dl_tti_pdsch_pdu_rel15_t *pdsch_pdu_rel15 = &dl_tti_pdsch_pdu->pdsch_pdu.pdsch_pdu_rel15;
|
|
||||||
|
|
||||||
LOG_A(NR_MAC, "[gNB %d] [RAPROC] CC_id %d Frame %d, slotP %d: Generating RA-Msg4 DCI, state %d\n", module_idP, CC_id, frameP, slotP, ra->state);
|
|
||||||
|
|
||||||
// SCF222: PDU index incremented for each PDSCH PDU sent in TX control message. This is used to associate control
|
|
||||||
// information to data and is reset every slot.
|
|
||||||
const int pduindex = nr_mac->pdu_index[CC_id]++;
|
const int pduindex = nr_mac->pdu_index[CC_id]++;
|
||||||
|
prepare_dl_pdus(nr_mac, ra, dl_bwp, dl_req, pucch, dmrs_info, msg4_tda, aggregation_level, CCEIndex, tb_size, harq->ndi, sched_ctrl->tpc1, delta_PRI,
|
||||||
pdsch_pdu_rel15->pduBitmap = 0;
|
current_harq_pid, time_domain_assignment, CC_id, ra->rnti, harq->round, mcsIndex, tb_scaling, pduindex, rbStart, rbSize);
|
||||||
pdsch_pdu_rel15->rnti = ra->rnti;
|
|
||||||
pdsch_pdu_rel15->pduIndex = pduindex;
|
|
||||||
pdsch_pdu_rel15->BWPSize = BWPSize;
|
|
||||||
pdsch_pdu_rel15->BWPStart = BWPStart;
|
|
||||||
pdsch_pdu_rel15->SubcarrierSpacing = dl_bwp->scs;
|
|
||||||
pdsch_pdu_rel15->CyclicPrefix = 0;
|
|
||||||
pdsch_pdu_rel15->NrOfCodewords = 1;
|
|
||||||
int R = nr_get_code_rate_dl(mcsIndex,mcsTableIdx);
|
|
||||||
pdsch_pdu_rel15->targetCodeRate[0] = R;
|
|
||||||
int Qm = nr_get_Qm_dl(mcsIndex, mcsTableIdx);
|
|
||||||
pdsch_pdu_rel15->qamModOrder[0] = Qm;
|
|
||||||
pdsch_pdu_rel15->mcsIndex[0] = mcsIndex;
|
|
||||||
pdsch_pdu_rel15->mcsTable[0] = mcsTableIdx;
|
|
||||||
pdsch_pdu_rel15->rvIndex[0] = nr_rv_round_map[harq->round%4];
|
|
||||||
pdsch_pdu_rel15->dataScramblingId = *scc->physCellId;
|
|
||||||
pdsch_pdu_rel15->nrOfLayers = 1;
|
|
||||||
pdsch_pdu_rel15->transmissionScheme = 0;
|
|
||||||
pdsch_pdu_rel15->refPoint = 0;
|
|
||||||
pdsch_pdu_rel15->dmrsConfigType = dmrs_info.dmrsConfigType;
|
|
||||||
pdsch_pdu_rel15->dlDmrsScramblingId = *scc->physCellId;
|
|
||||||
pdsch_pdu_rel15->SCID = 0;
|
|
||||||
pdsch_pdu_rel15->numDmrsCdmGrpsNoData = dmrs_info.numDmrsCdmGrpsNoData;
|
|
||||||
pdsch_pdu_rel15->dmrsPorts = 1;
|
|
||||||
pdsch_pdu_rel15->resourceAlloc = 1;
|
|
||||||
pdsch_pdu_rel15->rbStart = rbStart;
|
|
||||||
pdsch_pdu_rel15->rbSize = rbSize;
|
|
||||||
pdsch_pdu_rel15->VRBtoPRBMapping = 0;
|
|
||||||
pdsch_pdu_rel15->StartSymbolIndex = msg4_tda.startSymbolIndex;
|
|
||||||
pdsch_pdu_rel15->NrOfSymbols = msg4_tda.nrOfSymbols;
|
|
||||||
pdsch_pdu_rel15->dlDmrsSymbPos = dmrs_info.dl_dmrs_symb_pos;
|
|
||||||
|
|
||||||
int x_Overhead = 0;
|
|
||||||
nr_get_tbs_dl(&dl_tti_pdsch_pdu->pdsch_pdu, x_Overhead, pdsch_pdu_rel15->numDmrsCdmGrpsNoData, tb_scaling);
|
|
||||||
|
|
||||||
int bw_tbslbrm = get_dlbw_tbslbrm(dl_bwp->initial_BWPSize, ra->CellGroup);
|
|
||||||
pdsch_pdu_rel15->maintenance_parms_v3.tbSizeLbrmBytes = nr_compute_tbslbrm(mcsTableIdx,
|
|
||||||
bw_tbslbrm,
|
|
||||||
1);
|
|
||||||
pdsch_pdu_rel15->maintenance_parms_v3.ldpcBaseGraph = get_BG(harq->tb_size<<3,R);
|
|
||||||
|
|
||||||
pdsch_pdu_rel15->precodingAndBeamforming.num_prgs=1;
|
|
||||||
pdsch_pdu_rel15->precodingAndBeamforming.prg_size=275;
|
|
||||||
pdsch_pdu_rel15->precodingAndBeamforming.dig_bf_interfaces=1;
|
|
||||||
pdsch_pdu_rel15->precodingAndBeamforming.prgs_list[0].pm_idx = 0;
|
|
||||||
pdsch_pdu_rel15->precodingAndBeamforming.prgs_list[0].dig_bf_interface_list[0].beam_idx = ra->beam_id;
|
|
||||||
|
|
||||||
/* Fill PDCCH DL DCI PDU */
|
|
||||||
nfapi_nr_dl_dci_pdu_t *dci_pdu = &pdcch_pdu_rel15->dci_pdu[pdcch_pdu_rel15->numDlDci];
|
|
||||||
pdcch_pdu_rel15->numDlDci++;
|
|
||||||
dci_pdu->RNTI = ra->rnti;
|
|
||||||
dci_pdu->ScramblingId = *scc->physCellId;
|
|
||||||
dci_pdu->ScramblingRNTI = 0;
|
|
||||||
dci_pdu->AggregationLevel = aggregation_level;
|
|
||||||
dci_pdu->CceIndex = CCEIndex;
|
|
||||||
dci_pdu->beta_PDCCH_1_0 = 0;
|
|
||||||
dci_pdu->powerControlOffsetSS = 1;
|
|
||||||
|
|
||||||
dci_pdu_rel15_t dci_payload;
|
|
||||||
dci_payload.frequency_domain_assignment.val = PRBalloc_to_locationandbandwidth0(pdsch_pdu_rel15->rbSize,
|
|
||||||
pdsch_pdu_rel15->rbStart,
|
|
||||||
BWPSize);
|
|
||||||
|
|
||||||
dci_payload.format_indicator = 1;
|
|
||||||
dci_payload.time_domain_assignment.val = time_domain_assignment;
|
|
||||||
dci_payload.vrb_to_prb_mapping.val = 0;
|
|
||||||
dci_payload.mcs = pdsch_pdu_rel15->mcsIndex[0];
|
|
||||||
dci_payload.tb_scaling = tb_scaling;
|
|
||||||
dci_payload.rv = pdsch_pdu_rel15->rvIndex[0];
|
|
||||||
dci_payload.harq_pid = current_harq_pid;
|
|
||||||
dci_payload.ndi = harq->ndi;
|
|
||||||
dci_payload.dai[0].val = (pucch->dai_c-1)&3;
|
|
||||||
dci_payload.tpc = sched_ctrl->tpc1; // TPC for PUCCH: table 7.2.1-1 in 38.213
|
|
||||||
dci_payload.pucch_resource_indicator = delta_PRI; // This is delta_PRI from 9.2.1 in 38.213
|
|
||||||
dci_payload.pdsch_to_harq_feedback_timing_indicator.val = pucch->timing_indicator;
|
|
||||||
|
|
||||||
LOG_D(NR_MAC,
|
|
||||||
"[RAPROC] DCI 1_0 payload: freq_alloc %d (%d,%d,%d), time_alloc %d, vrb to prb %d, mcs %d tb_scaling %d pucchres %d harqtiming %d\n",
|
|
||||||
dci_payload.frequency_domain_assignment.val,
|
|
||||||
pdsch_pdu_rel15->rbStart,
|
|
||||||
pdsch_pdu_rel15->rbSize,
|
|
||||||
pdsch_pdu_rel15->BWPSize,
|
|
||||||
dci_payload.time_domain_assignment.val,
|
|
||||||
dci_payload.vrb_to_prb_mapping.val,
|
|
||||||
dci_payload.mcs,
|
|
||||||
dci_payload.tb_scaling,
|
|
||||||
dci_payload.pucch_resource_indicator,
|
|
||||||
dci_payload.pdsch_to_harq_feedback_timing_indicator.val);
|
|
||||||
|
|
||||||
LOG_D(NR_MAC,
|
|
||||||
"[RAPROC] DCI params: rnti 0x%x, rnti_type %d, dci_format %d coreset params: FreqDomainResource %llx, start_symbol %d n_symb %d, BWPsize %d\n",
|
|
||||||
pdcch_pdu_rel15->dci_pdu[0].RNTI,
|
|
||||||
NR_RNTI_TC,
|
|
||||||
NR_DL_DCI_FORMAT_1_0,
|
|
||||||
(unsigned long long)pdcch_pdu_rel15->FreqDomainResource,
|
|
||||||
pdcch_pdu_rel15->StartSymbolIndex,
|
|
||||||
pdcch_pdu_rel15->DurationSymbols,
|
|
||||||
pdsch_pdu_rel15->BWPSize);
|
|
||||||
|
|
||||||
fill_dci_pdu_rel15(scc,
|
|
||||||
ra->CellGroup,
|
|
||||||
dl_bwp,
|
|
||||||
&ra->UL_BWP,
|
|
||||||
&pdcch_pdu_rel15->dci_pdu[pdcch_pdu_rel15->numDlDci - 1],
|
|
||||||
&dci_payload,
|
|
||||||
NR_DL_DCI_FORMAT_1_0,
|
|
||||||
NR_RNTI_TC,
|
|
||||||
dl_bwp->bwp_id,
|
|
||||||
ss,
|
|
||||||
coreset,
|
|
||||||
nr_mac->cset0_bwp_size);
|
|
||||||
|
|
||||||
// Add padding header and zero rest out if there is space left
|
// Add padding header and zero rest out if there is space left
|
||||||
if (ra->mac_pdu_length < harq->tb_size) {
|
if (ra->mac_pdu_length < harq->tb_size) {
|
||||||
@@ -1794,58 +2009,12 @@ void nr_generate_Msg4(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
|
|||||||
&ra->sched_pdcch,
|
&ra->sched_pdcch,
|
||||||
CCEIndex,
|
CCEIndex,
|
||||||
aggregation_level);
|
aggregation_level);
|
||||||
for (int rb = 0; rb < pdsch_pdu_rel15->rbSize; rb++) {
|
for (int rb = 0; rb < rbSize; rb++) {
|
||||||
vrb_map[BWPStart + rb + pdsch_pdu_rel15->rbStart] |= SL_to_bitmap(msg4_tda.startSymbolIndex, msg4_tda.nrOfSymbols);
|
vrb_map[BWPStart + rb + rbStart] |= SL_to_bitmap(msg4_tda.startSymbolIndex, msg4_tda.nrOfSymbols);
|
||||||
}
|
}
|
||||||
|
|
||||||
LOG_D(NR_MAC,"BWPSize: %i\n", pdcch_pdu_rel15->BWPSize);
|
ra->state = WAIT_Msg4_ACK;
|
||||||
LOG_D(NR_MAC,"BWPStart: %i\n", pdcch_pdu_rel15->BWPStart);
|
LOG_D(NR_MAC,"[gNB %d][RAPROC] Frame %d, Subframe %d: RA state %d\n", module_idP, frameP, slotP, ra->state);
|
||||||
LOG_D(NR_MAC,"SubcarrierSpacing: %i\n", pdcch_pdu_rel15->SubcarrierSpacing);
|
|
||||||
LOG_D(NR_MAC,"CyclicPrefix: %i\n", pdcch_pdu_rel15->CyclicPrefix);
|
|
||||||
LOG_D(NR_MAC,"StartSymbolIndex: %i\n", pdcch_pdu_rel15->StartSymbolIndex);
|
|
||||||
LOG_D(NR_MAC,"DurationSymbols: %i\n", pdcch_pdu_rel15->DurationSymbols);
|
|
||||||
for(int n=0;n<6;n++) LOG_D(NR_MAC,"FreqDomainResource[%i]: %x\n",n, pdcch_pdu_rel15->FreqDomainResource[n]);
|
|
||||||
LOG_D(NR_MAC,"CceRegMappingType: %i\n", pdcch_pdu_rel15->CceRegMappingType);
|
|
||||||
LOG_D(NR_MAC,"RegBundleSize: %i\n", pdcch_pdu_rel15->RegBundleSize);
|
|
||||||
LOG_D(NR_MAC,"InterleaverSize: %i\n", pdcch_pdu_rel15->InterleaverSize);
|
|
||||||
LOG_D(NR_MAC,"CoreSetType: %i\n", pdcch_pdu_rel15->CoreSetType);
|
|
||||||
LOG_D(NR_MAC,"ShiftIndex: %i\n", pdcch_pdu_rel15->ShiftIndex);
|
|
||||||
LOG_D(NR_MAC,"precoderGranularity: %i\n", pdcch_pdu_rel15->precoderGranularity);
|
|
||||||
LOG_D(NR_MAC,"numDlDci: %i\n", pdcch_pdu_rel15->numDlDci);
|
|
||||||
|
|
||||||
if(ra->msg3_dcch_dtch) {
|
|
||||||
// If the UE used MSG3 to transfer a DCCH or DTCH message, then contention resolution is successful upon transmission of PDCCH
|
|
||||||
LOG_A(NR_MAC, "(ue rnti 0x%04x) CBRA procedure succeeded!\n", ra->rnti);
|
|
||||||
nr_clear_ra_proc(module_idP, CC_id, frameP, ra);
|
|
||||||
UE->Msg3_dcch_dtch = true;
|
|
||||||
UE->Msg4_ACKed = true;
|
|
||||||
UE->ra_timer = 0;
|
|
||||||
|
|
||||||
remove_front_nr_list(&sched_ctrl->feedback_dl_harq);
|
|
||||||
harq->feedback_slot = -1;
|
|
||||||
harq->is_waiting = false;
|
|
||||||
add_tail_nr_list(&sched_ctrl->available_dl_harq, current_harq_pid);
|
|
||||||
harq->round = 0;
|
|
||||||
harq->ndi ^= 1;
|
|
||||||
|
|
||||||
if(!UE->CellGroup)
|
|
||||||
// In the specific scenario where UE correctly received MSG4 (assuming it decoded RRCsetup with CellGroup) and gNB didn't correctly received an ACK,
|
|
||||||
// the UE would already have CG but the UE-dedicated gNB structure wouldn't (because RA didn't complete on gNB side).
|
|
||||||
uper_decode(NULL,
|
|
||||||
&asn_DEF_NR_CellGroupConfig, //might be added prefix later
|
|
||||||
(void **)&UE->CellGroup,
|
|
||||||
(uint8_t *)UE->cg_buf,
|
|
||||||
(UE->enc_rval.encoded+7)/8, 0, 0);
|
|
||||||
process_CellGroup(UE->CellGroup, sched_ctrl);
|
|
||||||
configure_UE_BWP(nr_mac, scc, sched_ctrl, NULL, UE);
|
|
||||||
|
|
||||||
// Reset uplink failure flags/counters/timers at MAC so gNB will resume again scheduling resources for this UE
|
|
||||||
UE->UE_sched_ctrl.pusch_consecutive_dtx_cnt = 0;
|
|
||||||
UE->UE_sched_ctrl.ul_failure = 0;
|
|
||||||
} else {
|
|
||||||
ra->state = WAIT_Msg4_ACK;
|
|
||||||
LOG_D(NR_MAC,"[gNB %d][RAPROC] Frame %d, Subframe %d: RA state %d\n", module_idP, frameP, slotP, ra->state);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1897,7 +2066,6 @@ void nr_clear_ra_proc(module_id_t module_idP, int CC_id, frame_t frameP, NR_RA_t
|
|||||||
ra->timing_offset = 0;
|
ra->timing_offset = 0;
|
||||||
ra->RRC_timer = 20;
|
ra->RRC_timer = 20;
|
||||||
ra->msg3_round = 0;
|
ra->msg3_round = 0;
|
||||||
ra->msg3_dcch_dtch = false;
|
|
||||||
ra->crnti = 0;
|
ra->crnti = 0;
|
||||||
if(ra->cfra == false) {
|
if(ra->cfra == false) {
|
||||||
ra->rnti = 0;
|
ra->rnti = 0;
|
||||||
|
|||||||
@@ -2021,8 +2021,10 @@ void configure_UE_BWP(gNB_MAC_INST *nr_mac,
|
|||||||
NR_ServingCellConfigCommon_t *scc,
|
NR_ServingCellConfigCommon_t *scc,
|
||||||
NR_UE_sched_ctrl_t *sched_ctrl,
|
NR_UE_sched_ctrl_t *sched_ctrl,
|
||||||
NR_RA_t *ra,
|
NR_RA_t *ra,
|
||||||
NR_UE_info_t *UE) {
|
NR_UE_info_t *UE,
|
||||||
|
int dl_bwp_switch,
|
||||||
|
int ul_bwp_switch)
|
||||||
|
{
|
||||||
AssertFatal((ra != NULL && UE == NULL) || (ra == NULL && UE != NULL), "RA and UE structures are mutually exlusive in BWP configuration\n");
|
AssertFatal((ra != NULL && UE == NULL) || (ra == NULL && UE != NULL), "RA and UE structures are mutually exlusive in BWP configuration\n");
|
||||||
|
|
||||||
NR_CellGroupConfig_t *CellGroup;
|
NR_CellGroupConfig_t *CellGroup;
|
||||||
@@ -2067,23 +2069,10 @@ void configure_UE_BWP(gNB_MAC_INST *nr_mac,
|
|||||||
|
|
||||||
target_ss = NR_SearchSpace__searchSpaceType_PR_ue_Specific;
|
target_ss = NR_SearchSpace__searchSpaceType_PR_ue_Specific;
|
||||||
|
|
||||||
if(UE && UE->Msg3_dcch_dtch) {
|
if(dl_bwp_switch >= 0 && ul_bwp_switch >= 0) {
|
||||||
// switching to initial BWP
|
AssertFatal(dl_bwp_switch == ul_bwp_switch, "Different UL and DL BWP not supported\n");
|
||||||
DL_BWP->bwp_id = 0;
|
DL_BWP->bwp_id = dl_bwp_switch;
|
||||||
UL_BWP->bwp_id = 0;
|
UL_BWP->bwp_id = ul_bwp_switch;
|
||||||
UE->Msg3_dcch_dtch = false;
|
|
||||||
|
|
||||||
// Schedule BWP switching to the first active BWP (previous active BWP before RA with Msg3 carrying DCCH or DTCH message)
|
|
||||||
if (servingCellConfig->firstActiveDownlinkBWP_Id) {
|
|
||||||
sched_ctrl->next_dl_bwp_id = *servingCellConfig->firstActiveDownlinkBWP_Id;
|
|
||||||
} else {
|
|
||||||
sched_ctrl->next_dl_bwp_id = 0;
|
|
||||||
}
|
|
||||||
if (servingCellConfig->uplinkConfig->firstActiveUplinkBWP_Id) {
|
|
||||||
sched_ctrl->next_ul_bwp_id = *servingCellConfig->uplinkConfig->firstActiveUplinkBWP_Id;
|
|
||||||
} else {
|
|
||||||
sched_ctrl->next_ul_bwp_id = 0;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
// (re)configuring BWP
|
// (re)configuring BWP
|
||||||
@@ -2335,7 +2324,7 @@ NR_UE_info_t *add_new_nr_ue(gNB_MAC_INST *nr_mac, rnti_t rntiP, NR_CellGroupConf
|
|||||||
memset(dl_bwp, 0, sizeof(*dl_bwp));
|
memset(dl_bwp, 0, sizeof(*dl_bwp));
|
||||||
NR_UE_UL_BWP_t *ul_bwp = &UE->current_UL_BWP;
|
NR_UE_UL_BWP_t *ul_bwp = &UE->current_UL_BWP;
|
||||||
memset(ul_bwp, 0, sizeof(*ul_bwp));
|
memset(ul_bwp, 0, sizeof(*ul_bwp));
|
||||||
configure_UE_BWP(nr_mac, scc, sched_ctrl, NULL, UE);
|
configure_UE_BWP(nr_mac, scc, sched_ctrl, NULL, UE, -1, -1);
|
||||||
|
|
||||||
/* set illegal time domain allocation to force recomputation of all fields */
|
/* set illegal time domain allocation to force recomputation of all fields */
|
||||||
sched_ctrl->sched_pdsch.time_domain_allocation = -1;
|
sched_ctrl->sched_pdsch.time_domain_allocation = -1;
|
||||||
@@ -2811,7 +2800,7 @@ void nr_mac_update_timers(module_id_t module_id,
|
|||||||
process_CellGroup(cg,&UE->UE_sched_ctrl);
|
process_CellGroup(cg,&UE->UE_sched_ctrl);
|
||||||
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
|
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
|
||||||
|
|
||||||
configure_UE_BWP(RC.nrmac[module_id], scc, sched_ctrl, NULL, UE);
|
configure_UE_BWP(RC.nrmac[module_id], scc, sched_ctrl, NULL, UE, -1, -1);
|
||||||
|
|
||||||
if (get_softmodem_params()->sa) {
|
if (get_softmodem_params()->sa) {
|
||||||
// add all available DL HARQ processes for this UE in SA
|
// add all available DL HARQ processes for this UE in SA
|
||||||
|
|||||||
@@ -227,7 +227,7 @@ int nr_process_mac_pdu(instance_t module_idP,
|
|||||||
NR_RA_t *ra = &RC.nrmac[module_idP]->common_channels[CC_id].ra[i];
|
NR_RA_t *ra = &RC.nrmac[module_idP]->common_channels[CC_id].ra[i];
|
||||||
if (ra->state >= WAIT_Msg3 && ra->rnti == UE->rnti) {
|
if (ra->state >= WAIT_Msg3 && ra->rnti == UE->rnti) {
|
||||||
ra->crnti = ((pduP[1]&0xFF)<<8)|(pduP[2]&0xFF);
|
ra->crnti = ((pduP[1]&0xFF)<<8)|(pduP[2]&0xFF);
|
||||||
ra->msg3_dcch_dtch = true;
|
ra->state = Msg3_dcch_dtch;
|
||||||
LOG_I(NR_MAC, "Received UL_SCH_LCID_C_RNTI with C-RNTI 0x%04x\n", ra->crnti);
|
LOG_I(NR_MAC, "Received UL_SCH_LCID_C_RNTI with C-RNTI 0x%04x\n", ra->crnti);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@@ -755,9 +755,8 @@ void nr_rx_sdu(const module_id_t gnb_mod_idP,
|
|||||||
// harq_pid set a non valid value because it is not used in this call
|
// harq_pid set a non valid value because it is not used in this call
|
||||||
// the function is only called to decode the contention resolution sub-header
|
// the function is only called to decode the contention resolution sub-header
|
||||||
if (nr_process_mac_pdu(gnb_mod_idP, UE, CC_idP, frameP, slotP, sduP, sdu_lenP, -1) == 0) {
|
if (nr_process_mac_pdu(gnb_mod_idP, UE, CC_idP, frameP, slotP, sduP, sdu_lenP, -1) == 0) {
|
||||||
ra->state = Msg4;
|
|
||||||
|
|
||||||
if (ra->msg3_dcch_dtch) {
|
if (ra->state == Msg3_dcch_dtch) {
|
||||||
// Check if the UE identified by C-RNTI still exists at the gNB
|
// Check if the UE identified by C-RNTI still exists at the gNB
|
||||||
NR_UE_info_t * UE_C = find_nr_UE(&gNB_mac->UE_info, ra->crnti);
|
NR_UE_info_t * UE_C = find_nr_UE(&gNB_mac->UE_info, ra->crnti);
|
||||||
if (!UE_C) {
|
if (!UE_C) {
|
||||||
@@ -775,13 +774,18 @@ void nr_rx_sdu(const module_id_t gnb_mod_idP,
|
|||||||
reset_dl_harq_list(&UE_C->UE_sched_ctrl);
|
reset_dl_harq_list(&UE_C->UE_sched_ctrl);
|
||||||
reset_ul_harq_list(&UE_C->UE_sched_ctrl);
|
reset_ul_harq_list(&UE_C->UE_sched_ctrl);
|
||||||
}
|
}
|
||||||
|
LOG_I(NR_MAC, "Activating scheduling response to MSG3 with DCCH/DTCCH and RNTI 0x%04x (state %d)\n",
|
||||||
|
ra->crnti, ra->state);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
LOG_I(NR_MAC, "Activating scheduling RA-Msg4 for TC_RNTI 0x%04x (state %d)\n",
|
||||||
|
ra->rnti, ra->state);
|
||||||
|
ra->state = Msg4;
|
||||||
}
|
}
|
||||||
LOG_I(NR_MAC, "Activating scheduling RA-Msg4 for TC_RNTI 0x%04x (state %d)\n",
|
|
||||||
(ra->msg3_dcch_dtch?ra->crnti:ra->rnti), ra->state);
|
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
nr_mac_remove_ra_rnti(gnb_mod_idP, ra->rnti);
|
nr_mac_remove_ra_rnti(gnb_mod_idP, ra->rnti);
|
||||||
nr_clear_ra_proc(gnb_mod_idP, CC_idP, frameP, ra);
|
nr_clear_ra_proc(gnb_mod_idP, CC_idP, frameP, ra);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return;
|
return;
|
||||||
|
|||||||
@@ -343,7 +343,9 @@ void configure_UE_BWP(gNB_MAC_INST *nr_mac,
|
|||||||
NR_ServingCellConfigCommon_t *scc,
|
NR_ServingCellConfigCommon_t *scc,
|
||||||
NR_UE_sched_ctrl_t *sched_ctrl,
|
NR_UE_sched_ctrl_t *sched_ctrl,
|
||||||
NR_RA_t *ra,
|
NR_RA_t *ra,
|
||||||
NR_UE_info_t *UE);
|
NR_UE_info_t *UE,
|
||||||
|
int dl_bwp_switch,
|
||||||
|
int ul_bwp_switch);
|
||||||
|
|
||||||
NR_UE_info_t* add_new_nr_ue(gNB_MAC_INST *nr_mac, rnti_t rntiP, NR_CellGroupConfig_t *CellGroup);
|
NR_UE_info_t* add_new_nr_ue(gNB_MAC_INST *nr_mac, rnti_t rntiP, NR_CellGroupConfig_t *CellGroup);
|
||||||
|
|
||||||
@@ -371,6 +373,8 @@ void nr_generate_Msg4(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
|
|||||||
|
|
||||||
void nr_check_Msg4_Ack(module_id_t module_id, int CC_id, frame_t frame, sub_frame_t slot, NR_RA_t *ra);
|
void nr_check_Msg4_Ack(module_id_t module_id, int CC_id, frame_t frame, sub_frame_t slot, NR_RA_t *ra);
|
||||||
|
|
||||||
|
void nr_generate_Msg3_dcch_dtch_response(module_id_t module_idP, int CC_id, frame_t frameP, sub_frame_t slotP, NR_RA_t *ra);
|
||||||
|
|
||||||
int binomial(int n, int k);
|
int binomial(int n, int k);
|
||||||
|
|
||||||
bool is_xlsch_in_slot(uint64_t bitmap, sub_frame_t slot);
|
bool is_xlsch_in_slot(uint64_t bitmap, sub_frame_t slot);
|
||||||
|
|||||||
@@ -94,8 +94,9 @@ typedef enum {
|
|||||||
Msg2 = 1,
|
Msg2 = 1,
|
||||||
WAIT_Msg3 = 2,
|
WAIT_Msg3 = 2,
|
||||||
Msg3_retransmission = 3,
|
Msg3_retransmission = 3,
|
||||||
Msg4 = 4,
|
Msg3_dcch_dtch = 4,
|
||||||
WAIT_Msg4_ACK = 5
|
Msg4 = 5,
|
||||||
|
WAIT_Msg4_ACK = 6
|
||||||
} RA_gNB_state_t;
|
} RA_gNB_state_t;
|
||||||
|
|
||||||
typedef struct NR_preamble_ue {
|
typedef struct NR_preamble_ue {
|
||||||
@@ -163,8 +164,6 @@ typedef struct {
|
|||||||
uint8_t msg3_cqireq;
|
uint8_t msg3_cqireq;
|
||||||
/// Round of Msg3 HARQ
|
/// Round of Msg3 HARQ
|
||||||
uint8_t msg3_round;
|
uint8_t msg3_round;
|
||||||
/// Flag to indicate if Msg3 carries a DCCH or DTCH message
|
|
||||||
bool msg3_dcch_dtch;
|
|
||||||
int msg3_startsymb;
|
int msg3_startsymb;
|
||||||
int msg3_nrsymb;
|
int msg3_nrsymb;
|
||||||
/// TBS used for Msg4
|
/// TBS used for Msg4
|
||||||
@@ -659,7 +658,6 @@ typedef struct {
|
|||||||
asn_enc_rval_t enc_rval;
|
asn_enc_rval_t enc_rval;
|
||||||
// UE selected beam index
|
// UE selected beam index
|
||||||
uint8_t UE_beam_index;
|
uint8_t UE_beam_index;
|
||||||
bool Msg3_dcch_dtch;
|
|
||||||
bool Msg4_ACKed;
|
bool Msg4_ACKed;
|
||||||
uint32_t ra_timer;
|
uint32_t ra_timer;
|
||||||
float ul_thr_ue;
|
float ul_thr_ue;
|
||||||
|
|||||||
Reference in New Issue
Block a user