FreeCalypso > hg > fc-tourmaline
view src/cs/layer1/cfile/l1_afunc.c @ 223:740a8e8fc9d7
startup sync logic rework for the new PWON button boot scheme
Previously we added logic to the MMI task to hold off PEI init until
R2D is running, and then extended that condition to wait for FCHG
init too. However, the dependencies of MMI upon R2D and FCHG don't
start until mmiInit(), and that call is driven by Switch_ON() code,
hence the wait for R2D and FCHG init can be made in that code path
instead of the MMI task. Furthermore, with our new way of signaling
PWON button boot to MMI, we need a new wait to ensure that the MMI
task is up - previously this assurance was provided by the wait for
Kp pointers to be set.
Solution: revert our previous PEI init hold-off additions to MMI,
add a new flag indicating MMI task init done, and put the combined
wait for all needed conditions into our new PWON button boot code
in power.c.
author | Mychaela Falconia <falcon@freecalypso.org> |
---|---|
date | Tue, 27 Apr 2021 06:24:52 +0000 |
parents | 4e78acac3d88 |
children |
line wrap: on
line source
/************* Revision Controle System Header ************* * GSM Layer 1 software * L1_AFUNC.C * * Filename l1_afunc.c * Copyright 2003 (C) Texas Instruments * ************* Revision Controle System Header *************/ #define L1_AFUNC_C #include "l1_macro.h" #include "l1_confg.h" #if (CODE_VERSION == SIMULATION) #include <string.h> #include "l1_types.h" #include "sys_types.h" #include "l1_const.h" #include "l1_signa.h" #if TESTMODE #include "l1tm_defty.h" #endif #if (AUDIO_TASK == 1) #include "l1audio_const.h" #include "l1audio_cust.h" #include "l1audio_defty.h" #endif #if (L1_GTT == 1) #include "l1gtt_const.h" #include "l1gtt_defty.h" #endif #if (L1_MIDI == 1) #include "l1midi_defty.h" #endif #if (L1_MP3 == 1) #include "l1mp3_defty.h" #endif //ADDED FOR AAC #if (L1_AAC == 1) #include "l1aac_defty.h" #endif #include "l1_defty.h" #include "cust_os.h" #include "l1_msgty.h" #include "l1_varex.h" #include "l1_proto.h" #include "l1_tabs.h" #include "l1_time.h" #if L1_GPRS #include "l1p_cons.h" #include "l1p_msgt.h" #include "l1p_deft.h" #include "l1p_vare.h" #endif #else #include <string.h> #include "l1_types.h" #include "sys_types.h" #include "l1_const.h" #include "l1_signa.h" #include "l1_time.h" #if TESTMODE #include "l1tm_defty.h" #endif #if (AUDIO_TASK == 1) #include "l1audio_const.h" #include "l1audio_cust.h" #include "l1audio_defty.h" #endif #if (L1_GTT == 1) #include "l1gtt_const.h" #include "l1gtt_defty.h" #endif #if (L1_MP3 == 1) #include "l1mp3_defty.h" #endif #if (L1_MIDI == 1) #include "l1midi_defty.h" #endif //ADDED FOR AAC #if (L1_AAC == 1) #include "l1aac_defty.h" #endif #include "l1_defty.h" #include "cust_os.h" #include "l1_msgty.h" #include "l1_varex.h" #include "l1_proto.h" #include "l1_tabs.h" #if L1_GPRS #include "l1p_cons.h" #include "l1p_msgt.h" #include "l1p_deft.h" #include "l1p_vare.h" #endif #if (GSM_IDLE_RAM > 1) #if (OP_L1_STANDALONE == 1) #include "csmi_simul.h" #else #include "csmi/csmi.h" #endif #endif #endif #if (OP_L1_STANDALONE == 1) #if (ANLG_FAM == 11) #include "bspTwl3029_Madc.h" #endif #endif #if (L1_MADC_ON == 1) #if (OP_L1_STANDALONE == 1) #if (RF_FAM == 61) #include "drp_api.h" #include "l1_rf61.h" #include <string.h> extern T_DRP_SRM_API* drp_srm_api; #endif #if (ANLG_FAM == 11) BspTwl3029_MadcResults l1_madc_results; void l1a_madc_callback(void); #endif #endif #endif //L1_MADC_ON /*-------------------------------------------------------*/ /* l1a_reset_ba_list() */ /*-------------------------------------------------------*/ /* */ /* Description: */ /* ------------ */ /* This function resets the BA list content. */ /* */ /*-------------------------------------------------------*/ void l1a_reset_ba_list() { UWORD8 i; // Rem: this reset function do not touch the "ba_id", "nbr_carrier" and // "radio_freq" fields. //!!! remove this initialization when BA list handling changed for dedic mode if(l1a_l1s_com.mode != I_MODE) { l1a_l1s_com.ba_list.next_to_ctrl = 0; // Carrier for next power measurement control. l1a_l1s_com.ba_list.next_to_read = 0; // Carrier for next power measurement result. l1a_l1s_com.ba_list.first_index = 0; // First BA index measured in current session. } // Reset of "ms_ctrl, ms_ctrl_d, msctrl_dd" is done at L1 startup // and when SYNCHRO task is executed. l1a_l1s_com.ba_list.np_ctrl = 0; // PCH burst number. for(i=0; i<C_BA_PM_MEAS; i++) // 2 measurements / PCH frame... { l1a_l1s_com.ba_list.used_il [i] = l1_config.params.il_min; // IL used in CTRL phase for AGC setting. l1a_l1s_com.ba_list.used_il_d [i] = l1_config.params.il_min; // ... 1 frame delay. l1a_l1s_com.ba_list.used_il_dd[i] = l1_config.params.il_min; // ... 2 frames delay, used in READ phase. l1a_l1s_com.ba_list.used_lna [i] = FALSE; // LNA used in CTRL phase for AGC setting. l1a_l1s_com.ba_list.used_lna_d [i] = FALSE; // ... 1 frame delay. l1a_l1s_com.ba_list.used_lna_dd[i] = FALSE; // ... 2 frames delay, used in READ phase. } for(i=0; i<32+1; i++) { l1a_l1s_com.ba_list.A[i].acc = 0; // Reset IL accumulation. } } /*-------------------------------------------------------*/ /* l1a_reset_full_list() */ /*-------------------------------------------------------*/ /* */ /* Description: */ /* ------------ */ /* This function resets the FULL list content. */ /* */ /*-------------------------------------------------------*/ void l1a_reset_full_list() { UWORD16 i; // Init power measurement multi_session process l1a_l1s_com.full_list.meas_1st_pass_ctrl = 1; // Set 1st pass flag for power measurement session in ctrl. l1a_l1s_com.full_list.meas_1st_pass_read = 1; // Set 1st pass flag for power measurement session in read. l1a_l1s_com.full_list.nbr_sat_carrier_ctrl = 0; // Clear number of saturated carrier in ctrl. l1a_l1s_com.full_list.nbr_sat_carrier_read = 0; // Clear number of saturated carrier in read. // Set global parameters for full list measurement. l1a_l1s_com.full_list.next_to_ctrl = 0; // Set next carrier to control to 1st one. l1a_l1s_com.full_list.next_to_read = 0; // Set next carrier to control to 1st one. // Reset Pipeline // Note: l1a_l1s_com.full_list.ms_ctrl_d is reset at the end of l1_meas_manager() l1a_l1s_com.full_list.ms_ctrl_dd = 0; l1a_l1s_com.full_list.ms_ctrl_d = 0; // Reset the FULL LIST. #if (L1_FF_MULTIBAND == 0) for(i=0; i<l1_config.std.nbmax_carrier; i++) #else for(i=0; i< NBMAX_CARRIER; i++) #endif { l1a_l1s_com.full_list.sat_flag[i] = 0; // Reset sat_flag } #if L1_GPRS // Reset PPCH burst ctrl indication l1pa_l1ps_com.cr_freq_list.pnp_ctrl = 0; #endif } #if ((L1_EOTD == 1) && (L1_EOTD_QBIT_ACC == 1)) /*-------------------------------------------------------*/ /* l1a_add_time_delta() */ /*-------------------------------------------------------*/ /* */ /* Description: */ /* ------------ */ /* This function shifts a given cell timing (given as a */ /* couple [time_alignmt, fn_offset]) by adding */ /* a specified new time_alignmt offset (+ve or -ve */ /* between -4999 and +4999 qb) */ /* to that timing. */ /* */ /*-------------------------------------------------------*/ void l1a_add_time_delta(UWORD32 * time_alignmt, UWORD32 * fn_offset, WORD32 delta) { WORD32 new_time_alignmt = *time_alignmt + delta; UWORD32 new_fn_offset = *fn_offset; if(new_time_alignmt < 0) { new_time_alignmt += TPU_CLOCK_RANGE; new_fn_offset = (new_fn_offset + 1) % MAX_FN; } else if(new_time_alignmt >= TPU_CLOCK_RANGE) { new_time_alignmt -= TPU_CLOCK_RANGE; new_fn_offset = (new_fn_offset - 1 + MAX_FN) % MAX_FN; } *time_alignmt = new_time_alignmt; *fn_offset = new_fn_offset; } /*-------------------------------------------------------*/ /* l1a_compensate_sync_ind() */ /*-------------------------------------------------------*/ /* */ /* Description: */ /* ------------ */ /* Attempts to modify the time_alignmt and fn_offset */ /* fields of an MPHC_NCELL_SYNC_IND message based on */ /* E-OTD cross-correlation information in order to */ /* post-correct the result. This can be used to form a */ /* quater-bit alignment with slow drifting neighbours */ /* */ /*-------------------------------------------------------*/ void l1a_compensate_sync_ind(T_MPHC_NCELL_SYNC_IND * msg) { // This process can only be applied to SBCONF messages // with good SCH decodes and valid EOTD results. // // a_eotd_crosscor [0] [1] [2] [3] [4] [5] [6] [7] [8] // // <------ Peak Range -----> // // As long as the cross-correlation peak lies in the range // [1] to [7] then we can examine the slope of the correlation // points on either side of the peak in order to perform a // positive or negative QB shift. if((msg->sb_flag) && (msg->eotd_data_valid)) { WORD16 peak_index = msg->d_eotd_max - msg->d_eotd_first; if((peak_index >= 1) && (peak_index <= 7)) { UWORD32 a_power[9]; UWORD32 pre_power, post_power, thresh_power; UWORD32 i; WORD32 shift = 0; // Calculate the normalised power of the cross-correlation samples // in a_eotd_crosscor. This could be improved to only calculate // the terms for [peak_index-1] [peak_index] [peak_index+1] if // the algorithm proves viable in the long term. // Normalised power[i] = real[i]^2 + imag[i]^2 for(i=0; i<9; ++i) { // // Awkward looking code to square values as our compiler / assembler // gets the following construct wrong. Very strange... // // UWORD32 real = ... // real *= real; <-- Assembler allocates registers incorrectly here // UWORD32 real = msg->a_eotd_crosscor[2*i] * msg->a_eotd_crosscor[2*i]; UWORD32 imag = msg->a_eotd_crosscor[(2*i)+1] * msg->a_eotd_crosscor[(2*i)+1]; // Sum of the squares... a_power[i] = real + imag; } // By inspection of practical examples, it appears that (peak power/3) // is a good threshold on which to compare the shape of the slope. thresh_power = a_power[peak_index] / 3; pre_power = a_power[peak_index-1]; post_power = a_power[peak_index+1]; // Decision on whether the gradient of the slope of the crosscor points // on either side of the peak is large enough to cause a (max) +/- 1QB shift // to the time_alignmt field. if( (pre_power < thresh_power) && (post_power > thresh_power) ) { // Right skew on the cross corrrelation - shift time_alignmt // to be one greater shift = 1; } else if ( (pre_power > thresh_power) && (post_power < thresh_power) ) { // Left skew on the cross correlation - shift time_alignmt // to be one less shift = -1; } l1a_add_time_delta( &(msg->time_alignmt), &(msg->fn_offset), shift ); } } } #endif /*-------------------------------------------------------*/ /* l1a_add_time_for_nb() */ /*-------------------------------------------------------*/ /* */ /* Description: */ /* ------------ */ /* This function shift a given cell timing (given as a */ /* couple [time_alignmt, fn_offset]) by adding */ /* "SB_MARGIN - NB_MARGIN" */ /* to that timing. */ /* */ /*-------------------------------------------------------*/ void l1a_add_time_for_nb(UWORD32 *time_alignmt, UWORD32 *fn_offset) { // Add "SB_MARGIN - NB_MARGIN" qbit to "fn_offset" and "time_alignmt". // Pay attention to the modulos. *time_alignmt += (SB_MARGIN - NB_MARGIN); if(*time_alignmt >= TPU_CLOCK_RANGE) { *time_alignmt -= TPU_CLOCK_RANGE; *fn_offset = (*fn_offset + MAX_FN - 1) % MAX_FN; } } /*-------------------------------------------------------*/ /* l1a_add_timeslot() */ /*-------------------------------------------------------*/ /* */ /* Description: */ /* ------------ */ /* This function shift a given cell timing (given as a */ /* couple [time_alignmt, fn_offset]) by adding a number */ /* of TIMESLOT (given as "tn") to that timing. */ /* */ /*-------------------------------------------------------*/ void l1a_add_timeslot(UWORD32 *time_alignmt, UWORD32 *fn_offset, UWORD8 tn) { // Add "tn" timeslot to "fn_offset" and "time_alignmt". // Pay attention to the modulos. *time_alignmt += tn * BP_DURATION; if(*time_alignmt >= TPU_CLOCK_RANGE) { *time_alignmt -= TPU_CLOCK_RANGE; *fn_offset = (*fn_offset + MAX_FN - 1) % MAX_FN; } } /*-------------------------------------------------------*/ /* l1a_sub_time_for_nb() */ /*-------------------------------------------------------*/ /* */ /* Description: */ /* ------------ */ /* This function shift a given cell timing (given as a */ /* couple [time_alignmt, fn_offset]) by substacting */ /* "SB_MARGIN - NB_MARGIN" */ /* to that timing. */ /* */ /*-------------------------------------------------------*/ void l1a_sub_time_for_nb(UWORD32 *time_alignmt, UWORD32 *fn_offset) { WORD32 new_time_alignmt; // Sub "SB_MARGIN - NB_MARGIN" qbit to "fn_offset" and "time_alignmt". // Pay attention to the modulos. new_time_alignmt = *time_alignmt - (SB_MARGIN - NB_MARGIN); if(new_time_alignmt < 0) { new_time_alignmt += TPU_CLOCK_RANGE; *fn_offset = (*fn_offset + 1) % MAX_FN; } *time_alignmt = new_time_alignmt; } /*-------------------------------------------------------*/ /* l1a_sub_timeslot() */ /*-------------------------------------------------------*/ /* */ /* Description: */ /* ------------ */ /* This function shift a given cell timing (given as a */ /* couple [time_alignmt, fn_offset]) by substracting a */ /* number of TIMESLOT (given as "tn") to that timing. */ /* */ /*-------------------------------------------------------*/ void l1a_sub_timeslot(UWORD32 *time_alignmt, UWORD32 *fn_offset, UWORD8 tn) { WORD32 new_time_alignmt; // Sub "tn" timeslot to "fn_offset" and "time_alignmt". // Pay attention to the modulos. new_time_alignmt = *time_alignmt - (tn * BP_DURATION); if(new_time_alignmt < 0) { new_time_alignmt += TPU_CLOCK_RANGE; *fn_offset = (*fn_offset + 1) % MAX_FN; } *time_alignmt = new_time_alignmt; } /*-------------------------------------------------------*/ /* l1a_correct_timing() */ /*-------------------------------------------------------*/ /* */ /* Description: */ /* ------------ */ /* */ /*-------------------------------------------------------*/ #if (L1_12NEIGH == 1) void l1a_correct_timing (UWORD8 neigh_id,UWORD32 time_alignmt,UWORD32 fn_offset) { // Save timing information in case of future handovers. l1a_l1s_com.nsync.list[neigh_id].time_alignmt_mem = time_alignmt; l1a_l1s_com.nsync.list[neigh_id].fn_offset_mem = fn_offset; // Sub the serving cell timeslot number to the Neigh./Serving timing // difference to format it for L1S use. l1a_sub_timeslot(&time_alignmt, &fn_offset, l1a_l1s_com.dl_tn); l1a_sub_time_for_nb(&time_alignmt, &fn_offset); // Save neighbor information in the neighbor confirmation cell structure. l1a_l1s_com.nsync.list[neigh_id].time_alignmt = time_alignmt; l1a_l1s_com.nsync.list[neigh_id].fn_offset = fn_offset; } #endif /*-------------------------------------------------------*/ /* l1a_compute_Eotd_data() */ /*-------------------------------------------------------*/ /* */ /* Description: */ /* ------------ */ /* */ /*-------------------------------------------------------*/ #if ((L1_12NEIGH ==1) && (L1_EOTD == 1)) void l1a_compute_Eotd_data( UWORD8 *first_scell, UWORD8 neigh_id, UWORD32 SignalCode, xSignalHeaderRec *msg) { WORD32 ta_sb_neigh; UWORD32 fn_sb_neigh; WORD16 d_eotd_first; WORD32 toa_correction; UWORD32 timetag; // SB case ..... if (SignalCode == L1C_SB_INFO) { fn_sb_neigh = ((T_L1C_SB_INFO *)(msg->SigP))->fn_sb_neigh; d_eotd_first= ((T_L1C_SB_INFO *)(msg->SigP))->d_eotd_first; toa_correction = ((T_L1C_SB_INFO *)(msg->SigP))->toa_correction; } // SBCONF case ..... else { fn_sb_neigh = ((T_L1C_SBCONF_INFO *)(msg->SigP))->fn_sb_neigh; d_eotd_first= ((T_L1C_SBCONF_INFO *)(msg->SigP))->d_eotd_first; toa_correction = ((T_L1C_SBCONF_INFO *)(msg->SigP))->toa_correction; } // compute the true Serving/Neighbor time difference. // 1) update time_alignmt with (23bit - d_eotd_first) delta // 2) Add the serving cell timeslot number to the Serving/Neighbor time difference. ta_sb_neigh = l1a_l1s_com.nsync.list[neigh_id].time_alignmt; ta_sb_neigh += (d_eotd_first - (23))*4 + (l1a_l1s_com.dl_tn * 625); // for Serving cell, timetag reference is 0 if (*first_scell == TRUE) { l1a_l1s_com.nsync.fn_sb_serv = fn_sb_neigh; l1a_l1s_com.nsync.ta_sb_serv = ta_sb_neigh; timetag = 0; } else { UWORD32 delta_fn; WORD32 delta_qbit; delta_fn = (fn_sb_neigh - l1a_l1s_com.nsync.fn_sb_serv + MAX_FN)%MAX_FN; delta_qbit = ta_sb_neigh - l1a_l1s_com.nsync.ta_sb_serv; // Set timetag timetag = (delta_fn*5000) + (WORD32)(delta_qbit) + toa_correction; #if (CODE_VERSION == SIMULATION) #if (TRACE_TYPE==5) ((T_MPHC_NCELL_SYNC_IND *)(msg->SigP))->delta_fn = delta_fn; ((T_MPHC_NCELL_SYNC_IND *)(msg->SigP))->delta_qbit = delta_qbit; #endif #endif } // Set timetag ((T_MPHC_NCELL_SYNC_IND *)(msg->SigP))->timetag = timetag; } #endif /*-------------------------------------------------------*/ /* l1a_get_free_dedic_set() */ /*-------------------------------------------------------*/ /* Parameters : */ /* Return : */ /* Functionality : */ /*-------------------------------------------------------*/ T_DEDIC_SET *l1a_get_free_dedic_set() { T_DEDIC_SET *fset; UWORD8 i; // Get free set pointer. if(l1a_l1s_com.dedic_set.aset == &(l1a_l1s_com.dedic_set.set[0])) fset = &(l1a_l1s_com.dedic_set.set[1]); else fset = &(l1a_l1s_com.dedic_set.set[0]); // Clear free set. fset->achan_ptr = NULL; fset->chan1.desc.channel_type = INVALID_CHANNEL; fset->chan1.desc_bef_sti.channel_type = INVALID_CHANNEL; fset->chan2.desc.channel_type = INVALID_CHANNEL; fset->chan2.desc_bef_sti.channel_type = INVALID_CHANNEL; fset->ma.alist_ptr = NULL; fset->ma.freq_list.rf_chan_cnt = 0; fset->ma.freq_list_bef_sti.rf_chan_cnt = 0; // Starting time. fset->serv_sti_fn = -1; fset->neig_sti_fn = -1; // Frequency redefinition flag. fset->freq_redef_flag = FALSE; // Timing Advance fset->timing_advance = 0; fset->new_timing_advance = 0; // TXPWR fset->new_target_txpwr = NO_TXPWR; // Cell Information l1a_reset_cell_info(&(fset->cell_desc)); // Cipering. fset->a5mode = 0; // Ciphering OFF. // Clear O&M test variables. fset->dai_mode = 0; // No DAI test. fset->chan1.tch_loop = 0; // No TCH loop on chan1. fset->chan2.tch_loop = 0; // No TCH loop on chan2. // For handover... fset->ho_acc = 0; fset->ho_acc_to_send = 0; fset->t3124 = 0; #if ((REL99 == 1) && (FF_BHO == 1)) // For blind handover... fset->report_time_diff = FALSE; fset->nci = FALSE; fset->report_time_diff = FALSE; fset->real_time_difference = 0; fset->HO_SignalCode = 0; #endif // Reset DPAGC fifo for(i=0;i<DPAGC_FIFO_LEN;i++) { fset->G_all[i] = 200; fset->G_DTX[i] = 200; } // Reset DTX_ALLOWED field. fset->dtx_allowed = FALSE; #if IDS // clear ids_mode: default value = speech mode fset->ids_mode = 0; #endif #if (AMR == 1) // Clear the AMR ver 1.0 network settings fset->amr_configuration.noise_suppression_bit = FALSE; fset->amr_configuration.initial_codec_mode_indicator = FALSE; fset->amr_configuration.initial_codec_mode = 0; fset->amr_configuration.active_codec_set = 0; fset->amr_configuration.threshold[0] = 0; fset->amr_configuration.threshold[1] = 0; fset->amr_configuration.threshold[2] = 0; fset->amr_configuration.hysteresis[0] = 0; fset->amr_configuration.hysteresis[1] = 0; fset->amr_configuration.hysteresis[2] = 0; fset->cmip = C_AMR_CMIP_DEFAULT; #endif return(fset); } /*-------------------------------------------------------*/ /* l1a_fill_bef_sti_param() */ /*-------------------------------------------------------*/ /* Parameters : */ /* Return : */ /* Functionality : */ /*-------------------------------------------------------*/ void l1a_fill_bef_sti_param(T_DEDIC_SET *set_ptr, BOOL start_time_present) { if(start_time_present == TRUE) // There is a STARTING TIME field... { if((set_ptr->ma.freq_list_bef_sti.rf_chan_cnt != 0) || (set_ptr->chan1.desc_bef_sti.channel_type != INVALID_CHANNEL) || (set_ptr->chan2.desc_bef_sti.channel_type != INVALID_CHANNEL)) // There is at least one "bef_sti" parameter given for this channel. // Other empty parameters must be filled with the according "AFTER STARTING TIME" parameters. { // Fill "chan1.desc_bef_sti" if(set_ptr->chan1.desc_bef_sti.channel_type == INVALID_CHANNEL) set_ptr->chan1.desc_bef_sti = set_ptr->chan1.desc; // Fill "chan2.desc_bef_sti" if(set_ptr->chan2.desc_bef_sti.channel_type == INVALID_CHANNEL) set_ptr->chan2.desc_bef_sti = set_ptr->chan2.desc; // Fill "freq_list_bef_sti" if(set_ptr->ma.freq_list_bef_sti.rf_chan_cnt == 0) set_ptr->ma.freq_list_bef_sti = set_ptr->ma.freq_list; } } } /*-------------------------------------------------------*/ /* l1a_decode_starting_time() */ /*-------------------------------------------------------*/ /* Parameters : */ /* Return : */ /* Functionality : */ /*-------------------------------------------------------*/ WORD32 l1a_decode_starting_time(T_STARTING_TIME coded_starting_time) { WORD32 starting_time; if(coded_starting_time.start_time_present == TRUE ) // A starting time is present. // --------------------------- { WORD32 tp1 = coded_starting_time.start_time.n32; WORD32 t2 = coded_starting_time.start_time.n26; WORD32 t3 = coded_starting_time.start_time.n51; // Compute STI. starting_time = 51*((26 + t3 - t2) % 26) + t3 + (51*26*tp1) ; } else { starting_time = -1; } return(starting_time); } /*-------------------------------------------------------*/ /* l1a_reset_cell_info() */ /*-------------------------------------------------------*/ /* Parameters : */ /* Return : */ /* Functionality : */ /*-------------------------------------------------------*/ void l1a_reset_cell_info(T_CELL_INFO *cell_info) { cell_info->bsic = 0; cell_info->fn_offset = 0; cell_info->time_alignmt = 0; cell_info->meas.acc = 0; cell_info->meas.nbr_meas = 0; cell_info->attempt_count = 0; cell_info->si_bit_map = 0; cell_info->traffic_meas.input_level = l1_config.params.il_min; cell_info->traffic_meas_beacon.input_level = l1_config.params.il_min; cell_info->traffic_meas.lna_off = FALSE; cell_info->traffic_meas_beacon.lna_off = FALSE; cell_info->buff_beacon[0] = cell_info->buff_beacon[1] = cell_info->buff_beacon[2] = cell_info->buff_beacon[3] = l1_config.params.il_min; #if L1_GPRS cell_info->transfer_meas.input_level = l1_config.params.il_min; cell_info->transfer_meas.lna_off = FALSE; cell_info->pb = 0; #endif } /*-------------------------------------------------------*/ /* l1a_send_confirmation() */ /*-------------------------------------------------------*/ /* Parameters : */ /* Return : */ /* Functionality : */ /*-------------------------------------------------------*/ void l1a_send_confirmation(UWORD32 SignalCode, UWORD8 queue_type) { xSignalHeaderRec *msg; msg = os_alloc_sig(0); DEBUGMSG(status,NU_ALLOC_ERR) msg->SignalCode = (int)SignalCode; #if (TRACE_TYPE==1) || (TRACE_TYPE==4) l1_trace_message(msg); #endif #if (OP_L1_STANDALONE == 1) os_send_sig(msg, queue_type); #else os_send_sig(msg, ((T_ENUM_OS_QUEUE)queue_type)); //omaps00090550 #endif DEBUGMSG(status,NU_SEND_QUEUE_ERR) } /*-------------------------------------------------------*/ /* l1a_send_result() */ /*-------------------------------------------------------*/ /* Parameters : */ /* Return : */ /* Functionality : */ /*-------------------------------------------------------*/ void l1a_send_result(UWORD32 SignalCode, xSignalHeaderRec *msg, UWORD8 queue) { // Set flag to avoid the FREE(msg) in L1ASYNC. l1a.l1_msg_forwarded = TRUE; msg->SignalCode = (int)SignalCode; // May not be necessary -> to check #if (GSM_IDLE_RAM > 1) if (!READ_TRAFFIC_CONT_STATE) { CSMI_TrafficControllerOn(); } #endif #if (TRACE_TYPE==1) || (TRACE_TYPE==4) l1_trace_message(msg); #endif #if (OP_L1_STANDALONE == 1) os_send_sig(msg, queue); #else os_send_sig(msg, ((T_ENUM_OS_QUEUE)queue)); //omaps00090550 #endif DEBUGMSG(status,NU_SEND_QUEUE_ERR) } /*-------------------------------------------------------*/ /* l1a_encode_rxqual() */ /*-------------------------------------------------------*/ /* Parameters : */ /* Return : */ /* Functionality : */ /*-------------------------------------------------------*/ UWORD8 l1a_encode_rxqual (UWORD32 inlevel) { enum qual_thr { thr_0_2 = 4, thr_0_4 = 8, thr_0_8 = 16, thr_1_6 = 32, thr_3_2 = 64, thr_6_4 = 128, thr_12_8 = 256 }; UWORD8 rxqual; if (inlevel < thr_0_2) rxqual = 0; else if (inlevel < thr_0_4) rxqual = 1; else if (inlevel < thr_0_8) rxqual = 2; else if (inlevel < thr_1_6) rxqual = 3; else if (inlevel < thr_3_2) rxqual = 4; else if (inlevel < thr_6_4) rxqual = 5; else if (inlevel < thr_12_8) rxqual = 6; else rxqual = 7; return((UWORD8) rxqual); } /*-------------------------------------------------------*/ /* l1a_report_failling_ncell_sync() */ /*-------------------------------------------------------*/ /* Parameters : */ /* Return : */ /* Functionality : */ /*-------------------------------------------------------*/ void l1a_report_failling_ncell_sync(UWORD32 SignalCode, UWORD8 neigh_id) { xSignalHeaderRec *msg; // Send MPHC_NCELL_SYNC_IND message to L3 with a FAILLURE indication. msg = os_alloc_sig(sizeof(T_MPHC_NCELL_SYNC_IND)); DEBUGMSG(status,NU_ALLOC_ERR) msg->SignalCode = SignalCode; ((T_MPHC_NCELL_SYNC_IND*)(msg->SigP))->sb_flag = FALSE; ((T_MPHC_NCELL_SYNC_IND*)(msg->SigP))->radio_freq = l1a_l1s_com.nsync.list[neigh_id].radio_freq; ((T_MPHC_NCELL_SYNC_IND*)(msg->SigP))->bsic = 0; ((T_MPHC_NCELL_SYNC_IND*)(msg->SigP))->fn_offset = 0; ((T_MPHC_NCELL_SYNC_IND*)(msg->SigP))->time_alignmt = 0; // For trace/debug only ((T_MPHC_NCELL_SYNC_IND*)(msg->SigP))->neigh_id = neigh_id; #if (TRACE_TYPE==1) || (TRACE_TYPE==4) l1_trace_message(msg); #endif os_send_sig(msg, RRM1_QUEUE); DEBUGMSG(status,NU_SEND_QUEUE_ERR) } /*-------------------------------------------------------*/ /* l1a_clip_txpwr() */ /*-------------------------------------------------------*/ /* Parameters : */ /* Return : */ /* Functionality : */ /*-------------------------------------------------------*/ #if (L1_FF_MULTIBAND == 0) UWORD8 l1a_clip_txpwr (UWORD8 supplied_txpwr, UWORD16 radio_freq) { #define txpwr_to_compare(pwr) ((pwr<=l1_config.std.txpwr_turning_point)? pwr+32:pwr) switch(l1_config.std.id) { case GSM: case GSM_E: { // Clip LOW according to powerclass_band1. if ( supplied_txpwr < MIN_TXPWR_GSM[l1a_l1s_com.powerclass_band1]) return(MIN_TXPWR_GSM[l1a_l1s_com.powerclass_band1]); // Clip HIGH according to GSM spec. 05.05. if ( supplied_txpwr > l1_config.std.max_txpwr_band1) return(l1_config.std.max_txpwr_band1); } break; case PCS1900: { // Clip LOW according to powerclass_band1. if ( txpwr_to_compare(supplied_txpwr) < txpwr_to_compare(MIN_TXPWR_PCS[l1a_l1s_com.powerclass_band1]) ) return(MIN_TXPWR_PCS[l1a_l1s_com.powerclass_band1]); // Clip HIGH according to GSM spec. 05.05. if ( txpwr_to_compare(supplied_txpwr) > txpwr_to_compare(l1_config.std.max_txpwr_band1) ) return(l1_config.std.max_txpwr_band1); } break; case DCS1800: { // Clip LOW according to powerclass_band1. if ( txpwr_to_compare(supplied_txpwr) < txpwr_to_compare(MIN_TXPWR_DCS[l1a_l1s_com.powerclass_band1]) ) return(MIN_TXPWR_DCS[l1a_l1s_com.powerclass_band1]); // Clip HIGH according to GSM spec. 05.05. if ( txpwr_to_compare(supplied_txpwr) > txpwr_to_compare(l1_config.std.max_txpwr_band1) ) return(l1_config.std.max_txpwr_band1); } break; case GSM850: { // Clip LOW according to powerclass_band1. if ( txpwr_to_compare(supplied_txpwr) < txpwr_to_compare(MIN_TXPWR_GSM850[l1a_l1s_com.powerclass_band1]) ) return(MIN_TXPWR_GSM850[l1a_l1s_com.powerclass_band1]); // Clip HIGH according to GSM spec. 05.05. if ( txpwr_to_compare(supplied_txpwr) > txpwr_to_compare(l1_config.std.max_txpwr_band1) ) return(l1_config.std.max_txpwr_band1); } break; case DUAL: case DUALEXT: { // Test which Band is used: GSM or DCS 1800 if (radio_freq >= l1_config.std.first_radio_freq_band2) { // Clip LOW according to powerclass_band1. if ( txpwr_to_compare(supplied_txpwr) < txpwr_to_compare(MIN_TXPWR_DCS[l1a_l1s_com.powerclass_band2]) ) return(MIN_TXPWR_DCS[l1a_l1s_com.powerclass_band2]); // Clip HIGH according to GSM spec. 05.05. if ( txpwr_to_compare(supplied_txpwr) > txpwr_to_compare(l1_config.std.max_txpwr_band2) ) return(l1_config.std.max_txpwr_band2); } else { // Clip LOW according to powerclass_band1. if ( supplied_txpwr < MIN_TXPWR_GSM[l1a_l1s_com.powerclass_band1]) return(MIN_TXPWR_GSM[l1a_l1s_com.powerclass_band1]); // Clip HIGH according to GSM spec. 05.05. if ( supplied_txpwr > l1_config.std.max_txpwr_band1) return(l1_config.std.max_txpwr_band1); } } break; case DUAL_US: { // Test which Band is used: GSM 850 or PCS1900 if (radio_freq >= l1_config.std.first_radio_freq_band2) { // Clip LOW according to powerclass_band1. if ( txpwr_to_compare(supplied_txpwr) < txpwr_to_compare(MIN_TXPWR_PCS[l1a_l1s_com.powerclass_band2]) ) return(MIN_TXPWR_PCS[l1a_l1s_com.powerclass_band2]); // Clip HIGH according to GSM spec. 05.05. if ( txpwr_to_compare(supplied_txpwr) > txpwr_to_compare(l1_config.std.max_txpwr_band2) ) return(l1_config.std.max_txpwr_band2); } else { // Clip LOW according to powerclass_band1. if ( supplied_txpwr < MIN_TXPWR_GSM850[l1a_l1s_com.powerclass_band1]) return(MIN_TXPWR_GSM850[l1a_l1s_com.powerclass_band1]); // Clip HIGH according to GSM spec. 05.05. if ( supplied_txpwr > l1_config.std.max_txpwr_band1) return(l1_config.std.max_txpwr_band1); } } break; default: // should never occur { return(supplied_txpwr); } // omaps00090550 break; } return(supplied_txpwr); } #else /*L1_FF_MULTIBAND = 1 below */ UWORD8 l1a_clip_txpwr (UWORD8 supplied_txpwr, UWORD16 radio_freq) { UWORD8 physical_band_id = 0; physical_band_id = l1_multiband_radio_freq_convert_into_physical_band_id(radio_freq); #define txpwr_to_compare(pwr) ((pwr<= multiband_rf[physical_band_id].tx_turning_point)? pwr+32:pwr) switch(multiband_rf[physical_band_id].gsm_band_identifier) { case RF_GSM900: { // Clip LOW according to powerclass_band1. if ( supplied_txpwr < MIN_TXPWR_GSM[l1a_l1s_com.powerclass[physical_band_id]]) return(MIN_TXPWR_GSM[l1a_l1s_com.powerclass[physical_band_id]]); // Clip HIGH according to GSM spec. 05.05. if ( supplied_txpwr > multiband_rf[physical_band_id].max_txpwr) return(multiband_rf[physical_band_id].max_txpwr); break; }/*case GSM900*/ case RF_PCS1900: { // Clip LOW according to powerclass_band1. if ( txpwr_to_compare(supplied_txpwr) < txpwr_to_compare(MIN_TXPWR_PCS[l1a_l1s_com.powerclass[physical_band_id]]) ) return(MIN_TXPWR_PCS[l1a_l1s_com.powerclass[physical_band_id]]); // Clip HIGH according to GSM spec. 05.05. if ( txpwr_to_compare(supplied_txpwr) > txpwr_to_compare(multiband_rf[physical_band_id].max_txpwr) ) return(multiband_rf[physical_band_id].max_txpwr); break; }/*case PCS1900*/ case RF_DCS1800: { // Clip LOW according to powerclass_band1. if ( txpwr_to_compare(supplied_txpwr) < txpwr_to_compare(MIN_TXPWR_DCS[l1a_l1s_com.powerclass[physical_band_id]]) ) return(MIN_TXPWR_DCS[l1a_l1s_com.powerclass[physical_band_id]]); // Clip HIGH according to GSM spec. 05.05. if ( txpwr_to_compare(supplied_txpwr) > txpwr_to_compare(multiband_rf[physical_band_id].max_txpwr) ) return(multiband_rf[physical_band_id].max_txpwr); break; }/*case DCS1800*/ case RF_GSM850: { // Clip LOW according to powerclass_band1. if ( txpwr_to_compare(supplied_txpwr) < txpwr_to_compare(MIN_TXPWR_GSM850[l1a_l1s_com.powerclass[physical_band_id]]) ) return(MIN_TXPWR_GSM850[l1a_l1s_com.powerclass[physical_band_id]]); // Clip HIGH according to GSM spec. 05.05. if ( txpwr_to_compare(supplied_txpwr) > txpwr_to_compare(multiband_rf[physical_band_id].max_txpwr) ) return(multiband_rf[physical_band_id].max_txpwr); break; }/*case GSM850*/ default: // should never occur { l1_multiband_error_handler(); return(supplied_txpwr); break; } /*default*/ }/*switch(multiband_rfphysical_band_id].gsm_band_identifier)*/ return(supplied_txpwr); } #endif /*L1_FF_MULTIBAND */ //MADC #if (L1_MADC_ON == 1) #if (OP_L1_STANDALONE == 1) #if (ANLG_FAM == 11) void l1a_madc_callback(void) { char str[40]; xSignalHeaderRec *adc_msg; UWORD16 *adc_result; UWORD16 *madc_results; volatile UWORD16 *drp_temp_results; #if (RF_FAM == 61) drp_temp_results =(volatile UWORD16 *) (&drp_srm_api->inout.temperature.output); //omaps00090550 #endif #if 0 sprintf(str, "Temp Measure %x ", drp_temp_results); //L1_trace_string ("Temp Meas\n"); L1_trace_string(str); #endif #if 0 int i; adc_msg = os_alloc_sig(sizeof(BspTwl3029_MadcResults) + sizeof(UWORD16)); adc_result = &((BspTwl3029_MadcResults*)(adc_msg->SigP))->adc1; madc_results =& l1_madc_results.adc1; //TEMP_MEAS: DRP #if (RF_FAM == 61) drp_temp_results =& (drp_srm_api->inout.temperature.output); #endif //copy the measured values into the the message structure. memcpy(adc_result,madc_results,11*sizeof(UWORD16));//11 madc adc_result[11] = *drp_temp_results; // 1 temp meas /* for (i=0;i<11;i++) adc_result[i] = madc_results[i]; */ //Send the message adc_msg->SignalCode = CST_ADC_RESULT; os_send_sig(adc_msg, RRM1_QUEUE); #endif } #endif // ANLG_FAM == 11 #endif //OP_L1_STANDALONE #endif // L1_MADC_ON //==============================================================================================