Commit 2bf11808 authored by Cedric Roux's avatar Cedric Roux

Merge remote-tracking branch 'origin/feature-68-enb-agent' into develop_integration_w06

 Conflicts:
	openair2/LAYER2/MAC/flexran_agent_scheduler_dlsch_ue.c
parents ce14050b 274030c4
...@@ -92,6 +92,9 @@ extern uint16_t hundred_times_log10_NPRB[100]; ...@@ -92,6 +92,9 @@ extern uint16_t hundred_times_log10_NPRB[100];
unsigned int max_peak_val; unsigned int max_peak_val;
int max_sync_pos; int max_sync_pos;
int harq_pid_updated[NUMBER_OF_UE_MAX][8] = {{0}};
int harq_pid_round[NUMBER_OF_UE_MAX][8] = {{0}};
//DCI_ALLOC_t dci_alloc[8]; //DCI_ALLOC_t dci_alloc[8];
#ifdef EMOS #ifdef EMOS
...@@ -1444,15 +1447,6 @@ void phy_procedures_eNB_TX(PHY_VARS_eNB *eNB, ...@@ -1444,15 +1447,6 @@ void phy_procedures_eNB_TX(PHY_VARS_eNB *eNB,
eNB->dlsch_ra->active = 0; eNB->dlsch_ra->active = 0;
} }
#if defined(FLEXRAN_AGENT_SB_IF)
#ifndef DISABLE_SF_TRIGGER
//Send subframe trigger to the controller
if (mac_agent_registered[eNB->Mod_id]) {
agent_mac_xface[eNB->Mod_id]->flexran_agent_send_sf_trigger(eNB->Mod_id);
}
#endif
#endif
// Now scan UE specific DLSCH // Now scan UE specific DLSCH
for (UE_id=0; UE_id<NUMBER_OF_UE_MAX; UE_id++) for (UE_id=0; UE_id<NUMBER_OF_UE_MAX; UE_id++)
{ {
...@@ -1553,7 +1547,6 @@ void process_HARQ_feedback(uint8_t UE_id, ...@@ -1553,7 +1547,6 @@ void process_HARQ_feedback(uint8_t UE_id,
int subframe = proc->subframe_rx; int subframe = proc->subframe_rx;
int harq_pid = subframe2harq_pid( fp,frame,subframe); int harq_pid = subframe2harq_pid( fp,frame,subframe);
if (fp->frame_type == FDD) { //FDD if (fp->frame_type == FDD) { //FDD
subframe_m4 = (subframe<4) ? subframe+6 : subframe-4; subframe_m4 = (subframe<4) ? subframe+6 : subframe-4;
...@@ -1681,6 +1674,7 @@ void process_HARQ_feedback(uint8_t UE_id, ...@@ -1681,6 +1674,7 @@ void process_HARQ_feedback(uint8_t UE_id,
mp = m; mp = m;
dl_harq_pid[m] = dlsch->harq_ids[dl_subframe]; dl_harq_pid[m] = dlsch->harq_ids[dl_subframe];
harq_pid_updated[UE_id][dl_harq_pid[m]] = 1;
if ((pucch_sel != 2)&&(pusch_flag == 0)) { // multiplexing if ((pucch_sel != 2)&&(pusch_flag == 0)) { // multiplexing
if ((SR_payload == 1)&&(all_ACKed == 1)) if ((SR_payload == 1)&&(all_ACKed == 1))
...@@ -1768,7 +1762,7 @@ void process_HARQ_feedback(uint8_t UE_id, ...@@ -1768,7 +1762,7 @@ void process_HARQ_feedback(uint8_t UE_id,
eNB->dlsch[(uint8_t)UE_id][0]->harq_processes[dl_harq_pid[m]]->TBS; eNB->dlsch[(uint8_t)UE_id][0]->harq_processes[dl_harq_pid[m]]->TBS;
*/ */
} }
// Do fine-grain rate-adaptation for DLSCH // Do fine-grain rate-adaptation for DLSCH
if (ue_stats->dlsch_NAK_round0 > dlsch->error_threshold) { if (ue_stats->dlsch_NAK_round0 > dlsch->error_threshold) {
if (ue_stats->dlsch_mcs_offset == 1) if (ue_stats->dlsch_mcs_offset == 1)
...@@ -1781,7 +1775,7 @@ void process_HARQ_feedback(uint8_t UE_id, ...@@ -1781,7 +1775,7 @@ void process_HARQ_feedback(uint8_t UE_id,
LOG_D(PHY,"[process_HARQ_feedback] Frame %d Setting round to %d for pid %d (subframe %d)\n",frame, LOG_D(PHY,"[process_HARQ_feedback] Frame %d Setting round to %d for pid %d (subframe %d)\n",frame,
dlsch_harq_proc->round,dl_harq_pid[m],subframe); dlsch_harq_proc->round,dl_harq_pid[m],subframe);
#endif #endif
harq_pid_round[UE_id][dl_harq_pid[m]] = dlsch_harq_proc->round;
// Clear NAK stats and adjust mcs offset // Clear NAK stats and adjust mcs offset
// after measurement window timer expires // after measurement window timer expires
if (ue_stats->dlsch_sliding_cnt == dlsch->ra_window_size) { if (ue_stats->dlsch_sliding_cnt == dlsch->ra_window_size) {
...@@ -1800,8 +1794,6 @@ void process_HARQ_feedback(uint8_t UE_id, ...@@ -1800,8 +1794,6 @@ void process_HARQ_feedback(uint8_t UE_id,
ue_stats->dlsch_NAK_round0 = 0; ue_stats->dlsch_NAK_round0 = 0;
ue_stats->dlsch_sliding_cnt = 0; ue_stats->dlsch_sliding_cnt = 0;
} }
} }
} }
} }
...@@ -3426,14 +3418,21 @@ void phy_procedures_eNB_uespec_RX(PHY_VARS_eNB *eNB,eNB_rxtx_proc_t *proc,const ...@@ -3426,14 +3418,21 @@ void phy_procedures_eNB_uespec_RX(PHY_VARS_eNB *eNB,eNB_rxtx_proc_t *proc,const
} }
#endif #endif
//} //}
#ifdef EMOS #ifdef EMOS
phy_procedures_emos_eNB_RX(subframe,eNB); phy_procedures_emos_eNB_RX(subframe,eNB);
#endif #endif
#if defined(FLEXRAN_AGENT_SB_IF)
#ifndef DISABLE_SF_TRIGGER
//Send subframe trigger to the controller
if (mac_agent_registered[eNB->Mod_id]) {
agent_mac_xface[eNB->Mod_id]->flexran_agent_send_sf_trigger(eNB->Mod_id);
}
#endif
#endif
VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME( VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_PROCEDURES_ENB_RX_UESPEC+offset, 0 ); VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME( VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_PROCEDURES_ENB_RX_UESPEC+offset, 0 );
stop_meas(&eNB->phy_proc_rx); stop_meas(&eNB->phy_proc_rx);
......
...@@ -443,14 +443,14 @@ int flexran_agent_mac_stats_reply(mid_t mod_id, ...@@ -443,14 +443,14 @@ int flexran_agent_mac_stats_reply(mid_t mod_id,
if (rlc_reports[j] == NULL) if (rlc_reports[j] == NULL)
goto error; goto error;
protocol__flex_rlc_bsr__init(rlc_reports[j]); protocol__flex_rlc_bsr__init(rlc_reports[j]);
rlc_reports[j]->lc_id = j+1; rlc_reports[j]->lc_id = j + 1;
rlc_reports[j]->has_lc_id = 1; rlc_reports[j]->has_lc_id = 1;
rlc_reports[j]->tx_queue_size = flexran_get_tx_queue_size(enb_id,i,j+1); rlc_reports[j]->tx_queue_size = flexran_get_tx_queue_size(enb_id,i,j + 1);
rlc_reports[j]->has_tx_queue_size = 1; rlc_reports[j]->has_tx_queue_size = 1;
//TODO:Set tx queue head of line delay in ms //TODO:Set tx queue head of line delay in ms
rlc_reports[j]->tx_queue_hol_delay = 100; rlc_reports[j]->tx_queue_hol_delay = flexran_get_hol_delay(enb_id, i, j+1);
rlc_reports[j]->has_tx_queue_hol_delay = 0; rlc_reports[j]->has_tx_queue_hol_delay = 1;
//TODO:Set retransmission queue size in bytes //TODO:Set retransmission queue size in bytes
rlc_reports[j]->retransmission_queue_size = 10; rlc_reports[j]->retransmission_queue_size = 10;
rlc_reports[j]->has_retransmission_queue_size = 0; rlc_reports[j]->has_retransmission_queue_size = 0;
...@@ -657,6 +657,8 @@ int flexran_agent_mac_stats_reply(mid_t mod_id, ...@@ -657,6 +657,8 @@ int flexran_agent_mac_stats_reply(mid_t mod_id,
full_ul_report->pucch_dbm[j]->p0_pucch_dbm = flexran_get_p0_pucch_dbm(enb_id,i,j); full_ul_report->pucch_dbm[j]->p0_pucch_dbm = flexran_get_p0_pucch_dbm(enb_id,i,j);
full_ul_report->pucch_dbm[j]->has_p0_pucch_dbm = 1; full_ul_report->pucch_dbm[j]->has_p0_pucch_dbm = 1;
} }
full_ul_report->pucch_dbm[j]->has_p0_pucch_updated = 1;
full_ul_report->pucch_dbm[j]->p0_pucch_updated = flexran_get_p0_pucch_status(enb_id, i, j);
} }
//Add full UL CQI report to the UE report //Add full UL CQI report to the UE report
...@@ -921,9 +923,13 @@ int flexran_agent_mac_destroy_sr_info(Protocol__FlexranMessage *msg) { ...@@ -921,9 +923,13 @@ int flexran_agent_mac_destroy_sr_info(Protocol__FlexranMessage *msg) {
int flexran_agent_mac_sf_trigger(mid_t mod_id, const void *params, Protocol__FlexranMessage **msg) { int flexran_agent_mac_sf_trigger(mid_t mod_id, const void *params, Protocol__FlexranMessage **msg) {
Protocol__FlexHeader *header; Protocol__FlexHeader *header;
int i,j; int i, j, UE_id;
int available_harq[NUMBER_OF_UE_MAX];
const int xid = *((int *)params); const int xid = *((int *)params);
Protocol__FlexSfTrigger *sf_trigger_msg; Protocol__FlexSfTrigger *sf_trigger_msg;
sf_trigger_msg = malloc(sizeof(Protocol__FlexSfTrigger)); sf_trigger_msg = malloc(sizeof(Protocol__FlexSfTrigger));
if (sf_trigger_msg == NULL) { if (sf_trigger_msg == NULL) {
...@@ -937,29 +943,47 @@ int flexran_agent_mac_sf_trigger(mid_t mod_id, const void *params, Protocol__Fle ...@@ -937,29 +943,47 @@ int flexran_agent_mac_sf_trigger(mid_t mod_id, const void *params, Protocol__Fle
frame_t frame; frame_t frame;
sub_frame_t subframe; sub_frame_t subframe;
int ahead_of_time = 1; for (i = 0; i < NUMBER_OF_UE_MAX; i++) {
available_harq[i] = -1;
}
int ahead_of_time = 0;
frame = (frame_t) flexran_get_current_system_frame_num(mod_id); frame = (frame_t) flexran_get_current_system_frame_num(mod_id);
subframe = (sub_frame_t) flexran_get_current_subframe(mod_id); subframe = (sub_frame_t) flexran_get_current_subframe(mod_id);
subframe = ((subframe + ahead_of_time) % 10); subframe = ((subframe + ahead_of_time) % 10);
int full_frames_ahead = ((ahead_of_time / 10) % 10);
frame = frame + full_frames_ahead;
if (subframe < flexran_get_current_subframe(mod_id)) { if (subframe < flexran_get_current_subframe(mod_id)) {
frame++; frame = (frame + 1) % 1024;
} }
int additional_frames = ahead_of_time / 10;
frame = (frame + additional_frames) % 1024;
sf_trigger_msg->header = header; sf_trigger_msg->header = header;
sf_trigger_msg->has_sfn_sf = 1; sf_trigger_msg->has_sfn_sf = 1;
sf_trigger_msg->sfn_sf = flexran_get_future_sfn_sf(mod_id, 1); sf_trigger_msg->sfn_sf = flexran_get_future_sfn_sf(mod_id, 3);
sf_trigger_msg->n_dl_info = 0;
for (i = 0; i < NUMBER_OF_UE_MAX; i++) {
for (j = 0; j < 8; j++) {
if (harq_pid_updated[i][j] == 1) {
available_harq[i] = j;
sf_trigger_msg->n_dl_info++;
break;
}
}
}
// LOG_I(FLEXRAN_AGENT, "Sending subframe trigger for frame %d and subframe %d\n", flexran_get_current_frame(mod_id), (flexran_get_current_subframe(mod_id) + 1) % 10);
/*TODO: Fill in the number of dl HARQ related info, based on the number of currently /*TODO: Fill in the number of dl HARQ related info, based on the number of currently
*transmitting UEs *transmitting UEs
*/ */
sf_trigger_msg->n_dl_info = flexran_get_num_ues(mod_id); // sf_trigger_msg->n_dl_info = flexran_get_num_ues(mod_id);
Protocol__FlexDlInfo **dl_info = NULL; Protocol__FlexDlInfo **dl_info = NULL;
...@@ -967,29 +991,39 @@ int flexran_agent_mac_sf_trigger(mid_t mod_id, const void *params, Protocol__Fle ...@@ -967,29 +991,39 @@ int flexran_agent_mac_sf_trigger(mid_t mod_id, const void *params, Protocol__Fle
dl_info = malloc(sizeof(Protocol__FlexDlInfo *) * sf_trigger_msg->n_dl_info); dl_info = malloc(sizeof(Protocol__FlexDlInfo *) * sf_trigger_msg->n_dl_info);
if(dl_info == NULL) if(dl_info == NULL)
goto error; goto error;
i = -1;
//Fill the status of the current HARQ process for each UE //Fill the status of the current HARQ process for each UE
for(i = 0; i < sf_trigger_msg->n_dl_info; i++) { for(UE_id = 0; UE_id < NUMBER_OF_UE_MAX; UE_id++) {
if (available_harq[UE_id] < 0) {
continue;
} else {
i++;
}
dl_info[i] = malloc(sizeof(Protocol__FlexDlInfo)); dl_info[i] = malloc(sizeof(Protocol__FlexDlInfo));
if(dl_info[i] == NULL) if(dl_info[i] == NULL)
goto error; goto error;
protocol__flex_dl_info__init(dl_info[i]); protocol__flex_dl_info__init(dl_info[i]);
dl_info[i]->rnti = flexran_get_ue_crnti(mod_id, i); dl_info[i]->rnti = flexran_get_ue_crnti(mod_id, UE_id);
dl_info[i]->has_rnti = 1; dl_info[i]->has_rnti = 1;
/*Fill in the right id of this round's HARQ process for this UE*/ /*Fill in the right id of this round's HARQ process for this UE*/
unsigned char harq_id; // uint8_t harq_id;
unsigned char harq_status; //uint8_t harq_status;
flexran_get_harq(mod_id, UE_PCCID(mod_id,i), i, frame, subframe, &harq_id, &harq_status); // flexran_get_harq(mod_id, UE_PCCID(mod_id,i), i, frame, subframe, &harq_id, &harq_status);
dl_info[i]->harq_process_id = harq_id;
dl_info[i]->harq_process_id = available_harq[UE_id];
harq_pid_updated[UE_id][available_harq[UE_id]] = 0;
dl_info[i]->has_harq_process_id = 1; dl_info[i]->has_harq_process_id = 1;
/* Fill in the status of the HARQ process (2 TBs)*/ /* Fill in the status of the HARQ process (2 TBs)*/
dl_info[i]->n_harq_status = 2; dl_info[i]->n_harq_status = 2;
dl_info[i]->harq_status = malloc(sizeof(uint32_t) * dl_info[i]->n_harq_status); dl_info[i]->harq_status = malloc(sizeof(uint32_t) * dl_info[i]->n_harq_status);
for (j = 0; j < dl_info[i]->n_harq_status; j++) { for (j = 0; j < dl_info[i]->n_harq_status; j++) {
dl_info[i]->harq_status[j] = harq_pid_round[UE_id][available_harq[UE_id]];
// TODO: This should be different per TB // TODO: This should be different per TB
if(harq_status == 0) }
dl_info[i]->harq_status[j] = PROTOCOL__FLEX_HARQ_STATUS__FLHS_ACK; // LOG_I(FLEXRAN_AGENT, "Sending subframe trigger for frame %d and subframe %d and harq %d (round %d)\n", flexran_get_current_frame(mod_id), (flexran_get_current_subframe(mod_id) + 1) % 10, dl_info[i]->harq_process_id, dl_info[i]->harq_status[0]);
else if (harq_status > 0) if(dl_info[i]->harq_status[0] > 0) {
dl_info[i]->harq_status[j] = PROTOCOL__FLEX_HARQ_STATUS__FLHS_NACK; // LOG_I(FLEXRAN_AGENT, "[Frame %d][Subframe %d]Need to make a retransmission for harq %d (round %d)\n", flexran_get_current_frame(mod_id), flexran_get_current_subframe(mod_id), dl_info[i]->harq_process_id, dl_info[i]->harq_status[0]);
} }
/*Fill in the serving cell index for this UE */ /*Fill in the serving cell index for this UE */
dl_info[i]->serv_cell_index = UE_PCCID(mod_id,i); dl_info[i]->serv_cell_index = UE_PCCID(mod_id,i);
...@@ -1234,12 +1268,18 @@ int flexran_agent_mac_handle_dl_mac_config(mid_t mod_id, const void *params, Pro ...@@ -1234,12 +1268,18 @@ int flexran_agent_mac_handle_dl_mac_config(mid_t mod_id, const void *params, Pro
} }
void flexran_agent_init_mac_agent(mid_t mod_id) { void flexran_agent_init_mac_agent(mid_t mod_id) {
int i, j;
lfds700_misc_library_init_valid_on_current_logical_core(); lfds700_misc_library_init_valid_on_current_logical_core();
lfds700_misc_prng_init(&ps[mod_id]); lfds700_misc_prng_init(&ps[mod_id]);
int num_elements = RINGBUFFER_SIZE + 1; int num_elements = RINGBUFFER_SIZE + 1;
//Allow RINGBUFFER_SIZE messages to be stored in the ringbuffer at any time //Allow RINGBUFFER_SIZE messages to be stored in the ringbuffer at any time
dl_mac_config_array[mod_id] = malloc( sizeof(struct lfds700_ringbuffer_element) * num_elements); dl_mac_config_array[mod_id] = malloc( sizeof(struct lfds700_ringbuffer_element) * num_elements);
lfds700_ringbuffer_init_valid_on_current_logical_core( &ringbuffer_state[mod_id], dl_mac_config_array[mod_id], num_elements, &ps[mod_id], NULL ); lfds700_ringbuffer_init_valid_on_current_logical_core( &ringbuffer_state[mod_id], dl_mac_config_array[mod_id], num_elements, &ps[mod_id], NULL );
for (i = 0; i < NUMBER_OF_UE_MAX; i++) {
for (j = 0; j < 8; j++) {
harq_pid_updated[i][j] = 0;
}
}
} }
/*********************************************** /***********************************************
......
...@@ -166,6 +166,7 @@ message flex_ul_cqi_report { ...@@ -166,6 +166,7 @@ message flex_ul_cqi_report {
message flex_pucch_dbm { message flex_pucch_dbm {
optional int32 p0_pucch_dbm = 1; optional int32 p0_pucch_dbm = 1;
optional uint32 serv_cell_index = 2; optional uint32 serv_cell_index = 2;
optional uint32 p0_pucch_updated = 3;
} }
// //
......
...@@ -516,15 +516,14 @@ uint16_t flexran_get_future_sfn_sf (mid_t mod_id, int ahead_of_time) { ...@@ -516,15 +516,14 @@ uint16_t flexran_get_future_sfn_sf (mid_t mod_id, int ahead_of_time) {
subframe = (sub_frame_t) flexran_get_current_subframe(mod_id); subframe = (sub_frame_t) flexran_get_current_subframe(mod_id);
subframe = ((subframe + ahead_of_time) % 10); subframe = ((subframe + ahead_of_time) % 10);
int full_frames_ahead = ((ahead_of_time / 10) % 10);
frame = frame + full_frames_ahead;
if (subframe < flexran_get_current_subframe(mod_id)) { if (subframe < flexran_get_current_subframe(mod_id)) {
frame++; frame = (frame + 1) % 1024;
} }
int additional_frames = ahead_of_time / 10;
frame = (frame + additional_frames) % 1024;
frame_mask = ((1<<12) - 1); frame_mask = ((1<<12) - 1);
sf_mask = ((1<<4) - 1); sf_mask = ((1<<4) - 1);
sfn_sf = (subframe & sf_mask) | ((frame & frame_mask) << 4); sfn_sf = (subframe & sf_mask) | ((frame & frame_mask) << 4);
...@@ -553,69 +552,81 @@ int flexran_get_ue_phr (mid_t mod_id, mid_t ue_id) { ...@@ -553,69 +552,81 @@ int flexran_get_ue_phr (mid_t mod_id, mid_t ue_id) {
} }
int flexran_get_ue_wcqi (mid_t mod_id, mid_t ue_id) { int flexran_get_ue_wcqi (mid_t mod_id, mid_t ue_id) {
return ((UE_list_t *)enb_ue[mod_id])->eNB_UE_stats[UE_PCCID(mod_id,ue_id)][ue_id].dl_cqi; LTE_eNB_UE_stats *eNB_UE_stats = NULL;
eNB_UE_stats = mac_xface->get_eNB_UE_stats(mod_id, 0, UE_RNTI(mod_id, ue_id));
return eNB_UE_stats->DL_cqi[0];
// return ((UE_list_t *)enb_ue[mod_id])->eNB_UE_stats[UE_PCCID(mod_id,ue_id)][ue_id].dl_cqi;
} }
int flexran_get_tx_queue_size(mid_t mod_id, mid_t ue_id, logical_chan_id_t channel_id) { int flexran_get_tx_queue_size(mid_t mod_id, mid_t ue_id, logical_chan_id_t channel_id) {
rnti_t rnti = flexran_get_ue_crnti(mod_id,ue_id); rnti_t rnti = flexran_get_ue_crnti(mod_id,ue_id);
uint16_t frame = (uint16_t) flexran_get_current_frame(mod_id); uint16_t frame = (uint16_t) flexran_get_current_frame(mod_id);
mac_rlc_status_resp_t rlc_status = mac_rlc_status_ind(mod_id,rnti, mod_id,frame,ENB_FLAG_YES,MBMS_FLAG_NO,channel_id,0); mac_rlc_status_resp_t rlc_status = mac_rlc_status_ind(mod_id,rnti, mod_id,frame,ENB_FLAG_YES,MBMS_FLAG_NO, channel_id, 0);
return rlc_status.bytes_in_buffer; return rlc_status.bytes_in_buffer;
} }
int flexran_update_TA(mid_t mod_id, mid_t ue_id, int CC_id) { int flexran_get_hol_delay(mid_t mod_id, mid_t ue_id, logical_chan_id_t channel_id) {
rnti_t rnti = flexran_get_ue_crnti(mod_id,ue_id);
uint16_t frame = (uint16_t) flexran_get_current_frame(mod_id);
mac_rlc_status_resp_t rlc_status = mac_rlc_status_ind(mod_id, rnti, mod_id, frame, ENB_FLAG_YES, MBMS_FLAG_NO, channel_id, 0);
return rlc_status.head_sdu_creation_time;
}
short flexran_get_TA(mid_t mod_id, mid_t ue_id, int CC_id) {
UE_list_t *UE_list=&eNB_mac_inst[mod_id].UE_list; UE_list_t *UE_list=&eNB_mac_inst[mod_id].UE_list;
UE_sched_ctrl *ue_sched_ctl = &UE_list->UE_sched_ctrl[ue_id];
int rnti; int rnti;
rnti = flexran_get_ue_crnti(mod_id, ue_id); rnti = flexran_get_ue_crnti(mod_id, ue_id);
if (ue_sched_ctl->ta_timer == 0) {
// WE SHOULD PROTECT the eNB_UE_stats with a mutex here ... LTE_eNB_UE_stats *eNB_UE_stats = mac_xface->get_eNB_UE_stats(mod_id, CC_id, rnti);
LTE_eNB_UE_stats *eNB_UE_stats = mac_xface->get_eNB_UE_stats(mod_id, CC_id, rnti); //ue_sched_ctl->ta_timer = 20; // wait 20 subframes before taking TA measurement from PHY
ue_sched_ctl->ta_timer = 20; // wait 20 subframes before taking TA measurement from PHY switch (PHY_vars_eNB_g[mod_id][CC_id]->frame_parms.N_RB_DL) {
switch (PHY_vars_eNB_g[mod_id][CC_id]->frame_parms.N_RB_DL) { case 6:
case 6: return eNB_UE_stats->timing_advance_update;
ue_sched_ctl->ta_update = eNB_UE_stats->timing_advance_update; case 15:
break; return eNB_UE_stats->timing_advance_update/2;
case 25:
case 15: return eNB_UE_stats->timing_advance_update/4;
ue_sched_ctl->ta_update = eNB_UE_stats->timing_advance_update/2; case 50:
break; return eNB_UE_stats->timing_advance_update/8;
case 75:
case 25: return eNB_UE_stats->timing_advance_update/12;
ue_sched_ctl->ta_update = eNB_UE_stats->timing_advance_update/4; case 100:
break; if (PHY_vars_eNB_g[mod_id][CC_id]->frame_parms.threequarter_fs == 0) {
return eNB_UE_stats->timing_advance_update/16;
case 50: } else {
ue_sched_ctl->ta_update = eNB_UE_stats->timing_advance_update/8; return eNB_UE_stats->timing_advance_update/12;
break;
case 75:
ue_sched_ctl->ta_update = eNB_UE_stats->timing_advance_update/12;
break;
case 100:
ue_sched_ctl->ta_update = eNB_UE_stats->timing_advance_update/16;
break;
} }
// clear the update in case PHY does not have a new measurement after timer expiry default:
eNB_UE_stats->timing_advance_update = 0; return 0;
}
else {
ue_sched_ctl->ta_timer--;
ue_sched_ctl->ta_update = 0; // don't trigger a timing advance command
} }
}
return ue_sched_ctl->ta_update = 0; void flexran_update_TA(mid_t mod_id, mid_t ue_id, int CC_id) {
UE_list_t *UE_list=&eNB_mac_inst[mod_id].UE_list;
UE_sched_ctrl *ue_sched_ctl = &UE_list->UE_sched_ctrl[ue_id];
if (ue_sched_ctl->ta_timer == 0) {
// WE SHOULD PROTECT the eNB_UE_stats with a mutex here ...
// LTE_eNB_UE_stats *eNB_UE_stats = mac_xface->get_eNB_UE_stats(mod_id, CC_id, rnti);
//ue_sched_ctl->ta_timer = 20; // wait 20 subframes before taking TA measurement from PHY
ue_sched_ctl->ta_update = flexran_get_TA(mod_id, ue_id, CC_id);
// clear the update in case PHY does not have a new measurement after timer expiry
// eNB_UE_stats->timing_advance_update = 0;
} else {
ue_sched_ctl->ta_timer--;
ue_sched_ctl->ta_update = 0; // don't trigger a timing advance command
}
} }
int flexran_get_MAC_CE_bitmap_TA(mid_t mod_id, mid_t ue_id,int CC_id) { int flexran_get_MAC_CE_bitmap_TA(mid_t mod_id, mid_t ue_id,int CC_id) {
UE_list_t *UE_list = &eNB_mac_inst[mod_id].UE_list; UE_list_t *UE_list = &eNB_mac_inst[mod_id].UE_list;
UE_sched_ctrl *ue_sched_ctl = &UE_list->UE_sched_ctrl[ue_id];
rnti_t rnti = flexran_get_ue_crnti(mod_id,ue_id); rnti_t rnti = flexran_get_ue_crnti(mod_id,ue_id);
LTE_eNB_UE_stats *eNB_UE_stats = mac_xface->get_eNB_UE_stats(mod_id,CC_id,rnti); LTE_eNB_UE_stats *eNB_UE_stats = mac_xface->get_eNB_UE_stats(mod_id,CC_id,rnti);
...@@ -624,8 +635,8 @@ int flexran_get_MAC_CE_bitmap_TA(mid_t mod_id, mid_t ue_id,int CC_id) { ...@@ -624,8 +635,8 @@ int flexran_get_MAC_CE_bitmap_TA(mid_t mod_id, mid_t ue_id,int CC_id) {
return 0; return 0;
} }
if (ue_sched_ctl->ta_update == 0) { if (flexran_get_TA(mod_id, ue_id, CC_id) != 0) {
return 1; return PROTOCOL__FLEX_CE_TYPE__FLPCET_TA;
} else { } else {
return 0; return 0;
} }
...@@ -680,8 +691,13 @@ int flexran_get_tpc(mid_t mod_id, mid_t ue_id) { ...@@ -680,8 +691,13 @@ int flexran_get_tpc(mid_t mod_id, mid_t ue_id) {
return tpc; return tpc;
} }
int flexran_get_harq(const mid_t mod_id, const uint8_t CC_id, const mid_t ue_id, const int frame, const uint8_t subframe, int flexran_get_harq(const mid_t mod_id,
unsigned char *id, unsigned char *round) { //flag_id_status = 0 then id, else status const uint8_t CC_id,
const mid_t ue_id,
const int frame,
const uint8_t subframe,
uint8_t *id,
uint8_t *round) { //flag_id_status = 0 then id, else status
/*TODO: Add int TB in function parameters to get the status of the second TB. This can be done to by editing in /*TODO: Add int TB in function parameters to get the status of the second TB. This can be done to by editing in
* get_ue_active_harq_pid function in line 272 file: phy_procedures_lte_eNB.c to add * get_ue_active_harq_pid function in line 272 file: phy_procedures_lte_eNB.c to add
* DLSCH_ptr = PHY_vars_eNB_g[Mod_id][CC_id]->dlsch_eNB[(uint32_t)UE_id][1];*/ * DLSCH_ptr = PHY_vars_eNB_g[Mod_id][CC_id]->dlsch_eNB[(uint32_t)UE_id][1];*/
...@@ -707,43 +723,43 @@ int flexran_get_harq(const mid_t mod_id, const uint8_t CC_id, const mid_t ue_id, ...@@ -707,43 +723,43 @@ int flexran_get_harq(const mid_t mod_id, const uint8_t CC_id, const mid_t ue_id,
} }
int flexran_get_p0_pucch_dbm(mid_t mod_id, mid_t ue_id, int CC_id) { int flexran_get_p0_pucch_dbm(mid_t mod_id, mid_t ue_id, int CC_id) {
LTE_eNB_UE_stats *eNB_UE_stats = NULL; LTE_eNB_UE_stats *eNB_UE_stats = NULL;
uint32_t rnti = flexran_get_ue_crnti(mod_id,ue_id); uint32_t rnti = flexran_get_ue_crnti(mod_id,ue_id);
eNB_UE_stats = mac_xface->get_eNB_UE_stats(mod_id, CC_id, rnti); eNB_UE_stats = mac_xface->get_eNB_UE_stats(mod_id, CC_id, rnti);
if (eNB_UE_stats == NULL) { if (eNB_UE_stats == NULL) {
return -1; return -1;
} }
if(eNB_UE_stats->Po_PUCCH_update == 1) { // if(eNB_UE_stats->Po_PUCCH_update == 1) {
return eNB_UE_stats->Po_PUCCH_dBm; return eNB_UE_stats->Po_PUCCH_dBm;
} //}
else //else
return -1; // return -1;
} }
int flexran_get_p0_nominal_pucch(mid_t mod_id, int CC_id) { int flexran_get_p0_nominal_pucch(mid_t mod_id, int CC_id) {
int32_t pucch_rx_received = mac_xface->get_target_pucch_rx_power(mod_id, CC_id); int32_t pucch_rx_received = mac_xface->get_target_pucch_rx_power(mod_id, CC_id);
return pucch_rx_received; return pucch_rx_received;
} }
int flexran_get_p0_pucch_status(mid_t mod_id, mid_t ue_id, int CC_id) { int flexran_get_p0_pucch_status(mid_t mod_id, mid_t ue_id, int CC_id) {
LTE_eNB_UE_stats *eNB_UE_stats = NULL; LTE_eNB_UE_stats *eNB_UE_stats = NULL;
uint32_t rnti = flexran_get_ue_crnti(mod_id,ue_id); uint32_t rnti = flexran_get_ue_crnti(mod_id,ue_id);
eNB_UE_stats = mac_xface->get_eNB_UE_stats(mod_id, CC_id, rnti); eNB_UE_stats = mac_xface->get_eNB_UE_stats(mod_id, CC_id, rnti);
return eNB_UE_stats->Po_PUCCH_update; return eNB_UE_stats->Po_PUCCH_update;
} }
int flexran_update_p0_pucch(mid_t mod_id, mid_t ue_id, int CC_id) { int flexran_update_p0_pucch(mid_t mod_id, mid_t ue_id, int CC_id) {
LTE_eNB_UE_stats *eNB_UE_stats = NULL; LTE_eNB_UE_stats *eNB_UE_stats = NULL;
uint32_t rnti = flexran_get_ue_crnti(mod_id,ue_id); uint32_t rnti = flexran_get_ue_crnti(mod_id,ue_id);
eNB_UE_stats = mac_xface->get_eNB_UE_stats(mod_id, CC_id, rnti); eNB_UE_stats = mac_xface->get_eNB_UE_stats(mod_id, CC_id, rnti);
eNB_UE_stats->Po_PUCCH_update = 0; eNB_UE_stats->Po_PUCCH_update = 0;
return 0; return 0;
} }
......
...@@ -185,8 +185,14 @@ int flexran_get_ue_wcqi (mid_t mod_id, mid_t ue_id); ...@@ -185,8 +185,14 @@ int flexran_get_ue_wcqi (mid_t mod_id, mid_t ue_id);
/* Get the transmission queue size for a UE with a channel_id logical channel id */ /* Get the transmission queue size for a UE with a channel_id logical channel id */
int flexran_get_tx_queue_size(mid_t mod_id, mid_t ue_id, logical_chan_id_t channel_id); int flexran_get_tx_queue_size(mid_t mod_id, mid_t ue_id, logical_chan_id_t channel_id);
/* Get the head of line delay for a UE with a channel_id logical channel id */
int flexran_get_hol_delay(mid_t mod_id, mid_t ue_id, logical_chan_id_t channel_id);
/* Check the status of the timing advance for a UE */
short flexran_get_TA(mid_t mod_id, mid_t ue_id, int CC_id);
/* Update the timing advance status (find out whether a timing advance command is required) */ /* Update the timing advance status (find out whether a timing advance command is required) */
int flexran_update_TA(mid_t mod_id, mid_t ue_id, int CC_id); void flexran_update_TA(mid_t mod_id, mid_t ue_id, int CC_id);
/* Return timing advance MAC control element for a designated cell and UE */ /* Return timing advance MAC control element for a designated cell and UE */
int flexran_get_MAC_CE_bitmap_TA(mid_t mod_id, mid_t ue_id, int CC_id); int flexran_get_MAC_CE_bitmap_TA(mid_t mod_id, mid_t ue_id, int CC_id);
......
...@@ -45,4 +45,8 @@ extern AGENT_MAC_xface *agent_mac_xface[NUM_MAX_ENB]; ...@@ -45,4 +45,8 @@ extern AGENT_MAC_xface *agent_mac_xface[NUM_MAX_ENB];
/* Flag indicating whether the VSFs for the MAC control module have been registered */ /* Flag indicating whether the VSFs for the MAC control module have been registered */
extern unsigned int mac_agent_registered[NUM_MAX_ENB]; extern unsigned int mac_agent_registered[NUM_MAX_ENB];
/* Requried to know which UEs had a harq updated over some subframe */
extern int harq_pid_updated[NUMBER_OF_UE_MAX][8];
extern int harq_pid_round[NUMBER_OF_UE_MAX][8];
#endif #endif
...@@ -172,7 +172,7 @@ Protocol__FlexranMessage* flexran_agent_process_timeout(long timer_id, void* tim ...@@ -172,7 +172,7 @@ Protocol__FlexranMessage* flexran_agent_process_timeout(long timer_id, void* tim
struct flexran_agent_timer_element_s *found = get_timer_entry(timer_id); struct flexran_agent_timer_element_s *found = get_timer_entry(timer_id);
if (found == NULL ) goto error; if (found == NULL ) goto error;
LOG_I(FLEXRAN_AGENT, "Found the entry (%p): timer_id is 0x%lx 0x%lx\n", found, timer_id, found->timer_id); LOG_D(FLEXRAN_AGENT, "Found the entry (%p): timer_id is 0x%lx 0x%lx\n", found, timer_id, found->timer_id);
if (timer_args == NULL) if (timer_args == NULL)
LOG_W(FLEXRAN_AGENT,"null timer args\n"); LOG_W(FLEXRAN_AGENT,"null timer args\n");
......
...@@ -131,19 +131,6 @@ void _assign_rbs_required (module_id_t Mod_id, ...@@ -131,19 +131,6 @@ void _assign_rbs_required (module_id_t Mod_id,
uint16_t nb_rbs_allowed_slice[MAX_NUM_CCs][MAX_NUM_SLICES], uint16_t nb_rbs_allowed_slice[MAX_NUM_CCs][MAX_NUM_SLICES],
int min_rb_unit[MAX_NUM_CCs]); int min_rb_unit[MAX_NUM_CCs]);
int _maxround(module_id_t Mod_id,
uint16_t rnti,
int frame,
sub_frame_t subframe,
uint8_t ul_flag );
int _maxcqi(module_id_t Mod_id,
int32_t UE_id);
void _sort_UEs (module_id_t Mod_idP,
int frameP,
sub_frame_t subframeP);
void _dlsch_scheduler_pre_processor (module_id_t Mod_id, void _dlsch_scheduler_pre_processor (module_id_t Mod_id,
int slice_id, int slice_id,
frame_t frameP, frame_t frameP,
......
...@@ -53,6 +53,9 @@ ...@@ -53,6 +53,9 @@
#include "header.pb-c.h" #include "header.pb-c.h"
#include "flexran.pb-c.h" #include "flexran.pb-c.h"
#include "flexran_agent_extern.h"
#include "flexran_agent_common.h"
#include "SIMULATION/TOOLS/defs.h" // for taus #include "SIMULATION/TOOLS/defs.h" // for taus
...@@ -97,10 +100,10 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id, ...@@ -97,10 +100,10 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id,
unsigned char header_len = 0, header_len_tmp = 0; unsigned char header_len = 0, header_len_tmp = 0;
unsigned char sdu_lcids[11],offset,num_sdus=0; unsigned char sdu_lcids[11],offset,num_sdus=0;
uint16_t nb_rb; uint16_t nb_rb;
uint16_t TBS,j,sdu_lengths[11],rnti,padding=0,post_padding=0; uint16_t TBS, sdu_lengths[11],rnti,padding=0,post_padding=0;
unsigned char dlsch_buffer[MAX_DLSCH_PAYLOAD_BYTES]; unsigned char dlsch_buffer[MAX_DLSCH_PAYLOAD_BYTES];
unsigned char round = 0; uint8_t round = 0;
unsigned char harq_pid = 0; uint8_t harq_pid = 0;
// LTE_DL_FRAME_PARMS *frame_parms[MAX_NUM_CCs]; // LTE_DL_FRAME_PARMS *frame_parms[MAX_NUM_CCs];
LTE_eNB_UE_stats *eNB_UE_stats = NULL; LTE_eNB_UE_stats *eNB_UE_stats = NULL;
uint16_t sdu_length_total = 0; uint16_t sdu_length_total = 0;
...@@ -112,17 +115,16 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id, ...@@ -112,17 +115,16 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id,
int last_sdu_header_len = 0; int last_sdu_header_len = 0;
int i; int i, j;
Protocol__FlexDlData *dl_data; Protocol__FlexDlData *dl_data;
Protocol__FlexDlDci *dl_dci; Protocol__FlexDlDci *dl_dci;
uint32_t rlc_size, n_lc, lcid; uint32_t rlc_size, n_lc, lcid;
// For each UE-related command // For each UE-related command
for (i = 0; i < n_dl_ue_data; i++) { for (i = 0; i < n_dl_ue_data; i++) {
dl_data = dl_ue_data[i]; dl_data = dl_ue_data[i];
dl_dci = dl_data->dl_dci; dl_dci = dl_data->dl_dci;
...@@ -138,6 +140,9 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id, ...@@ -138,6 +140,9 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id,
round = dl_dci->rv[0]; round = dl_dci->rv[0];
harq_pid = dl_dci->harq_process; harq_pid = dl_dci->harq_process;
//LOG_I(FLEXRAN_AGENT, "[Frame %d][Subframe %d] Scheduling harq %d\n", frame, subframe, harq_pid);
// LOG_I(FLEXRAN_AGENT, "[Frame %d][Subframe %d]Now scheduling harq_pid %d (round %d)\n", frame, subframe, harq_pid, round);
// If this is a new transmission // If this is a new transmission
if (round == 0) { if (round == 0) {
// First we have to deal with the creation of the PDU based on the message instructions // First we have to deal with the creation of the PDU based on the message instructions
...@@ -147,27 +152,22 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id, ...@@ -147,27 +152,22 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id,
if (dl_data->n_ce_bitmap > 0) { if (dl_data->n_ce_bitmap > 0) {
//Check if there is TA command and set the length appropriately //Check if there is TA command and set the length appropriately
ta_len = (dl_data->ce_bitmap[0] & PROTOCOL__FLEX_CE_TYPE__FLPCET_TA) ? 1 : 0; ta_len = (dl_data->ce_bitmap[0] & PROTOCOL__FLEX_CE_TYPE__FLPCET_TA) ? 2 : 0;
} }
num_sdus = 0; num_sdus = 0;
sdu_length_total = 0; sdu_length_total = 0;
if (ta_len > 0) {
// Reset the measurement
ue_sched_ctl->ta_timer = 20;
eNB_UE_stats->timing_advance_update = 0;
header_len = ta_len;
last_sdu_header_len = ta_len;
}
n_lc = dl_data->n_rlc_pdu; n_lc = dl_data->n_rlc_pdu;
// Go through each one of the channel commands and create SDUs // Go through each one of the channel commands and create SDUs
for (i = 0; i < n_lc; i++) { header_len = 0;
lcid = dl_data->rlc_pdu[i]->rlc_pdu_tb[0]->logical_channel_id; last_sdu_header_len = 0;
rlc_size = dl_data->rlc_pdu[i]->rlc_pdu_tb[0]->size; for (j = 0; j < n_lc; j++) {
LOG_D(MAC,"[TEST] [eNB %d] Frame %d, LCID %d, CC_id %d, Requesting %d bytes from RLC (RRC message)\n", sdu_lengths[j] = 0;
mod_id, frame, lcid, CC_id, rlc_size); lcid = dl_data->rlc_pdu[j]->rlc_pdu_tb[0]->logical_channel_id;
rlc_size = dl_data->rlc_pdu[j]->rlc_pdu_tb[0]->size;
LOG_D(MAC,"[TEST] [eNB %d] [Frame %d] [Subframe %d], LCID %d, CC_id %d, Requesting %d bytes from RLC (RRC message)\n",
mod_id, frame, subframe, lcid, CC_id, rlc_size);
if (rlc_size > 0) { if (rlc_size > 0) {
rlc_status = mac_rlc_status_ind(mod_id, rlc_status = mac_rlc_status_ind(mod_id,
...@@ -181,10 +181,14 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id, ...@@ -181,10 +181,14 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id,
if (rlc_status.bytes_in_buffer > 0) { if (rlc_status.bytes_in_buffer > 0) {
if (rlc_size <= 2) { if (rlc_status.bytes_in_buffer < rlc_size) {
rlc_size = 3; rlc_size = rlc_status.bytes_in_buffer;
} }
if (rlc_size <= 2) {
rlc_size = 3;
}
rlc_status = mac_rlc_status_ind(mod_id, rlc_status = mac_rlc_status_ind(mod_id,
rnti, rnti,
mod_id, mod_id,
...@@ -194,29 +198,27 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id, ...@@ -194,29 +198,27 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id,
lcid, lcid,
rlc_size); // transport block set size rlc_size); // transport block set size
sdu_lengths[i] = 0;
LOG_D(MAC, "[TEST] RLC can give %d bytes for LCID %d during second call\n", rlc_status.bytes_in_buffer, lcid); LOG_D(MAC, "[TEST] RLC can give %d bytes for LCID %d during second call\n", rlc_status.bytes_in_buffer, lcid);
if (rlc_status.bytes_in_buffer > 0) { if (rlc_status.bytes_in_buffer > 0) {
sdu_lengths[i] += mac_rlc_data_req(mod_id, sdu_lengths[j] = mac_rlc_data_req(mod_id,
rnti, rnti,
mod_id, mod_id,
frame, frame,
ENB_FLAG_YES, ENB_FLAG_YES,
MBMS_FLAG_NO, MBMS_FLAG_NO,
lcid, lcid,
(char *)&dlsch_buffer[sdu_length_total]); (char *)&dlsch_buffer[sdu_length_total]);
LOG_D(MAC,"[eNB %d][LCID %d] CC_id %d Got %d bytes from RLC\n",mod_id, lcid, CC_id, sdu_lengths[i]); LOG_D(MAC,"[eNB %d][LCID %d] CC_id %d Got %d bytes from RLC\n",mod_id, lcid, CC_id, sdu_lengths[j]);
sdu_length_total += sdu_lengths[i]; sdu_length_total += sdu_lengths[j];
sdu_lcids[i] = lcid; sdu_lcids[j] = lcid;
UE_list->eNB_UE_stats[CC_id][UE_id].num_pdu_tx[lcid] += 1; UE_list->eNB_UE_stats[CC_id][UE_id].num_pdu_tx[lcid] += 1;
UE_list->eNB_UE_stats[CC_id][UE_id].num_bytes_tx[lcid] += sdu_lengths[i]; UE_list->eNB_UE_stats[CC_id][UE_id].num_bytes_tx[lcid] += sdu_lengths[j];
if (sdu_lengths[i] <= 128) { if (sdu_lengths[j] < 128) {
header_len += 2; header_len += 2;
last_sdu_header_len = 2; last_sdu_header_len = 2;
} else { } else {
...@@ -230,38 +232,46 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id, ...@@ -230,38 +232,46 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id,
} // SDU creation end } // SDU creation end
if (((sdu_length_total + header_len) > 0)) { if (((sdu_length_total + header_len + ta_len) > 0)) {
// header_len_tmp = header_len; header_len_tmp = header_len;
// If we have only a single SDU, header length becomes 1 // If we have only a single SDU, header length becomes 1
if ((num_sdus + ta_len) == 1) { if ((num_sdus) == 1) {
//if (header_len == 2 || header_len == 3) { //if (header_len == 2 || header_len == 3) {
header_len = 1; header_len = 1;
} else { } else {
header_len = (header_len - last_sdu_header_len) + 1; header_len = (header_len - last_sdu_header_len) + 1;
} }
// there is a payload // If we need a 1 or 2 bit padding or no padding at all
if (((sdu_length_total + header_len) > 0)) { if ((TBS - header_len - sdu_length_total - ta_len) <= 2
// If we need a 1 or 2 bit padding or no padding at all || (TBS - header_len - sdu_length_total - ta_len) > TBS) { //protect from overflow
if ((TBS - header_len - sdu_length_total - ta_len) <= 2 padding = (TBS - header_len - sdu_length_total - ta_len);
|| (TBS - header_len - sdu_length_total - ta_len) > TBS) { //protect from overflow post_padding = 0;
padding = (TBS - header_len - sdu_length_total - ta_len); } else { // The last sdu needs to have a length field, since we add padding
post_padding = 0; padding = 0;
} else { // The last sdu needs to have a length field, since we add padding header_len = header_len_tmp;
padding = 0; post_padding = TBS - sdu_length_total - header_len - ta_len; // 1 is for the postpadding header
header_len = header_len_tmp; }
post_padding = TBS - sdu_length_total - header_len - ta_len - 1; // 1 is for the postpadding header
} if (ta_len > 0) {
// Reset the measurement
ta_update = flexran_get_TA(mod_id, UE_id, CC_id);
ue_sched_ctl->ta_timer = 20;
eNB_UE_stats->timing_advance_update = 0;
} else {
ta_update = 0;
} }
ta_update = (ta_len > 0) ? ue_sched_ctl->ta_update : 0;
// If there is nothing to schedule, just leave // If there is nothing to schedule, just leave
if ((sdu_length_total) <= 0) { if ((sdu_length_total) <= 0) {
return; harq_pid_updated[UE_id][harq_pid] = 1;
harq_pid_round[UE_id][harq_pid] = 0;
continue;
} }
// LOG_I(FLEXRAN_AGENT, "[Frame %d][Subframe %d] TBS is %d and bytes are %d\n", frame, subframe, TBS, sdu_length_total);
offset = generate_dlsch_header((unsigned char*)UE_list->DLSCH_pdu[CC_id][0][UE_id].payload[0], offset = generate_dlsch_header((unsigned char*)UE_list->DLSCH_pdu[CC_id][0][UE_id].payload[0],
num_sdus, //num_sdus num_sdus, //num_sdus
...@@ -272,6 +282,10 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id, ...@@ -272,6 +282,10 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id,
NULL, // contention res id NULL, // contention res id
padding, padding,
post_padding); post_padding);
#ifdef DEBUG_eNB_SCHEDULER #ifdef DEBUG_eNB_SCHEDULER
LOG_T(MAC,"[eNB %d] First 16 bytes of DLSCH : \n"); LOG_T(MAC,"[eNB %d] First 16 bytes of DLSCH : \n");
...@@ -289,7 +303,7 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id, ...@@ -289,7 +303,7 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id,
// fill remainder of DLSCH with random data // fill remainder of DLSCH with random data
for (j=0; j<(TBS-sdu_length_total-offset); j++) { for (j=0; j<(TBS-sdu_length_total-offset); j++) {
UE_list->DLSCH_pdu[CC_id][0][UE_id].payload[0][offset+sdu_length_total+j] = (char)(taus()&0xff); UE_list->DLSCH_pdu[CC_id][0][UE_id].payload[0][offset+sdu_length_total+j] = (char)(taus()&0xff);
} }
//eNB_mac_inst[0].DLSCH_pdu[0][0].payload[0][offset+sdu_lengths[0]+j] = (char)(taus()&0xff); //eNB_mac_inst[0].DLSCH_pdu[0][0].payload[0][offset+sdu_lengths[0]+j] = (char)(taus()&0xff);
if (opt_enabled == 1) { if (opt_enabled == 1) {
...@@ -319,6 +333,8 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id, ...@@ -319,6 +333,8 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id,
nb_rb += get_min_rb_unit(mod_id, CC_id); nb_rb += get_min_rb_unit(mod_id, CC_id);
stats_tbs = mac_xface->get_TBS_DL(dl_dci->mcs[0], nb_rb); stats_tbs = mac_xface->get_TBS_DL(dl_dci->mcs[0], nb_rb);
} }
// LOG_I(FLEXRAN_AGENT, "The MCS was %d\n", dl_dci->mcs[0]);
UE_list->eNB_UE_stats[CC_id][UE_id].rbs_used = nb_rb; UE_list->eNB_UE_stats[CC_id][UE_id].rbs_used = nb_rb;
UE_list->eNB_UE_stats[CC_id][UE_id].total_rbs_used += nb_rb; UE_list->eNB_UE_stats[CC_id][UE_id].total_rbs_used += nb_rb;
...@@ -333,10 +349,14 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id, ...@@ -333,10 +349,14 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id,
//eNB_UE_stats->dlsch_mcs1 = cqi_to_mcs[eNB_UE_stats->DL_cqi[0]]; //eNB_UE_stats->dlsch_mcs1 = cqi_to_mcs[eNB_UE_stats->DL_cqi[0]];
//eNB_UE_stats->dlsch_mcs1 = cmin(eNB_UE_stats->dlsch_mcs1, openair_daq_vars.target_ue_dl_mcs); //eNB_UE_stats->dlsch_mcs1 = cmin(eNB_UE_stats->dlsch_mcs1, openair_daq_vars.target_ue_dl_mcs);
} else {
LOG_D(FLEXRAN_AGENT, "No need to schedule a dci after all. Just drop it\n");
harq_pid_updated[UE_id][harq_pid] = 1;
harq_pid_round[UE_id][harq_pid] = 0;
continue;
} }
} else { } else {
// No need to create anything apart of DCI in case of retransmission // No need to create anything apart of DCI in case of retransmission
/*TODO: Must add these */ /*TODO: Must add these */
// eNB_UE_stats->dlsch_trials[round]++; // eNB_UE_stats->dlsch_trials[round]++;
//UE_list->eNB_UE_stats[CC_id][UE_id].num_retransmission+=1; //UE_list->eNB_UE_stats[CC_id][UE_id].num_retransmission+=1;
...@@ -345,8 +365,8 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id, ...@@ -345,8 +365,8 @@ void flexran_apply_ue_spec_scheduling_decisions(mid_t mod_id,
//UE_list->eNB_UE_stats[CC_id][UE_id].ncce_used_retx=nCCECC_id]; //UE_list->eNB_UE_stats[CC_id][UE_id].ncce_used_retx=nCCECC_id];
} }
UE_list->UE_template[CC_id][UE_id].oldNDI[dl_dci->harq_process] = dl_dci->ndi[0]; // UE_list->UE_template[CC_id][UE_id].oldNDI[dl_dci->harq_process] = dl_dci->ndi[0];
eNB_UE_stats->dlsch_mcs1 = dl_dci->mcs[0]; // eNB_UE_stats->dlsch_mcs1 = dl_dci->mcs[0];
//Fill the proper DCI of OAI //Fill the proper DCI of OAI
flexran_fill_oai_dci(mod_id, CC_id, rnti, dl_dci); flexran_fill_oai_dci(mod_id, CC_id, rnti, dl_dci);
......
...@@ -68,7 +68,7 @@ ...@@ -68,7 +68,7 @@
/* this function checks that get_eNB_UE_stats returns /* this function checks that get_eNB_UE_stats returns
* a non-NULL pointer for all CCs for a given UE * a non-NULL pointer for all CCs for a given UE
*/ */
static int phy_stats_exist(module_id_t Mod_id, int rnti) int phy_stats_exist(module_id_t Mod_id, int rnti)
{ {
int CC_id; int CC_id;
for (CC_id = 0; CC_id < MAX_NUM_CCs; CC_id++) for (CC_id = 0; CC_id < MAX_NUM_CCs; CC_id++)
......
...@@ -536,6 +536,7 @@ void store_ulsch_buffer(module_id_t module_idP, int frameP, sub_frame_t subframe ...@@ -536,6 +536,7 @@ void store_ulsch_buffer(module_id_t module_idP, int frameP, sub_frame_t subframe
void sort_ue_ul (module_id_t module_idP,int frameP, sub_frame_t subframeP); void sort_ue_ul (module_id_t module_idP,int frameP, sub_frame_t subframeP);
void assign_max_mcs_min_rb(module_id_t module_idP,int frameP, sub_frame_t subframeP,uint16_t *first_rb); void assign_max_mcs_min_rb(module_id_t module_idP,int frameP, sub_frame_t subframeP,uint16_t *first_rb);
void adjust_bsr_info(int buffer_occupancy, uint16_t TBS, UE_TEMPLATE *UE_template); void adjust_bsr_info(int buffer_occupancy, uint16_t TBS, UE_TEMPLATE *UE_template);
int phy_stats_exist(module_id_t Mod_id, int rnti);
/*! \fn UE_L2_state_t ue_scheduler(const module_id_t module_idP,const frame_t frameP, const sub_frame_t subframe, const lte_subframe_t direction,const uint8_t eNB_index) /*! \fn UE_L2_state_t ue_scheduler(const module_id_t module_idP,const frame_t frameP, const sub_frame_t subframe, const lte_subframe_t direction,const uint8_t eNB_index)
\brief UE scheduler where all the ue background tasks are done. This function performs the following: 1) Trigger PDCP every 5ms 2) Call RRC for link status return to PHY3) Perform SR/BSR procedures for scheduling feedback 4) Perform PHR procedures. \brief UE scheduler where all the ue background tasks are done. This function performs the following: 1) Trigger PDCP every 5ms 2) Call RRC for link status return to PHY3) Perform SR/BSR procedures for scheduling feedback 4) Perform PHR procedures.
......
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