diff --git a/openair2/LAYER2/MAC/eNB_scheduler.c b/openair2/LAYER2/MAC/eNB_scheduler.c index 44ed72963d..4539fe8d02 100644 --- a/openair2/LAYER2/MAC/eNB_scheduler.c +++ b/openair2/LAYER2/MAC/eNB_scheduler.c @@ -55,8 +55,8 @@ #include "RRC/LITE/extern.h" #include "RRC/L2_INTERFACE/openair_rrc_L2_interface.h" - //#include "LAYER2/MAC/pre_processor.c" +#include "pdcp.h" double snr_mcs[28]={-4.1130, -3.3830, -2.8420, -2.0480, -1.3230, -0.6120, 0.1080, 0.977, 1.7230, 2.7550, 3.1960, 3.8080, 4.6870, 5.6840, 6.6550, 7.7570, 8.3730, 9.3040, 9.5990, 10.9020, 11.7220, 12.5950, 13.4390, 14.8790, 15.8800, 16.4800, 17.8690, 18.7690}; int cqi_mcs[3][16] = {{0, 0, 0, 2, 4, 6, 8, 11, 13, 15, 18, 20, 22, 25, 27, 27},{0, 0, 0, 2, 4, 6, 8, 11, 13, 15, 18, 20, 22, 25, 27, 27},{0, 0, 0, 2, 4, 6, 8, 11, 13, 15, 18, 19, 22, 24, 26, 27}}; @@ -4199,7 +4199,27 @@ void eNB_dlsch_ulsch_scheduler(u8 Mod_id,u8 cooperation_flag, u32 frame, u8 subf //if (subframe%5 == 0) #ifdef EXMIMO - pdcp_run(frame, 1, 0, Mod_id); + //pdcp_run(frame, 1, 0, Mod_id); + + if (pthread_mutex_lock (&pdcp_mutex) != 0) { + LOG_E(PDCP,"Cannot lock mutex\n"); + //return(-1); + } + else { + pdcp_instance_cnt++; + pthread_mutex_unlock(&pdcp_mutex); + + if (pdcp_instance_cnt == 0) { + if (pthread_cond_signal(&pdcp_cond) != 0) { + LOG_E(PDCP,"pthread_cond_signal unsuccessfull\n"); + //return(-1); + } + } + else { + LOG_W(PDCP,"PDCP thread busy!!! inst_cnt=%d\n",pdcp_instance_cnt); + } + } + #endif #ifdef CELLULAR rrc_rx_tx(Mod_id, frame, 0, 0); diff --git a/openair2/LAYER2/MAC/ue_procedures.c b/openair2/LAYER2/MAC/ue_procedures.c index b23b675718..0f9ef781bb 100644 --- a/openair2/LAYER2/MAC/ue_procedures.c +++ b/openair2/LAYER2/MAC/ue_procedures.c @@ -35,6 +35,10 @@ */ +#ifdef EXMIMO +#include +#endif + #include "extern.h" #include "defs.h" #ifdef PHY_EMUL @@ -54,6 +58,7 @@ #ifdef PHY_EMUL #include "SIMULATION/simulation_defs.h" #endif +#include "pdcp.h" #define DEBUG_HEADER_PARSING 1 #define ENABLE_MAC_PAYLOAD_DEBUG @@ -1211,7 +1216,27 @@ UE_L2_STATE_t ue_scheduler(u8 Mod_id,u32 frame, u8 subframe, lte_subframe_t dire //Rrc_xface->Frame_index=Mac_rlc_xface->frame; //if (subframe%5 == 0) #ifdef EXMIMO - pdcp_run(frame, 0, Mod_id, eNB_index); + //pdcp_run(frame, 0, Mod_id, eNB_index); + + if (pthread_mutex_lock (&pdcp_mutex) != 0) { + LOG_E(PDCP,"Cannot lock mutex\n"); + //return(-1); + } + else { + pdcp_instance_cnt++; + pthread_mutex_unlock(&pdcp_mutex); + + if (pdcp_instance_cnt == 0) { + if (pthread_cond_signal(&pdcp_cond) != 0) { + LOG_E(PDCP,"pthread_cond_signal unsuccessfull\n"); + //return(-1); + } + } + else { + LOG_W(PDCP,"PDCP thread busy!!! inst_cnt=%d\n",pdcp_instance_cnt); + } + } + #endif UE_mac_inst[Mod_id].frame = frame; UE_mac_inst[Mod_id].subframe = subframe; diff --git a/openair2/LAYER2/Makefile.inc b/openair2/LAYER2/Makefile.inc index 85100ca6f7..cae185260b 100644 --- a/openair2/LAYER2/Makefile.inc +++ b/openair2/LAYER2/Makefile.inc @@ -26,6 +26,7 @@ SOURCES_L2 += $(PDCP_DIR)/pdcp_fifo.c SOURCES_L2 += $(PDCP_DIR)/pdcp_sequence_manager.c SOURCES_L2 += $(PDCP_DIR)/pdcp_primitives.c SOURCES_L2 += $(PDCP_DIR)/pdcp_util.c +SOURCES_L2 += $(PDCP_DIR)/pdcp_thread.c SOURCES_L2 += $(RLC_AM_DIR)/rlc_am.c SOURCES_L2 += $(RLC_AM_DIR)/rlc_am_init.c diff --git a/openair2/LAYER2/PDCP_v10.1.0/pdcp.h b/openair2/LAYER2/PDCP_v10.1.0/pdcp.h index 49215f9a14..6ec0d67bc5 100755 --- a/openair2/LAYER2/PDCP_v10.1.0/pdcp.h +++ b/openair2/LAYER2/PDCP_v10.1.0/pdcp.h @@ -84,6 +84,17 @@ #define FALSE (0x00) #define TRUE !(FALSE) + +extern pthread_t pdcp_thread; +extern pthread_attr_t pdcp_thread_attr; +extern pthread_mutex_t pdcp_mutex; +extern pthread_cond_t pdcp_cond; +extern int pdcp_instance_cnt; + +static void *pdcp_thread_main(void* param); +int init_pdcp_thread(u8 eNB_flag); +void cleanup_pdcp_thread(void); + typedef unsigned char BOOL; public_pdcp(unsigned int Pdcp_stats_tx[NB_MODULES_MAX][NB_CNX_CH][NB_RAB_MAX]); diff --git a/openair2/LAYER2/PDCP_v10.1.0/pdcp_thread.c b/openair2/LAYER2/PDCP_v10.1.0/pdcp_thread.c new file mode 100644 index 0000000000..8c2b37bb6c --- /dev/null +++ b/openair2/LAYER2/PDCP_v10.1.0/pdcp_thread.c @@ -0,0 +1,154 @@ +/******************************************************************************* + + Eurecom OpenAirInterface + Copyright(c) 1999 - 2011 Eurecom + + This program is free software; you can redistribute it and/or modify it + under the terms and conditions of the GNU General Public License, + version 2, as published by the Free Software Foundation. + + This program is distributed in the hope it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for + more details. + + You should have received a copy of the GNU General Public License along with + this program; if not, write to the Free Software Foundation, Inc., + 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA. + + The full GNU General Public License is included in this distribution in + the file called "COPYING". + + Contact Information + Openair Admin: openair_admin@eurecom.fr + Openair Tech : openair_tech@eurecom.fr + Forums : http://forums.eurecom.fsr/openairinterface + Address : Eurecom, 2229, route des crĂȘtes, 06560 Valbonne Sophia Antipolis, France + +*******************************************************************************/ + +/*! \file pdcp_thread.c +* \brief +* \author F. Kaltenberger +* \date 2013 +* \version 0.1 +* \company Eurecom +* \email: florian.kaltenberger@eurecom.fr +* \note +* \warning +*/ +#include +//#include + +#include "pdcp.h" +#include "PHY/extern.h" //for PHY_vars +#include "UTIL/LOG/log.h" +#include "UTIL/LOG/vcd_signal_dumper.h" + +#define OPENAIR_THREAD_STACK_SIZE 8192 +#define OPENAIR_THREAD_PRIORITY 255 + +extern int oai_exit; + +pthread_t pdcp_thread; +pthread_attr_t pdcp_thread_attr; +pthread_mutex_t pdcp_mutex; +pthread_cond_t pdcp_cond; +int pdcp_instance_cnt; + +static void *pdcp_thread_main(void* param) { + + u8 eNB_flag = *((u8*)param); + + while (!oai_exit) { + + if (pthread_mutex_lock(&pdcp_mutex) != 0) { + LOG_E(PDCP,"Error locking mutex.\n"); + } + else { + while (pdcp_instance_cnt < 0) { + pthread_cond_wait(&pdcp_cond,&pdcp_mutex); + } + if (pthread_mutex_unlock(&pdcp_mutex) != 0) { + LOG_E(PDCP,"Error unlocking mutex.\n"); + } + } + + if (oai_exit) break; + + if (eNB_flag) { + pdcp_run(PHY_vars_eNB_g[0]->frame, eNB_flag, PHY_vars_eNB_g[0]->Mod_id, 0); + //LOG_I(PDCP,"Calling pdcp_run (eNB) for frame %d\n",PHY_vars_eNB_g[0]->frame); + } + else { + pdcp_run(PHY_vars_UE_g[0]->frame, eNB_flag, 0, PHY_vars_UE_g[0]->Mod_id); + //LOG_I(PDCP,"Calling pdcp_run (UE) for frame %d\n",PHY_vars_UE_g[0]->frame); + } + + + if (pthread_mutex_lock(&pdcp_mutex) != 0) { + LOG_E(PDCP,"Error locking mutex.\n"); + } + else { + pdcp_instance_cnt--; + if (pthread_mutex_unlock(&pdcp_mutex) != 0) { + LOG_E(PDCP,"Error unlocking mutex.\n"); + } + } + } + return(NULL); +} + + + +int init_pdcp_thread(u8 eNB_flag) { + + int error_code; + struct sched_param p; + + pthread_attr_init (&pdcp_thread_attr); + pthread_attr_setstacksize(&pdcp_thread_attr,OPENAIR_THREAD_STACK_SIZE); + //attr_dlsch_threads.priority = 1; + + p.sched_priority = OPENAIR_THREAD_PRIORITY; + pthread_attr_setschedparam (&pdcp_thread_attr, &p); +#ifndef RTAI_ISNT_POSIX + pthread_attr_setschedpolicy (&pdcp_thread_attr, SCHED_FIFO); +#endif + pthread_mutex_init(&pdcp_mutex,NULL); + pthread_cond_init(&pdcp_cond,NULL); + + pdcp_instance_cnt = -1; + LOG_I(PDCP,"Allocating PDCP thread\n"); + error_code = pthread_create(&pdcp_thread, + &pdcp_thread_attr, + pdcp_thread_main, + (void*)(&eNB_flag)); + + if (error_code!= 0) { + LOG_I(PDCP,"Could not allocate PDCP thread, error %d\n",error_code); + return(error_code); + } + else { + LOG_I(PDCP,"Allocate PDCP thread successful\n"); + } + + return(0); +} + +void cleanup_pdcp_thread(void) { + void *status; + + LOG_I(PDCP,"Scheduling PDCP thread to exit\n"); + + pdcp_instance_cnt = 0; + if (pthread_cond_signal(&pdcp_cond) != 0) + LOG_I(PDCP,"ERROR pthread_cond_signal\n"); + else + LOG_I(PDCP,"Signalled PDCP thread to exit\n"); + + pthread_join(pdcp_thread,&status); + LOG_I(PDCP,"PDCP thread exited\n"); + pthread_cond_destroy(&pdcp_cond); + pthread_mutex_destroy(&pdcp_mutex); +} diff --git a/openair2/LAYER2/RLC/UM_v9.3.0/rlc_um_dar.c b/openair2/LAYER2/RLC/UM_v9.3.0/rlc_um_dar.c index a0473dd563..aa9fd3318c 100644 --- a/openair2/LAYER2/RLC/UM_v9.3.0/rlc_um_dar.c +++ b/openair2/LAYER2/RLC/UM_v9.3.0/rlc_um_dar.c @@ -364,14 +364,14 @@ void rlc_um_try_reassembly(rlc_um_entity_t *rlcP, u32_t frame, u8_t eNB_flag, si rlcP->reassembly_missing_sn_detected = 0; break; default: + LOG_W(RLC, "[MSC_NBOX][FRAME %05d][RLC_UM][MOD %02d][RB %02d][Missing SN detected][RLC_UM][MOD %02d][RB %02d]\n", + frame, rlcP->module_id,rlcP->rb_id, rlcP->module_id,rlcP->rb_id); #ifdef USER_MODE assert(1 != 1); #endif rlcP->stat_rx_data_pdu_dropped += 1; rlcP->stat_rx_data_bytes_dropped += tb_ind->size; - LOG_W(RLC, "[MSC_NBOX][FRAME %05d][RLC_UM][MOD %02d][RB %02d][Missing SN detected][RLC_UM][MOD %02d][RB %02d]\n", - frame, rlcP->module_id,rlcP->rb_id, rlcP->module_id,rlcP->rb_id); rlcP->reassembly_missing_sn_detected = 1; } } @@ -381,8 +381,8 @@ void rlc_um_try_reassembly(rlc_um_entity_t *rlcP, u32_t frame, u8_t eNB_flag, si rlcP->dar_buffer[sn] = NULL; } else { rlcP->last_reassemblied_missing_sn = sn; - LOG_W(RLC, "[MSC_NBOX][FRAME %05d][RLC_UM][MOD %02d][RB %02d][Missing SN %04d detected, clearing RX SDU][RLC_UM][MOD %02d][RB %02d]\n", - frame, rlcP->module_id,rlcP->rb_id, sn, rlcP->module_id,rlcP->rb_id); + LOG_D(RLC, "[MSC_NBOX][FRAME %05d][RLC_UM][MOD %02d][RB %02d][Missing SN %04d detected, clearing RX SDU][RLC_UM][MOD %02d][RB %02d]\n", + frame, rlcP->module_id,rlcP->rb_id, sn, rlcP->module_id,rlcP->rb_id); rlcP->reassembly_missing_sn_detected = 1; rlc_um_clear_rx_sdu(rlcP); } diff --git a/openair2/RRC/LITE/defs.h b/openair2/RRC/LITE/defs.h index d8a024cc28..2e005a848c 100644 --- a/openair2/RRC/LITE/defs.h +++ b/openair2/RRC/LITE/defs.h @@ -461,6 +461,7 @@ void rrc_eNB_process_MeasurementReport(u8 Mod_id,u16 UE_index,MeasResults_t *me //void rrc_ue_process_ueCapabilityEnquiry(uint8_t Mod_id,uint32_t frame,UECapabilityEnquiry_t *UECapabilityEnquiry,uint8_t eNB_index); //void rrc_ue_process_securityModeCommand(uint8_t Mod_id,uint32_t frame,SecurityModeCommand_t *securityModeCommand,uint8_t eNB_index); +void rrc_remove_UE (u8 Mod_id, u8 UE_id); #endif diff --git a/targets/RTAI/USER/lte-softmodem.c b/targets/RTAI/USER/lte-softmodem.c index 4fe43ba3e6..f966ba7086 100644 --- a/targets/RTAI/USER/lte-softmodem.c +++ b/targets/RTAI/USER/lte-softmodem.c @@ -1391,6 +1391,10 @@ int main(int argc, char **argv) { // } #endif +#ifdef OPENAIR2 + init_pdcp_thread(!UE_flag); +#endif + number_of_cards = openair0_num_detected_cards; if (p_exmimo_id->board_exmimoversion==1) //ExpressMIMO1 openair_daq_vars.timing_advance = 138; @@ -1665,6 +1669,10 @@ int main(int argc, char **argv) { #endif } +#ifdef OPENAIR2 + cleanup_pdcp_thread(); +#endif + #ifdef RTAI stop_rt_timer(); #endif