FreeCalypso > hg > fc-magnetite
comparison src/g23m-gprs/grr/grr_csf.c @ 183:219afcfc6250
src/g23m-gprs: initial import from TCS3.2/LoCosto
author | Mychaela Falconia <falcon@freecalypso.org> |
---|---|
date | Thu, 13 Oct 2016 04:24:13 +0000 |
parents | |
children |
comparison
equal
deleted
inserted
replaced
182:f02d0a0e1849 | 183:219afcfc6250 |
---|---|
1 /* | |
2 +----------------------------------------------------------------------------- | |
3 | Project : GPRS (8441) | |
4 | Modul : GRR | |
5 +----------------------------------------------------------------------------- | |
6 | Copyright 2002 Texas Instruments Berlin, AG | |
7 | All rights reserved. | |
8 | | |
9 | This file is confidential and a trade secret of Texas | |
10 | Instruments Berlin, AG | |
11 | The receipt of or possession of this file does not convey | |
12 | any rights to reproduce or disclose its contents or to | |
13 | manufacture, use, or sell anything it may describe, in | |
14 | whole, or in part, without the specific written consent of | |
15 | Texas Instruments Berlin, AG. | |
16 +----------------------------------------------------------------------------- | |
17 | Purpose : This module implements local functions for service CS of | |
18 | entity GRR. | |
19 +----------------------------------------------------------------------------- | |
20 */ | |
21 | |
22 #ifndef GRR_CSF_C | |
23 #define GRR_CSF_C | |
24 #endif | |
25 | |
26 #define ENTITY_GRR | |
27 | |
28 /*==== INCLUDES =============================================================*/ | |
29 | |
30 #include <stdio.h> | |
31 #include <string.h> | |
32 #include "typedefs.h" /* to get Condat data types */ | |
33 #include "vsi.h" /* to get a lot of macros */ | |
34 #include "macdef.h" | |
35 #include "gprs.h" | |
36 #include "gsm.h" /* to get a lot of macros */ | |
37 #include "ccdapi.h" /* to get CCD API */ | |
38 #include "cnf_grr.h" /* to get cnf-definitions */ | |
39 #include "mon_grr.h" /* to get mon-definitions */ | |
40 #include "prim.h" /* to get the definitions of used SAP and directions */ | |
41 #include "message.h" | |
42 #include "grr.h" /* to get the global entity definitions */ | |
43 #include "grr_f.h" | |
44 #include "grr_ctrls.h" | |
45 #include "grr_meass.h" | |
46 #include "grr_csf.h" | |
47 #include "grr_em.h" /*for Engineering mode*/ | |
48 | |
49 | |
50 /*==== CONST ================================================================*/ | |
51 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
52 /* | |
53 * Bitmasks | |
54 */ | |
55 #define BIT_0 0x01 | |
56 #define BIT_1 0x02 | |
57 #define BIT_2 0x04 | |
58 #define BIT_3 0x08 | |
59 #define BIT_4 0x10 | |
60 #define BIT_5 0x20 | |
61 #define BIT_6 0x40 | |
62 #define BIT_7 0x80 | |
63 #endif | |
64 | |
65 T_NC_DATA* nc_data = NULL; /* pointer to neighbour cell data */ | |
66 | |
67 const SHORT p_res_off[32] = { -52, /* 0 -> -52 dB */ | |
68 -48, /* 1 -> -48 dB */ | |
69 -44, /* 2 -> -44 dB */ | |
70 -40, /* 3 -> -40 dB */ | |
71 -36, /* 4 -> -36 dB */ | |
72 -32, /* 5 -> -32 dB */ | |
73 -28, /* 6 -> -28 dB */ | |
74 -24, /* 7 -> -24 dB */ | |
75 -20, /* 8 -> -20 dB */ | |
76 -16, /* 9 -> -16 dB */ | |
77 -12, /* 10 -> -12 dB */ | |
78 -10, /* 11 -> -10 dB */ | |
79 - 8, /* 12 -> - 8 dB */ | |
80 - 6, /* 13 -> - 6 dB */ | |
81 - 4, /* 14 -> - 4 dB */ | |
82 - 2, /* 15 -> - 2 dB */ | |
83 0, /* 16 -> 0 dB */ | |
84 2, /* 17 -> 2 dB */ | |
85 4, /* 18 -> 4 dB */ | |
86 6, /* 19 -> 6 dB */ | |
87 8, /* 20 -> 8 dB */ | |
88 10, /* 21 -> 10 dB */ | |
89 12, /* 22 -> 12 dB */ | |
90 16, /* 23 -> 16 dB */ | |
91 20, /* 24 -> 20 dB */ | |
92 24, /* 25 -> 24 dB */ | |
93 28, /* 26 -> 28 dB */ | |
94 32, /* 27 -> 32 dB */ | |
95 36, /* 28 -> 36 dB */ | |
96 40, /* 29 -> 40 dB */ | |
97 44, /* 30 -> 44 dB */ | |
98 48 /* 31 -> 48 dB */ | |
99 }; | |
100 | |
101 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
102 /* | |
103 PURPOSE : checks whether the network colour code (ncc) is member | |
104 of the ncc permitted field. | |
105 */ | |
106 LOCAL const UBYTE ncc_bit_mask[8] = | |
107 { | |
108 BIT_0, BIT_1, BIT_2, BIT_3, | |
109 BIT_4, BIT_5, BIT_6, BIT_7 | |
110 }; | |
111 #endif | |
112 | |
113 #define NC_MODE_LEN 1 | |
114 #define NC_RXLEV_SCELL_LEN 6 | |
115 #define NC_IF_SCELL_LEN 6 | |
116 #define NC_NUM_OF_MEAS_LEN 3 | |
117 #define NC_FREQ_N_LEN 6 | |
118 #define NC_BSIC_N_LEN 6 | |
119 #define NC_RXLEV_N_LEN 6 | |
120 | |
121 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
122 #define BA_USED_LEN 1 | |
123 #define BA_USED_3G_LEN 1 | |
124 #define PSI3_CM_LEN 2 | |
125 #define PMO_USED_LEN 1 | |
126 #endif | |
127 | |
128 #define GET_NC_RPT_PRD(x) ((0x01<<(x))*480) /* multiple of 480 ms */ | |
129 | |
130 #define CS_PERIOD_1_SEC 217 /* 1 second defined by */ | |
131 /* multiplies of TDMA frames */ | |
132 #define MAX_SYNC_FAILED_CNT 3 | |
133 | |
134 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
135 #define INRANGE(min, x, max) ((unsigned)(x-min) <= (max-min)) | |
136 #endif | |
137 | |
138 #ifdef _TARGET_ | |
139 | |
140 #define MIN_RXLEV_FOR_SIX_STRGST 4 /* minimum RXLEV value of neighbour cells */ | |
141 /* which shall be considered for cell */ | |
142 /* re-selection decision */ | |
143 #endif /* #ifdef _TARGET_ */ | |
144 | |
145 #define RXLEV_ACRCY 1000 | |
146 #define RXLEV_MAX_NBR ((T_RXLEV_DATA_NBR)(~((T_RXLEV_DATA_NBR)0))) | |
147 #define RXLEV_AVG_INVALID 0xFF | |
148 | |
149 #ifdef TI_PS_FF_QUAD_BAND_SUPPORT | |
150 #define CHECK_DUAL_BANDS (std EQ STD_DUAL OR std EQ STD_DUAL_EGSM OR \ | |
151 std EQ STD_DUAL_US OR std EQ STD_850_1800 OR \ | |
152 std EQ STD_900_1900 OR std EQ STD_850_900_1800 OR \ | |
153 std EQ STD_850_900_1900) | |
154 #endif | |
155 | |
156 /*==== GLOBAL VARS ===========================================================*/ | |
157 | |
158 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
159 EXTERN BOOL use_ba_gprs; | |
160 #endif | |
161 | |
162 /*==== LOCAL VARS ===========================================================*/ | |
163 | |
164 /*==== PRIVATE FUNCTIONS ====================================================*/ | |
165 | |
166 LOCAL void cs_trace_nc_mval_lst ( void ); | |
167 LOCAL void cs_init_nc_mval ( T_NC_MVAL *mval ); | |
168 LOCAL void cs_reorg_nc_mval_lst ( void ); | |
169 | |
170 | |
171 LOCAL BOOL cs_build_meas_rpt ( T_U_MEAS_REPORT *u_meas_report ); | |
172 | |
173 LOCAL BOOL cs_process_serving_cell_data | |
174 ( UBYTE *rxlev_scell, UBYTE *v_i_scell, | |
175 UBYTE *i_scell, UBYTE *used_bits, | |
176 BOOL *rsc_avail, BOOL *isc_avail ); | |
177 | |
178 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
179 LOCAL void cs_build_enh_sorted_strng_arfcn_list | |
180 (T_ENH_STRNG_ARFCN_LIST *f_bin ); | |
181 /* | |
182 LOCAL UBYTE cs_sort_arfcns_into_bins | |
183 ( T_ENH_STRNG_ARFCN_LIST *p_s_bin, | |
184 T_ENH_STRNG_ARFCN_LIST *p_m_bin, | |
185 T_ENH_STRNG_ARFCN_LIST *p_r_bin);*/ | |
186 LOCAL UBYTE cs_sort_arfcns_into_bins | |
187 ( T_ENH_STRNG_ARFCN_LIST *p_s_bin, | |
188 T_ENH_STRNG_ARFCN_LIST *p_r_bin); | |
189 LOCAL void cs_sort_store_in_desc_order_rxlev | |
190 ( T_ENH_STRNG_ARFCN_LIST *p_bin, | |
191 T_ENH_STRNG_ARFCN_LIST *p_f_bin); | |
192 LOCAL BOOL cs_build_enh_meas_rpt( T_U_ENHNC_MEAS_REPORT *u_enh_meas_report ); | |
193 | |
194 LOCAL BOOL cs_fill_nc_enh_meas_results | |
195 (T_nc_meas_rep_enh *nc_meas_rep_enh); | |
196 LOCAL void cs_form_enh_cell_list (void ); | |
197 LOCAL void cs_form_ba_bcch_enh_cell_list | |
198 (void ); | |
199 LOCAL void cs_nc_sort_and_update_emr_info | |
200 (void ); | |
201 LOCAL void cs_nc_sort_cells_into_bins | |
202 (T_ENH_BIN *p_sbin,T_ENH_BIN *p_mbin, | |
203 T_ENH_BIN *p_rbin ); | |
204 LOCAL void cs_nc_sort_and_store_meas_results | |
205 (T_ENH_BIN *p_bin, UBYTE nbr_rpt ); | |
206 LOCAL void cs_nc_update_rest_bin | |
207 (T_ENH_BIN *p_rbin, | |
208 T_ENH_BIN *p_bin, UBYTE nbr_rpt ); | |
209 LOCAL UBYTE cs_get_band_index_for_emr | |
210 (USHORT arfcn); | |
211 LOCAL UBYTE cs_nc_scale_rxlev (void); | |
212 #endif | |
213 | |
214 LOCAL void cs_build_nc_freq_list | |
215 ( T_SC_DATABASE *db ); | |
216 LOCAL void cs_find_strongest_with_status | |
217 ( UBYTE *count, | |
218 UBYTE *index, | |
219 UBYTE select_status, | |
220 UBYTE maximum, | |
221 UBYTE limitation ); | |
222 LOCAL void cs_consider_multiband | |
223 ( UBYTE *count, | |
224 UBYTE *index, | |
225 UBYTE select_status, | |
226 UBYTE maximum ); | |
227 LOCAL BOOL cs_update_strongest ( UBYTE cnt_strgst, | |
228 UBYTE cnt_candid, | |
229 UBYTE *index, | |
230 ULONG fn_offset ); | |
231 LOCAL void cs_start_t3158 ( T_TIME time ); | |
232 LOCAL void cs_set_cnt_nc_six ( UBYTE strgst, | |
233 UBYTE candid ); | |
234 LOCAL T_TIME cs_get_nc_rpt_prd_idle | |
235 ( void ); | |
236 | |
237 LOCAL void cs_copy_rxlev_from_avg( UBYTE rxlev_avg, | |
238 T_CELL *cell ); | |
239 LOCAL void cs_reuse_old_cell_rxlev (void); | |
240 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
241 LOCAL void cs_build_ba_bcch_nc_freq_list (); | |
242 #endif | |
243 | |
244 /* | |
245 +------------------------------------------------------------------------------ | |
246 | Function : cs_set_cnt_nc_six | |
247 +------------------------------------------------------------------------------ | |
248 | Description : | |
249 | | |
250 | Parameters : | |
251 | | |
252 +------------------------------------------------------------------------------ | |
253 */ | |
254 LOCAL void cs_set_cnt_nc_six ( UBYTE strgst, UBYTE candid ) | |
255 { | |
256 TRACE_FUNCTION( "cs_set_cnt_nc_six" ); | |
257 | |
258 #if defined FF_EOTD | |
259 grr_data->db.cnt_nc_six.strgst = MINIMUM( CS_MAX_STRONG_CARRIER_CR, strgst ); | |
260 #else /* #if defined FF_EOTD */ | |
261 grr_data->db.cnt_nc_six.strgst = strgst; | |
262 #endif /* #if defined FF_EOTD */ | |
263 | |
264 grr_data->db.cnt_nc_six.candid = candid; | |
265 | |
266 } /* cs_set_cnt_nc_six() */ | |
267 | |
268 /* | |
269 +------------------------------------------------------------------------------ | |
270 | Function : cs_build_meas_rpt | |
271 +------------------------------------------------------------------------------ | |
272 | Description : This function ... | |
273 | | |
274 | Parameters : u_meas_report - Pointer to measurement report | |
275 | | |
276 +------------------------------------------------------------------------------ | |
277 */ | |
278 LOCAL BOOL cs_build_meas_rpt ( T_U_MEAS_REPORT *u_meas_report ) | |
279 { | |
280 T_NC_ORDER nc_ord = cs_get_network_ctrl_order( TRUE ); | |
281 BOOL pbcch_present = grr_is_pbcch_present( ); | |
282 UBYTE used_bits; | |
283 /* bits currently used for the measurement report */ | |
284 UBYTE next_meas_bits = 0; | |
285 /* bits used for the next element of the */ | |
286 /* measurement result list */ | |
287 BOOL is_first_instance; | |
288 | |
289 T_CS_MEAS_DATA *nmeas = &grr_data->cs_meas; | |
290 T_nc_meas_rep *ncmeas_rep = &u_meas_report->nc_meas_rep; | |
291 T_nc_meas_s1 *p_mrpt; | |
292 T_ncell_info *ncell; | |
293 T_NC_MVAL *mval; | |
294 UBYTE return_value; | |
295 BOOL rsc_avail = FALSE; | |
296 BOOL isc_avail = FALSE; | |
297 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
298 UBYTE psi3_cm = grr_get_psi3_cm(); | |
299 #endif | |
300 TRACE_FUNCTION( "cs_build_meas_rpt" ); | |
301 | |
302 /* process message type */ | |
303 used_bits = PMR_MSG_TYPE_LEN; | |
304 u_meas_report->msg_type = U_MEAS_REPORT_c; | |
305 | |
306 /* process TLLI */ | |
307 used_bits += PMR_TLLI_LEN; | |
308 grr_set_buf_tlli( &u_meas_report->tlli_value, grr_get_tlli( ) ); | |
309 | |
310 /* process PSI5 change mark */ | |
311 used_bits += PMR_FLAG_LEN; | |
312 | |
313 if( pbcch_present EQ FALSE OR | |
314 grr_data->db.nc_ref_lst.param EQ &psc_db->nc_ms.ncmeas.param ) | |
315 { | |
316 u_meas_report->v_psi5_cm = FALSE; | |
317 } | |
318 else if( grr_data->db.nc_ref_lst.param EQ &psc_db->nc_cw.param ) | |
319 { | |
320 used_bits += PMR_PSI5_CHNGE_MRK_LEN; | |
321 | |
322 u_meas_report->v_psi5_cm = TRUE; | |
323 u_meas_report->psi5_cm = psc_db->psi5_params.psi5_change_mark; | |
324 } | |
325 else | |
326 { | |
327 TRACE_ERROR( "cs_build_meas_rpt no valid data set" ); | |
328 return( FALSE ); | |
329 } | |
330 | |
331 /* process flags */ | |
332 used_bits += PMR_FLAG_LEN; | |
333 u_meas_report->flag = 0; | |
334 u_meas_report->v_nc_meas_rep = TRUE; | |
335 u_meas_report->v_xmeas_rep = FALSE; | |
336 | |
337 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
338 /*if(psc_db->network_rel NEQ BSS_NW_REL_97)*/ | |
339 { | |
340 used_bits += PMR_FLAG_LEN; | |
341 u_meas_report->v_release_99_str_pmr = TRUE; | |
342 | |
343 used_bits += PMR_FLAG_LEN; | |
344 u_meas_report->release_99_str_pmr.v_meas_rep_3g_str = FALSE; | |
345 | |
346 used_bits += PMR_FLAG_LEN; | |
347 u_meas_report->release_99_str_pmr.v_ba_psi3_str = TRUE; | |
348 | |
349 used_bits += PMO_IND_USED_LEN; | |
350 u_meas_report->release_99_str_pmr.ba_psi3_str.pmo_ind_used = psc_db->nc_ms.pmo_ind; | |
351 | |
352 /* 1 bit for u_meas_report->ba_psi3_str.flag */ | |
353 used_bits += PMR_FLAG_LEN; | |
354 | |
355 /* process BA used, PSI3 change mark and PMO used */ | |
356 if( pbcch_present EQ FALSE ) | |
357 { | |
358 TRACE_EVENT_P1("pbcch_present %d", pbcch_present); | |
359 u_meas_report->release_99_str_pmr.ba_psi3_str.flag = FALSE; | |
360 | |
361 u_meas_report->release_99_str_pmr.ba_psi3_str.v_ba_ind_used = TRUE; | |
362 u_meas_report->release_99_str_pmr.ba_psi3_str.v_ba_ind_used_3g = TRUE; | |
363 | |
364 used_bits += PMR_BA_IND_USED_LEN; | |
365 u_meas_report->release_99_str_pmr.ba_psi3_str.ba_ind_used = psc_db->ba_ind; | |
366 | |
367 /* Add 1 bit for ba_ind_used_3g */ | |
368 u_meas_report->release_99_str_pmr.ba_psi3_str.ba_ind_used_3g = 0; | |
369 used_bits += PMR_BA_IND_USED_LEN; | |
370 } | |
371 else | |
372 { | |
373 u_meas_report->release_99_str_pmr.ba_psi3_str.flag = TRUE; | |
374 | |
375 u_meas_report->release_99_str_pmr.ba_psi3_str.v_psi3_cm = TRUE; | |
376 | |
377 used_bits += PMR_PSI3_CHNGE_MRK_LEN; | |
378 u_meas_report->release_99_str_pmr.ba_psi3_str.psi3_cm = psi3_cm; | |
379 } | |
380 } | |
381 #endif | |
382 | |
383 /* process NC mode */ | |
384 used_bits += NC_MODE_LEN; | |
385 | |
386 switch( nc_ord ) | |
387 { | |
388 case NC_NC1: ncmeas_rep->nc_mode = NCMODE_NC1; break; | |
389 case NC_NC2: ncmeas_rep->nc_mode = NCMODE_NC2; break; | |
390 | |
391 default: TRACE_ERROR( "cs_build_meas_rpt no valid NC mode" ); return( FALSE ); | |
392 } | |
393 | |
394 /* process serving cell data - rxlev and ilev */ | |
395 | |
396 return_value = | |
397 cs_process_serving_cell_data(&ncmeas_rep->rxlev_scell, | |
398 &ncmeas_rep->v_i_scell, | |
399 &ncmeas_rep->i_scell, &used_bits, | |
400 &rsc_avail, &isc_avail); | |
401 if((return_value EQ FALSE) AND (rsc_avail EQ FALSE)) | |
402 return(FALSE); | |
403 | |
404 | |
405 /* process NC measurement results */ | |
406 used_bits += NC_NUM_OF_MEAS_LEN; | |
407 ncmeas_rep->num_nc_meas = 0; | |
408 ncmeas_rep->c_nc_meas_s1 = 0; | |
409 is_first_instance = nmeas->pmr_snd_ref EQ 0 ? TRUE : FALSE; | |
410 | |
411 do | |
412 { | |
413 /* calculate estimated length of next measurement result */ | |
414 if( nmeas->pmr_snd_ref >= grr_data->db.cnt_nc_six.candid ) | |
415 { | |
416 mval = NULL; | |
417 ncell = NULL; | |
418 } | |
419 else | |
420 { | |
421 mval = &grr_data->db.nc_mval_list.nc_mval[grr_data->db.nc_six_strgst[nmeas->pmr_snd_ref].idx]; | |
422 | |
423 next_meas_bits = NC_FREQ_N_LEN + NC_RXLEV_N_LEN + PMR_FLAG_LEN; | |
424 | |
425 if( mval->sync_info.sync.status EQ STAT_SYNC_OK ) | |
426 { | |
427 UBYTE ncell_idx = 0; | |
428 | |
429 ncell = grr_get_ncell_info( mval->arfcn, mval->sync_info.bsic ); | |
430 | |
431 while( ncell_idx < grr_data->db.nc_ref_lst.number AND | |
432 ncell EQ NULL ) | |
433 { | |
434 ncell = grr_data->db.nc_ref_lst.info[ncell_idx]; | |
435 | |
436 if( ncell->arfcn NEQ mval->arfcn OR | |
437 NC_GET_TYPE( ncell->info_src ) NEQ INFO_TYPE_BA_BCCH ) | |
438 { | |
439 ncell = NULL; | |
440 } | |
441 | |
442 ncell_idx++; | |
443 } | |
444 | |
445 if( ncell NEQ NULL ) | |
446 { | |
447 next_meas_bits = NC_FREQ_N_LEN + NC_RXLEV_N_LEN + PMR_FLAG_LEN; | |
448 | |
449 if( NC_GET_TYPE( ncell->info_src ) EQ INFO_TYPE_BA_BCCH ) | |
450 { | |
451 next_meas_bits += NC_BSIC_N_LEN; | |
452 } | |
453 } | |
454 } | |
455 else | |
456 { | |
457 ncell = NULL; | |
458 } | |
459 } | |
460 | |
461 if( ncell NEQ NULL AND mval NEQ NULL) | |
462 { | |
463 if( BIT_UL_CTRL_BLOCK_CONTENTS - used_bits >= next_meas_bits ) | |
464 { | |
465 /* copy next measurement result to measurement report */ | |
466 | |
467 ncmeas_rep->num_nc_meas++; | |
468 ncmeas_rep->c_nc_meas_s1++; | |
469 used_bits += next_meas_bits; | |
470 p_mrpt = &ncmeas_rep->nc_meas_s1[ncmeas_rep->c_nc_meas_s1 - 1]; | |
471 | |
472 p_mrpt->freq_n = ncell->index; | |
473 p_mrpt->rxlev_n = mval->rxlev_avg; | |
474 | |
475 if( NC_GET_TYPE( ncell->info_src ) EQ INFO_TYPE_BA_BCCH ) | |
476 { | |
477 p_mrpt->bsic = mval->sync_info.bsic; | |
478 p_mrpt->v_bsic = TRUE; | |
479 } | |
480 else | |
481 { | |
482 p_mrpt->v_bsic = FALSE; | |
483 } | |
484 | |
485 nmeas->pmr_snd_ref++; | |
486 } | |
487 else | |
488 { | |
489 mval = NULL; | |
490 } | |
491 } | |
492 else | |
493 { | |
494 nmeas->pmr_snd_ref++; | |
495 } | |
496 | |
497 } | |
498 while( mval NEQ NULL ); | |
499 | |
500 return( is_first_instance OR ncmeas_rep->num_nc_meas ); | |
501 | |
502 | |
503 } /* cs_build_meas_rpt() */ | |
504 | |
505 /* | |
506 +------------------------------------------------------------------------------ | |
507 | Function : cs_is_meas_reporting | |
508 +------------------------------------------------------------------------------ | |
509 | Description : This function ... | |
510 | | |
511 | Parameters : ... | |
512 | | |
513 +------------------------------------------------------------------------------ | |
514 */ | |
515 GLOBAL UBYTE cs_is_meas_reporting ( void ) | |
516 { | |
517 T_NC_ORDER ctrl_order = cs_get_network_ctrl_order( TRUE ); | |
518 | |
519 TRACE_FUNCTION( "cs_is_meas_reporting" ); | |
520 | |
521 return( ctrl_order EQ NC_NC1 OR ctrl_order EQ NC_NC2 ); | |
522 | |
523 } /* cs_is_meas_reporting() */ | |
524 | |
525 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
526 /* | |
527 +------------------------------------------------------------------------------ | |
528 | Function : cs_is_enh_meas_reporting | |
529 +------------------------------------------------------------------------------ | |
530 | Description : This function is used to check whether enhanced measurement | |
531 | reporting is to be done. | |
532 | | |
533 | Parameters : returns TRUE if ENH reporting is to be done | |
534 | | |
535 +------------------------------------------------------------------------------ | |
536 */ | |
537 GLOBAL BOOL cs_is_enh_meas_reporting ( void ) | |
538 { | |
539 BOOL return_value = FALSE; | |
540 | |
541 TRACE_FUNCTION( "cs_is_enh_meas_reporting" ); | |
542 | |
543 if ( cs_is_meas_reporting() AND | |
544 (grr_data->db.nc_ref_lst.enh_param->rept_type EQ REPORT_TYPE_ENH_REP) ) | |
545 { | |
546 return_value = TRUE; | |
547 } | |
548 | |
549 return( return_value ); | |
550 } /* cs_is_enh_meas_reporting() */ | |
551 #endif | |
552 | |
553 /* | |
554 +------------------------------------------------------------------------------ | |
555 | Function : cs_build_nc_freq_list | |
556 +------------------------------------------------------------------------------ | |
557 | Description : | |
558 | | |
559 | Parameters : db - pointer to serving cell database | |
560 | | |
561 +------------------------------------------------------------------------------ | |
562 */ | |
563 LOCAL void cs_build_nc_freq_list ( T_SC_DATABASE *db ) | |
564 { | |
565 UBYTE i, j, k; /* used for counting */ | |
566 UBYTE act_idx; /* index of actual processed reference list entry */ | |
567 BOOL is_removed; | |
568 BOOL is_overwritten; | |
569 | |
570 T_ncell_info *info_ref_lst; | |
571 T_ncell_info *info_prev = ( db->nc_cw.list.number EQ 0 ? | |
572 NULL : | |
573 &db->nc_cw.list.info[db->nc_cw.list.number-1] ); | |
574 T_ncell_info *info_curr; | |
575 T_INFO_SRC info_src = 0; | |
576 | |
577 TRACE_FUNCTION( "cs_build_nc_freq_list" ); | |
578 | |
579 /* | |
580 * add neighbour cell information of BA(GPRS) to reference list | |
581 * in case they are not removed | |
582 */ | |
583 for( i = 0; i < db->nc_cw.list.number; i++ ) | |
584 { | |
585 /* | |
586 * looking for entry with correct index, | |
587 * they are no longer sorted with increasing number | |
588 */ | |
589 k = 0; | |
590 | |
591 while( k < db->nc_cw.list.number AND i NEQ db->nc_cw.list.info[k].index ) | |
592 { | |
593 k++; | |
594 } | |
595 | |
596 if( db->nc_cw.list.info[k].arfcn EQ psc_db->pbcch.bcch.arfcn ) | |
597 { | |
598 /* remove the serving cell from the neighbour cell reference list */ | |
599 is_removed = TRUE; | |
600 } | |
601 else | |
602 { | |
603 for( j = 0, is_removed = FALSE; | |
604 j < db->nc_ms.rfreq.number AND is_removed EQ FALSE; | |
605 j++ ) | |
606 { | |
607 if( db->nc_cw.list.info[k].index EQ db->nc_ms.rfreq.idx[j] ) | |
608 { | |
609 is_removed = TRUE; | |
610 } | |
611 } | |
612 } | |
613 | |
614 if( is_removed EQ FALSE ) | |
615 { | |
616 if( !( db->nc_cw.list.info[k].v_cr_par EQ FALSE AND | |
617 NC_GET_TYPE( db->nc_cw.list.info[k].info_src ) NEQ INFO_TYPE_BA_BCCH AND | |
618 cs_get_network_ctrl_order( TRUE ) NEQ NC_NC2 ) | |
619 AND | |
620 !( db->nc_cw.list.info[k].cr_par.cell_ba ) ) | |
621 { | |
622 grr_data->db.nc_ref_lst.info[grr_data->db.nc_ref_lst.number] = | |
623 &db->nc_cw.list.info[k]; | |
624 grr_data->db.nc_ref_lst.number++; | |
625 } | |
626 else | |
627 { | |
628 | |
629 #if !defined (NTRACE) | |
630 | |
631 if( grr_data->cs.v_crp_trace EQ TRUE ) | |
632 { | |
633 TRACE_EVENT_P2( "cs_build_nc_freq_list 1: not added to NC_REF_LST %d %d", | |
634 db->nc_cw.list.info[k].arfcn, db->nc_cw.list.info[k].bsic ); | |
635 } | |
636 | |
637 #endif /* #if !defined (NTRACE) */ | |
638 | |
639 } | |
640 } | |
641 else | |
642 { | |
643 | |
644 #if !defined (NTRACE) | |
645 | |
646 if( grr_data->cs.v_crp_trace EQ TRUE ) | |
647 { | |
648 TRACE_EVENT_P2( "cs_build_nc_freq_list 2: not added to NC_REF_LST %d %d", | |
649 db->nc_cw.list.info[k].arfcn, db->nc_cw.list.info[k].bsic ); | |
650 } | |
651 | |
652 #endif /* #if !defined (NTRACE) */ | |
653 | |
654 | |
655 } | |
656 } | |
657 | |
658 /* | |
659 * add/overwrite neighbour cell information to/of reference list | |
660 */ | |
661 i = 0; | |
662 | |
663 while( ( info_curr = grr_get_next_bigger_ncell_param | |
664 ( &db->nc_ms.ncmeas.list, info_src ) ) NEQ NULL ) | |
665 { | |
666 j = 0; | |
667 is_overwritten = FALSE; | |
668 | |
669 while( j < grr_data->db.nc_ref_lst.number AND is_overwritten EQ FALSE ) | |
670 { | |
671 info_ref_lst = grr_data->db.nc_ref_lst.info[j]; | |
672 | |
673 if( NC_GET_TYPE( info_ref_lst->info_src ) NEQ INFO_TYPE_BA_BCCH AND | |
674 info_ref_lst->v_cr_par EQ TRUE AND | |
675 info_curr->v_cr_par EQ TRUE AND | |
676 info_ref_lst->bsic EQ info_curr->bsic AND | |
677 info_ref_lst->arfcn EQ info_curr->arfcn ) | |
678 { | |
679 is_overwritten = TRUE; | |
680 } | |
681 else | |
682 { | |
683 j++; | |
684 } | |
685 } | |
686 | |
687 /* | |
688 * calculate the index of the reference list entry | |
689 * which shall be used for further processing | |
690 */ | |
691 if( is_overwritten EQ FALSE ) | |
692 { | |
693 if( grr_data->db.nc_ref_lst.number < MAX_NR_OF_NCELL ) | |
694 { | |
695 act_idx = grr_data->db.nc_ref_lst.number; | |
696 } | |
697 else | |
698 { | |
699 TRACE_ERROR( "cs_build_nc_freq_list: reference list full" ); | |
700 return; | |
701 } | |
702 } | |
703 else | |
704 { | |
705 act_idx = j; | |
706 } | |
707 | |
708 | |
709 if( | |
710 !( info_curr->v_cr_par EQ FALSE AND | |
711 NC_GET_TYPE( info_curr->info_src ) NEQ INFO_TYPE_BA_BCCH AND | |
712 cs_get_network_ctrl_order( TRUE ) NEQ NC_NC2 ) | |
713 AND | |
714 !( info_curr->cr_par.cell_ba ) | |
715 AND | |
716 ( info_curr->arfcn NEQ psc_db->pbcch.bcch.arfcn ) | |
717 ) | |
718 { | |
719 /* | |
720 * add/overwrite reference list entry | |
721 */ | |
722 grr_data->db.nc_ref_lst.info[act_idx] = info_curr; | |
723 grr_data->db.nc_ref_lst.number++; | |
724 | |
725 /* process cell selection parameter */ | |
726 grr_restore_cs_param | |
727 ( info_curr, info_prev, (UBYTE)( db->nc_cw.list.number + i ) ); | |
728 | |
729 | |
730 if( info_curr->v_cr_par EQ TRUE ) | |
731 { | |
732 info_prev = info_curr; | |
733 } | |
734 } | |
735 else | |
736 { | |
737 | |
738 #if !defined (NTRACE) | |
739 | |
740 if( grr_data->cs.v_crp_trace EQ TRUE ) | |
741 { | |
742 TRACE_EVENT_P2( "cs_build_nc_freq_list 3: not added to NC_REF_LST %d %d", | |
743 info_curr->arfcn, info_curr->bsic ); | |
744 } | |
745 | |
746 #endif /* #if !defined (NTRACE) */ | |
747 | |
748 info_curr->index = db->nc_cw.list.number + i; | |
749 } | |
750 | |
751 info_src = info_curr->info_src; | |
752 | |
753 i++; | |
754 } | |
755 | |
756 #if !defined (NTRACE) | |
757 | |
758 if( grr_data->cs.v_crp_trace EQ TRUE ) | |
759 { | |
760 UBYTE read; | |
761 USHORT crp_s; | |
762 ULONG crp[4]; | |
763 T_ncell_info *info; | |
764 | |
765 crp[0] = ( ( ULONG )psc_db->pbcch.bcch.arfcn << 16 ); | |
766 crp[0] |= ( ( ULONG )psc_db->pbcch.bcch.bsic << 8 ); | |
767 crp[0] |= ( ULONG )psc_db->scell_par.cell_ba; | |
768 | |
769 crp[1] = ( ( ULONG )psc_db->scell_par.exc_acc << 24 ); | |
770 crp[1] |= ( ( ULONG )psc_db->scell_par.cr_par_1.cr_pow_par.gprs_rxlev_access_min << 16 ); | |
771 crp[1] |= ( ( ULONG )psc_db->scell_par.cr_par_1.cr_pow_par.gprs_ms_txpwr_max_cch << 8 ); | |
772 | |
773 if( psc_db->scell_par.cr_par_1.v_hcs_par ) | |
774 { | |
775 crp[1] |= ( ULONG )psc_db->scell_par.cr_par_1.hcs_par.gprs_prio_class; | |
776 crp_s = ( ( USHORT )psc_db->scell_par.cr_par_1.hcs_par.gprs_hcs_thr << 8 ); | |
777 } | |
778 else | |
779 { | |
780 crp[1] |= ( ULONG )0xFF; | |
781 crp_s = ( ( USHORT )0xFF << 8 ); | |
782 } | |
783 | |
784 crp_s |= ( ULONG )psc_db->scell_par.multi_band_rep; | |
785 | |
786 TRACE_EVENT_P3( "SCELL %08X%08X%04X", crp[0], crp[1], crp_s ); | |
787 | |
788 for( read = 0; read < grr_data->db.nc_ref_lst.number; read++ ) | |
789 { | |
790 info = grr_data->db.nc_ref_lst.info[read]; | |
791 | |
792 crp[0] = ( ( ULONG )info->arfcn << 16 ); | |
793 crp[0] |= ( ( ULONG )info->bsic << 8 ); | |
794 | |
795 if( info->v_cr_par ) | |
796 { | |
797 crp[0] |= ( ULONG )info->cr_par.cell_ba; | |
798 | |
799 crp[1] = ( ( ULONG )info->cr_par.exc_acc << 24 ); | |
800 crp[1] |= ( ( ULONG )info->cr_par.same_ra_scell << 16 ); | |
801 crp[1] |= ( ( ULONG )info->cr_par.cr_par_1.cr_pow_par.gprs_rxlev_access_min << 8 ); | |
802 crp[1] |= ( ULONG )info->cr_par.cr_par_1.cr_pow_par.gprs_ms_txpwr_max_cch; | |
803 | |
804 crp[2] = ( ( ULONG )info->cr_par.cr_offset.gprs_temp_offset << 24 ); | |
805 crp[2] |= ( ( ULONG )info->cr_par.cr_offset.gprs_penalty_time << 16 ); | |
806 crp[2] |= ( ( ULONG )info->cr_par.gprs_resel_off << 8 ); | |
807 | |
808 if( grr_data->db.nc_ref_lst.info[read]->cr_par.cr_par_1.v_hcs_par ) | |
809 { | |
810 crp[2] |= ( ULONG )info->cr_par.cr_par_1.hcs_par.gprs_prio_class; | |
811 crp[3] = ( ( ULONG )info->cr_par.cr_par_1.hcs_par.gprs_hcs_thr << 24 ); | |
812 } | |
813 else | |
814 { | |
815 crp[2] |= ( ULONG )0xFF; | |
816 crp[3] = ( ( ULONG )0xFF << 24 ); | |
817 } | |
818 | |
819 if( info->cr_par.v_si13_pbcch ) | |
820 { | |
821 if( info->cr_par.si13_pbcch.v_si13_location ) | |
822 { | |
823 crp[3] |= ( ( ULONG )info->cr_par.si13_pbcch.si13_location << 16 ); | |
824 crp[3] |= ( ( ULONG )0xFF << 8 ); | |
825 crp[3] |= ( ULONG )0xFF; | |
826 } | |
827 else | |
828 { | |
829 crp[3] |= ( ( ULONG )0xFF << 16 ); | |
830 crp[3] |= ( ( ULONG )info->cr_par.si13_pbcch.pbcch_location << 8 ); | |
831 crp[3] |= ( ULONG )info->cr_par.si13_pbcch.psi1_repeat_period; | |
832 } | |
833 } | |
834 else | |
835 { | |
836 crp[3] |= ( ULONG )0xFFFFFF; | |
837 } | |
838 } | |
839 else | |
840 { | |
841 crp[1] |= ( ULONG )0xFF; | |
842 crp[2] = ( ULONG )0xFFFFFFFF; | |
843 crp[3] = ( ULONG )0xFFFFFFFF; | |
844 } | |
845 | |
846 TRACE_EVENT_P5( "NC_REF_LST[%d] %08X%08X%08X%08X", | |
847 read, crp[0], crp[1], crp[2], crp[3] ); | |
848 } | |
849 } | |
850 | |
851 #endif /* #if !defined (NTRACE) */ | |
852 | |
853 }/* cs_build_nc_freq_list */ | |
854 | |
855 /* | |
856 +------------------------------------------------------------------------------ | |
857 | Function : cs_reorg_nc_mval_lst | |
858 +------------------------------------------------------------------------------ | |
859 | Description : | |
860 | | |
861 | Parameters : | |
862 | | |
863 +------------------------------------------------------------------------------ | |
864 */ | |
865 LOCAL void cs_reorg_nc_mval_lst ( void ) | |
866 { | |
867 BOOL scell_restored = FALSE; | |
868 UBYTE mval_idx; | |
869 UBYTE nc_idx; | |
870 T_NC_MVAL *nc_mval; | |
871 T_ncell_info *ncell_info; | |
872 | |
873 TRACE_FUNCTION( "cs_reorg_nc_mval_lst" ); | |
874 | |
875 for( mval_idx = 0; mval_idx < MAX_NR_OF_NC_MVAL; mval_idx++ ) | |
876 { | |
877 /* | |
878 * check whether measured values can be reused | |
879 */ | |
880 | |
881 nc_mval = &grr_data->db.nc_mval_list.nc_mval[mval_idx]; | |
882 | |
883 if( nc_mval->status NEQ NC_MVAL_STAT_NONE ) | |
884 { | |
885 /* | |
886 * only used entries shall be considered | |
887 */ | |
888 | |
889 if( psc_db->pbcch.bcch.arfcn EQ nc_mval->arfcn AND | |
890 psc_db->pbcch.bcch.arfcn NEQ RRGRR_INVALID_ARFCN ) | |
891 { | |
892 /* | |
893 * remove the measured values from the serving cell, | |
894 * this cell will not be used for cell re-selection | |
895 */ | |
896 cs_init_nc_mval( nc_mval ); | |
897 } | |
898 else | |
899 { | |
900 ncell_info = grr_get_ncell_info( nc_mval->arfcn, RRGRR_INVALID_BSIC ); | |
901 | |
902 if( ncell_info EQ NULL ) | |
903 { | |
904 /* | |
905 * cell is not on the neighbor cell list, | |
906 * keep the measured values until RR informs GRR, | |
907 * but do not use them | |
908 */ | |
909 nc_mval->status = NC_MVAL_STAT_PENDING; | |
910 nc_mval->rla_p.stat = CS_RLA_P_NOT_AVAIL; | |
911 } | |
912 else | |
913 { | |
914 /* | |
915 * cell is on the neighbor cell list, | |
916 * re-activate the measured values | |
917 */ | |
918 nc_mval->status = NC_MVAL_STAT_ASSIGNED; | |
919 } | |
920 | |
921 if( grr_data->db.old_scell.arfcn EQ nc_mval->arfcn AND | |
922 grr_data->db.old_scell.arfcn NEQ RRGRR_INVALID_ARFCN ) | |
923 { | |
924 /* | |
925 * in case the old serving cell is on the measured values list, | |
926 * keep the results for further use | |
927 */ | |
928 scell_restored = TRUE; | |
929 | |
930 nc_mval->sync_info.bsic = grr_data->db.old_scell.bsic; | |
931 nc_mval->sync_info.sync.status = STAT_SYNC_OK; | |
932 nc_mval->sync_info.sync.sync_failed_cnt = 0; | |
933 } | |
934 } | |
935 } | |
936 } | |
937 | |
938 for( nc_idx = 0; nc_idx < grr_data->db.nc_ref_lst.number; nc_idx++ ) | |
939 { | |
940 nc_mval = grr_get_nc_mval( grr_data->db.nc_ref_lst.info[nc_idx]->arfcn, | |
941 RRGRR_INVALID_BSIC, &mval_idx ); | |
942 | |
943 if( nc_mval EQ NULL ) | |
944 { | |
945 nc_mval = | |
946 grr_get_nc_mval( RRGRR_INVALID_ARFCN, RRGRR_INVALID_BSIC, &mval_idx ); | |
947 | |
948 if( nc_mval NEQ NULL ) | |
949 { | |
950 nc_mval->status = NC_MVAL_STAT_ASSIGNED; | |
951 nc_mval->arfcn = grr_data->db.nc_ref_lst.info[nc_idx]->arfcn; | |
952 | |
953 if( grr_data->db.old_scell.arfcn EQ nc_mval->arfcn AND | |
954 grr_data->db.old_scell.arfcn NEQ RRGRR_INVALID_ARFCN ) | |
955 { | |
956 scell_restored = TRUE; | |
957 | |
958 nc_mval->sync_info.bsic = grr_data->db.old_scell.bsic; | |
959 nc_mval->sync_info.sync.status = STAT_SYNC_OK; | |
960 nc_mval->sync_info.sync.sync_failed_cnt = 0; | |
961 | |
962 TRACE_EVENT_P2( "cs_reorg_nc_mval_lst: old SCELL on new NCELL list (1) %d %d", | |
963 grr_data->db.nc_ref_lst.info[nc_idx]->arfcn, | |
964 grr_data->db.nc_ref_lst.info[nc_idx]->bsic ); | |
965 } | |
966 } | |
967 else | |
968 { | |
969 TRACE_EVENT_P1( "cs_reorg_nc_mval_lst: nc_mval EQ NULL (1) %d", | |
970 RRGRR_INVALID_ARFCN ); | |
971 } | |
972 } | |
973 else | |
974 { | |
975 if( grr_data->db.old_scell.arfcn EQ nc_mval->arfcn AND | |
976 grr_data->db.old_scell.arfcn NEQ RRGRR_INVALID_ARFCN ) | |
977 { | |
978 scell_restored = TRUE; | |
979 | |
980 nc_mval->status = NC_MVAL_STAT_ASSIGNED; | |
981 nc_mval->sync_info.bsic = grr_data->db.old_scell.bsic; | |
982 nc_mval->sync_info.sync.status = STAT_SYNC_OK; | |
983 nc_mval->sync_info.sync.sync_failed_cnt = 0; | |
984 | |
985 TRACE_EVENT_P2( "cs_reorg_nc_mval_lst: old SCELL on new NCELL list (2) %d %d", | |
986 grr_data->db.nc_ref_lst.info[nc_idx]->arfcn, | |
987 grr_data->db.nc_ref_lst.info[nc_idx]->bsic ); | |
988 } | |
989 } | |
990 } | |
991 | |
992 if( scell_restored EQ FALSE AND | |
993 grr_data->db.old_scell.arfcn NEQ RRGRR_INVALID_ARFCN ) | |
994 { | |
995 nc_mval = | |
996 grr_get_nc_mval( RRGRR_INVALID_ARFCN, RRGRR_INVALID_BSIC, &mval_idx ); | |
997 | |
998 if( nc_mval NEQ NULL ) | |
999 { | |
1000 nc_mval->status = NC_MVAL_STAT_PENDING; | |
1001 nc_mval->arfcn = grr_data->db.old_scell.arfcn; | |
1002 nc_mval->sync_info.bsic = grr_data->db.old_scell.bsic; | |
1003 nc_mval->sync_info.sync.status = STAT_SYNC_OK; | |
1004 nc_mval->sync_info.sync.sync_failed_cnt = 0; | |
1005 } | |
1006 else | |
1007 { | |
1008 TRACE_EVENT_P1( "cs_reorg_nc_mval_lst: nc_mval EQ NULL (2) %d", | |
1009 RRGRR_INVALID_ARFCN ); | |
1010 } | |
1011 } | |
1012 | |
1013 grr_data->cs.is_mval_initialized = FALSE; | |
1014 | |
1015 cs_trace_nc_mval_lst( ); | |
1016 | |
1017 }/* cs_reorg_nc_mval_lst */ | |
1018 | |
1019 /*==== PUBLIC FUNCTIONS =====================================================*/ | |
1020 /* | |
1021 +------------------------------------------------------------------------------ | |
1022 | Function : cs_grr_init | |
1023 +------------------------------------------------------------------------------ | |
1024 | Description : The function cs_grr_init() .... name change becauce there is a | |
1025 | function in cs_init in TIL. | |
1026 | | |
1027 | Parameters : void | |
1028 | | |
1029 +------------------------------------------------------------------------------ | |
1030 */ | |
1031 GLOBAL void cs_grr_init ( void ) | |
1032 { | |
1033 TRACE_FUNCTION( "cs_grr_init" ); | |
1034 | |
1035 grr_data->cs.gmm_state = STANDBY_STATE; | |
1036 grr_data->cs.last_cr = 0; | |
1037 grr_data->cs.reselect_cause = CS_RESELECT_CAUSE_CS_NORMAL; | |
1038 grr_data->cs.is_mval_initialized = FALSE; | |
1039 grr_data->cs.nc_sync_rep_pd = 0; | |
1040 | |
1041 #if !defined (NTRACE) | |
1042 | |
1043 grr_data->cs.v_crp_trace = FALSE; | |
1044 | |
1045 #endif /* #if !defined (NTRACE) */ | |
1046 | |
1047 grr_init_ncmeas_extd_struct( &psc_db->nc_ms, FALSE ); | |
1048 cs_init_nc_ref_list( &grr_data->db.nc_ref_lst ); | |
1049 cs_init_nc_mval_lst( ); | |
1050 | |
1051 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
1052 /* Initialize Enhanced Measurement parameters and list */ | |
1053 grr_init_enh_param(&psc_db->enh_ms, TRUE); | |
1054 grr_init_enh_cell_list(); | |
1055 #endif | |
1056 | |
1057 grr_data->cs_meas.pmr_snd_ref = 0; | |
1058 grr_data->cs_meas.packet_mode = PACKET_MODE_NULL; | |
1059 | |
1060 nc_data = &grr_data->nc_data; | |
1061 | |
1062 cs_reset_all_cell_results( ); | |
1063 | |
1064 grr_data->cs.list_id = 0; | |
1065 grr_data->cs.stop_req = FALSE; | |
1066 | |
1067 nc_data->c_cell = 0; | |
1068 | |
1069 grr_data->cs.cr_meas_mode = CS_CRMM_BA_GPRS; | |
1070 grr_data->cs.cr_meas_update = FALSE; | |
1071 grr_data->cs.last_assignment_id = 0; | |
1072 | |
1073 | |
1074 INIT_STATE( CS_MEAS, CS_MEAS_NULL ); | |
1075 INIT_STATE( CS, CS_NULL ); | |
1076 } /* cs_grr_init() */ | |
1077 | |
1078 /* | |
1079 +------------------------------------------------------------------------------ | |
1080 | Function : cs_process_cc_order | |
1081 +------------------------------------------------------------------------------ | |
1082 | Description : The function cs_process_cc_order() .... | |
1083 | | |
1084 | Parameters : d_cell_chan_order - Pointer to packet cell change order message | |
1085 | | |
1086 +------------------------------------------------------------------------------ | |
1087 */ | |
1088 GLOBAL void cs_process_cc_order ( T_nc_meas_par *nc_meas_par, | |
1089 UBYTE v_nc_freq_list, | |
1090 T_nc_freq_list *nc_freq_list | |
1091 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
1092 , UBYTE v_enh_meas_param_pcco, | |
1093 T_enh_meas_param_pcco *enh_meas_param_pcco | |
1094 #endif | |
1095 ) | |
1096 { | |
1097 TRACE_FUNCTION( "cs_process_cc_order" ); | |
1098 | |
1099 grr_init_ncmeas_extd_struct( &pcr_db->nc_ms, FALSE ); | |
1100 | |
1101 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
1102 /* Initialize Enhanced Measurement parameters */ | |
1103 grr_init_enh_param(&pcr_db->enh_ms, TRUE); | |
1104 #endif | |
1105 | |
1106 /* | |
1107 * process the NC measurement parameter | |
1108 * | |
1109 * only one instance of PCCO, store data in final location | |
1110 */ | |
1111 grr_prcs_nc_param_struct ( &pcr_db->nc_ms.ncmeas.param, | |
1112 nc_meas_par, | |
1113 0 ); | |
1114 | |
1115 /* For PCCO the paramater obtained in PCCO should be applied immediately | |
1116 Sec 5.6.1 Spec 4.60 */ | |
1117 grr_data->db.nc_ref_lst.param = &pcr_db->nc_ms.ncmeas.param; | |
1118 | |
1119 /* | |
1120 * process NC_FREQUENCY_LIST | |
1121 * | |
1122 * only one instance of PCCO, store data in final location | |
1123 */ | |
1124 grr_prcs_nc_freq_list ( &pcr_db->nc_ms.ncmeas.list, | |
1125 &pcr_db->nc_ms.rfreq, | |
1126 v_nc_freq_list, | |
1127 nc_freq_list, | |
1128 INFO_TYPE_PCCO, | |
1129 0 ); | |
1130 | |
1131 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
1132 /* | |
1133 * process the ENH measurement parameter | |
1134 * | |
1135 * only one instance of PCCO, store data in final location | |
1136 */ | |
1137 if(v_enh_meas_param_pcco) | |
1138 { | |
1139 grr_prcs_enh_param_pcco ( pcr_db, enh_meas_param_pcco ); | |
1140 } | |
1141 #endif | |
1142 | |
1143 } /* cs_process_cc_order() */ | |
1144 | |
1145 /* | |
1146 +------------------------------------------------------------------------------ | |
1147 | Function : cs_calc_cr_criterion | |
1148 +------------------------------------------------------------------------------ | |
1149 | Description : The function cs_calc_cr_criterion() .... | |
1150 | | |
1151 | Parameters : dummy - description of parameter dummy | |
1152 | | |
1153 +------------------------------------------------------------------------------ | |
1154 */ | |
1155 GLOBAL void cs_calc_cr_criterion ( T_CR_CRITERIONS *cr_crit, | |
1156 USHORT arfcn, | |
1157 T_rla_p *rla_p, | |
1158 T_CR_PAR_1 *cr_par_1 ) | |
1159 { | |
1160 T_MS_PWR_CAP mspc; | |
1161 SHORT A, B; | |
1162 | |
1163 TRACE_FUNCTION( "cs_calc_cr_criterion" ); | |
1164 | |
1165 /* C1 = A - MAX(B,0) */ | |
1166 /* A = RLA_P - GPRS_RXLEV_ACCESS_MIN */ | |
1167 /* B = GPRS_MS_TXPWR_MAX_CCH - P */ | |
1168 /* P = max MS RF output power */ | |
1169 | |
1170 /* C31 = RLA_P(s) - HCS_THR(s) (serving cell) */ | |
1171 /* C31 = RLA_P(n) - HCS_THR(n) - TO(n)*L(n) (neighbour cell) */ | |
1172 /* TO(n) = GPRS_TEMPORARY_OFFSET(n) * H( GPRS_PENALTY_TIME(N) - T(n) ) */ | |
1173 /* L(n) = 0 if PRIORITY_CLASS(n) = PRIORITY_CLASS(s) */ | |
1174 /* 1 if PRIORITY_CLASS(n) = PRIORITY_CLASS(s) */ | |
1175 | |
1176 /* C32(s) = C1(s) */ | |
1177 /* C32(n) = C1(n) + GPRS_RESELECT OFFSET(n) - TO(n)*(1-L(n)) */ | |
1178 /* TO(n) = GPRS_TEMPORARY_OFFSET(n) * H( GPRS_PENALTY_TIME(N) - T(n) ) */ | |
1179 /* L(n) = 0 if PRIORITY_CLASS(n) = PRIORITY_CLASS(s) */ | |
1180 /* 1 if PRIORITY_CLASS(n) = PRIORITY_CLASS(s) */ | |
1181 /* H(n) = 0 for x < 0 */ | |
1182 /* 1 for x >= 0 */ | |
1183 /* T(n) = ????? */ | |
1184 | |
1185 grr_get_ms_pwr_cap( arfcn, grr_data->meas.pwr_offset, &mspc ); | |
1186 | |
1187 /* | |
1188 * calculate cell re-selection criteria acc. GSM05.08, | |
1189 * chapter 10.1.2 for the serving/neighbour cell | |
1190 */ | |
1191 | |
1192 /* intermediate results for serving/neighbour cell */ | |
1193 A = (SHORT)rla_p->lev - (SHORT)cr_par_1->cr_pow_par.gprs_rxlev_access_min; | |
1194 B = mspc.p_control[cr_par_1->cr_pow_par.gprs_ms_txpwr_max_cch] - mspc.p[mspc.ms_power]; | |
1195 | |
1196 /* path loss criterion for serving/neighbour cell */ | |
1197 cr_crit->c1 = A - MAXIMUM( B, 0 ); | |
1198 | |
1199 /* signal threshold criterion for serving/neighbour cell */ | |
1200 cr_crit->c31 = ( SHORT )rla_p->lev; | |
1201 | |
1202 if( cr_par_1->v_hcs_par ) | |
1203 { | |
1204 cr_crit->c31 -= ( 2 * cr_par_1->hcs_par.gprs_hcs_thr ); | |
1205 } | |
1206 | |
1207 /* cell ranking criterion for serving/neighbour cell */ | |
1208 cr_crit->c32 = cr_crit->c1; | |
1209 | |
1210 } /* cs_calc_cr_criterion() */ | |
1211 | |
1212 /* | |
1213 +------------------------------------------------------------------------------ | |
1214 | Function : cs_calc_params | |
1215 +------------------------------------------------------------------------------ | |
1216 | Description : The function cs_calc_params() .... | |
1217 | | |
1218 | Parameters : dummy - description of parameter dummy | |
1219 | | |
1220 +------------------------------------------------------------------------------ | |
1221 */ | |
1222 GLOBAL void cs_calc_params ( void ) | |
1223 { | |
1224 BOOL prio_cr = FALSE; | |
1225 UBYTE h; | |
1226 UBYTE i, prios, prion, strgst = 0xFF; | |
1227 T_ncell_info *ncell_info; | |
1228 T_NC_MVAL *nc_mval; | |
1229 | |
1230 TRACE_FUNCTION( "cs_calc_params" ); | |
1231 | |
1232 /* C1 = A - MAX(B,0) */ | |
1233 /* A = RLA_P - GPRS_RXLEV_ACCESS_MIN */ | |
1234 /* B = GPRS_MS_TXPWR_MAX_CCH - P */ | |
1235 /* P = max MS RF output power */ | |
1236 | |
1237 /* C31 = RLA_P(s) - HCS_THR(s) (serving cell) */ | |
1238 /* C31 = RLA_P(n) - HCS_THR(n) - TO(n)*L(n) (neighbour cell) */ | |
1239 /* TO(n) = GPRS_TEMPORARY_OFFSET(n) * H( GPRS_PENALTY_TIME(N) - T(n) ) */ | |
1240 /* L(n) = 0 if PRIORITY_CLASS(n) = PRIORITY_CLASS(s) */ | |
1241 /* 1 if PRIORITY_CLASS(n) = PRIORITY_CLASS(s) */ | |
1242 | |
1243 /* C32(s) = C1(s) */ | |
1244 /* C32(n) = C1(n) + GPRS_RESELECT OFFSET(n) - TO(n)*(1-L(n)) */ | |
1245 /* TO(n) = GPRS_TEMPORARY_OFFSET(n) * H( GPRS_PENALTY_TIME(N) - T(n) ) */ | |
1246 /* L(n) = 0 if PRIORITY_CLASS(n) = PRIORITY_CLASS(s) */ | |
1247 /* 1 if PRIORITY_CLASS(n) = PRIORITY_CLASS(s) */ | |
1248 /* H(n) = 0 for x < 0 */ | |
1249 /* 1 for x >= 0 */ | |
1250 /* T(n) = ????? */ | |
1251 | |
1252 cs_calc_cr_criterion( &grr_data->db.scell_info.cr_crit, | |
1253 psc_db->pbcch.bcch.arfcn, | |
1254 &grr_data->db.scell_info.rla_p, | |
1255 &psc_db->scell_par.cr_par_1 ); | |
1256 | |
1257 /* priority class for serving cell */ | |
1258 prios = ( psc_db->scell_par.cr_par_1.v_hcs_par ) ? | |
1259 psc_db->scell_par.cr_par_1.hcs_par.gprs_prio_class : 0; | |
1260 | |
1261 /* | |
1262 * calculate cell re-selection criteria acc. GSM05.08, | |
1263 * chapter 10.1.2 for the neighbour cells | |
1264 */ | |
1265 for( i = 0; i < grr_data->db.cnt_nc_six.strgst; i++ ) | |
1266 { | |
1267 h = FALSE; | |
1268 nc_mval = &grr_data->db.nc_mval_list.nc_mval[grr_data->db.nc_six_strgst[i].idx]; | |
1269 | |
1270 if( nc_mval->sync_info.sync.status EQ STAT_SYNC_OK ) | |
1271 { | |
1272 ncell_info = | |
1273 grr_get_ncell_info( nc_mval->arfcn, nc_mval->sync_info.bsic ); | |
1274 | |
1275 if( ncell_info NEQ NULL ) | |
1276 { | |
1277 cs_calc_cr_criterion( &grr_data->db.nc_six_strgst[i].cr_crit, | |
1278 ncell_info->arfcn, | |
1279 &nc_mval->rla_p, | |
1280 &ncell_info->cr_par.cr_par_1 ); | |
1281 | |
1282 /* cell ranking criterion for neighbour cell, add GPRS_RESELECT_OFFSET */ | |
1283 | |
1284 /* | |
1285 * if the parameter C32_QUAL is set, positive GPRS_RESELECT_OFFSET values | |
1286 * shall only be applied to the neighbour cell with the highest RLA_P value | |
1287 * of those cells for which C32 is compared. | |
1288 * | |
1289 * calculation part 1 | |
1290 */ | |
1291 if( psc_db->gen_cell_par.c32_qual EQ FALSE OR | |
1292 p_res_off[ncell_info->cr_par.gprs_resel_off] < 0 ) | |
1293 { | |
1294 grr_data->db.nc_six_strgst[i].cr_crit.c32 += | |
1295 p_res_off[ncell_info->cr_par.gprs_resel_off]; | |
1296 } | |
1297 | |
1298 /* priority class of neighbour cell */ | |
1299 prion = ( ncell_info->cr_par.cr_par_1.v_hcs_par ) ? | |
1300 ncell_info->cr_par.cr_par_1.hcs_par.gprs_prio_class : 0; | |
1301 | |
1302 /* check whether GPRS_TEMPORARY_OFFSET shall be considered */ | |
1303 if( (ULONG)( ( ncell_info->cr_par.cr_offset.gprs_penalty_time + 1 ) * | |
1304 10 * CS_PERIOD_1_SEC ) > grr_data->db.nc_six_strgst[i].avail_time ) | |
1305 { | |
1306 h = TRUE; | |
1307 } | |
1308 | |
1309 /* | |
1310 * cell ranking and signal threshold criterion for neighbour cell, | |
1311 * subtract GPRS_TEMPORARY_OFFSET | |
1312 */ | |
1313 if( h ) | |
1314 { | |
1315 SHORT *criterion; | |
1316 | |
1317 if( prios NEQ prion ) | |
1318 { | |
1319 criterion = &grr_data->db.nc_six_strgst[i].cr_crit.c31; | |
1320 } | |
1321 else | |
1322 { | |
1323 criterion = &grr_data->db.nc_six_strgst[i].cr_crit.c32; | |
1324 } | |
1325 | |
1326 if( ncell_info->cr_par.cr_offset.gprs_temp_offset EQ | |
1327 GPRS_TEMPORARY_OFFSET_INFINITY ) | |
1328 { | |
1329 *criterion = CS_SMALLEST_SHORT_VALUE; | |
1330 } | |
1331 else | |
1332 { | |
1333 *criterion -= 10 * ncell_info->cr_par.cr_offset.gprs_temp_offset; | |
1334 } | |
1335 } | |
1336 | |
1337 /* | |
1338 * cell ranking and signal threshold criterion for neighbour cell, | |
1339 * subtract RA_RESELECT_HYSTERESIS and/or GPRS_CELL_RESELECT_HYSTERESIS | |
1340 */ | |
1341 if( !ncell_info->cr_par.same_ra_scell ) | |
1342 { | |
1343 grr_data->db.nc_six_strgst[i].cr_crit.c32 -= | |
1344 2 * psc_db->gen_cell_par.ra_re_hyst; | |
1345 } | |
1346 else if( grr_data->cs.gmm_state NEQ STANDBY_STATE ) | |
1347 { | |
1348 grr_data->db.nc_six_strgst[i].cr_crit.c32 -= | |
1349 2 * psc_db->gen_cell_par.gprs_c_hyst; | |
1350 | |
1351 if( psc_db->gen_cell_par.c31_hyst ) | |
1352 { | |
1353 grr_data->db.nc_six_strgst[i].cr_crit.c31 -= | |
1354 2 * psc_db->gen_cell_par.gprs_c_hyst; | |
1355 } | |
1356 } | |
1357 | |
1358 /* | |
1359 * in case a cell re-selection occured within the | |
1360 * previous 15 seconds, subtract 5 dB | |
1361 */ | |
1362 if(grr_t_status( T15_SEC_CC ) > 0) | |
1363 { | |
1364 grr_data->db.nc_six_strgst[i].cr_crit.c32 -= 5; | |
1365 } | |
1366 } | |
1367 else | |
1368 { | |
1369 grr_data->db.nc_six_strgst[i].cr_crit.c1 = -2; | |
1370 grr_data->db.nc_six_strgst[i].cr_crit.c31 = -2; | |
1371 grr_data->db.nc_six_strgst[i].cr_crit.c32 = -2; | |
1372 } | |
1373 } | |
1374 else | |
1375 { | |
1376 grr_data->db.nc_six_strgst[i].cr_crit.c1 = -1; | |
1377 grr_data->db.nc_six_strgst[i].cr_crit.c31 = -1; | |
1378 grr_data->db.nc_six_strgst[i].cr_crit.c32 = -1; | |
1379 } | |
1380 } | |
1381 | |
1382 /* | |
1383 * calculate the correct neighbour cell for adding positive | |
1384 * GPRS_RESELECT_OFFSET values to C32 in case C32_QUAL is set | |
1385 */ | |
1386 if( psc_db->gen_cell_par.c32_qual EQ TRUE ) | |
1387 { | |
1388 /* | |
1389 * check whether priorized cell re-selection should be performed | |
1390 */ | |
1391 for( i = 0; i < grr_data->db.cnt_nc_six.strgst; i++ ) | |
1392 { | |
1393 if( grr_data->db.nc_six_strgst[i].cr_crit.c31 >= 0 ) | |
1394 { | |
1395 prio_cr = TRUE; | |
1396 } | |
1397 } | |
1398 | |
1399 if( grr_data->db.scell_info.cr_crit.c31 >= 0 ) | |
1400 { | |
1401 prio_cr = TRUE; | |
1402 } | |
1403 | |
1404 /* find out the strongest neighbour cell */ | |
1405 for( i = 0; i < grr_data->db.cnt_nc_six.strgst; i++ ) | |
1406 { | |
1407 if( ( prio_cr AND grr_data->db.nc_six_strgst[i].cr_crit.c31 >= 0 ) OR | |
1408 ( !prio_cr ) ) | |
1409 { | |
1410 if( strgst EQ 0xFF OR | |
1411 grr_data->db.nc_mval_list.nc_mval[grr_data->db.nc_six_strgst[i].idx].rla_p.lev > | |
1412 grr_data->db.nc_mval_list.nc_mval[grr_data->db.nc_six_strgst[strgst].idx].rla_p.lev ) | |
1413 { | |
1414 strgst = i; | |
1415 } | |
1416 } | |
1417 } | |
1418 | |
1419 if( strgst NEQ 0xFF ) | |
1420 { | |
1421 nc_mval = &grr_data->db.nc_mval_list.nc_mval[grr_data->db.nc_six_strgst[strgst].idx]; | |
1422 | |
1423 if( nc_mval->sync_info.sync.status EQ STAT_SYNC_OK ) | |
1424 { | |
1425 ncell_info = | |
1426 grr_get_ncell_info( nc_mval->arfcn, nc_mval->sync_info.bsic ); | |
1427 | |
1428 if( ncell_info NEQ NULL ) | |
1429 { | |
1430 /* | |
1431 * if the parameter C32_QUAL is set, positive GPRS_RESELECT_OFFSET values | |
1432 * shall only be applied to the neighbour cell with the highest RLA_P value | |
1433 * of those cells for which C32 is compared. | |
1434 * | |
1435 * calculation part 2 | |
1436 */ | |
1437 | |
1438 if( p_res_off[ncell_info->cr_par.gprs_resel_off] > 0 ) | |
1439 { | |
1440 grr_data->db.nc_six_strgst[strgst].cr_crit.c32 += | |
1441 p_res_off[ncell_info->cr_par.gprs_resel_off]; | |
1442 } | |
1443 } | |
1444 } | |
1445 } | |
1446 } | |
1447 | |
1448 /* | |
1449 * perform some tracing | |
1450 */ | |
1451 | |
1452 #if !defined (NTRACE) | |
1453 | |
1454 if( grr_data->cs.v_crp_trace EQ TRUE ) | |
1455 { | |
1456 /* trace the C1 criterion */ | |
1457 for( i = grr_data->db.cnt_nc_six.strgst; i < CS_MAX_STRONG_CARRIER; i++ ) | |
1458 { | |
1459 grr_data->db.nc_six_strgst[i].cr_crit.c1 = 0; | |
1460 } | |
1461 | |
1462 TRACE_EVENT_P7 | |
1463 ( | |
1464 "C1 : %6d %6d %6d %6d %6d %6d %6d", | |
1465 grr_data->db.scell_info.cr_crit.c1, | |
1466 grr_data->db.nc_six_strgst[0].cr_crit.c1, | |
1467 grr_data->db.nc_six_strgst[1].cr_crit.c1, | |
1468 grr_data->db.nc_six_strgst[2].cr_crit.c1, | |
1469 grr_data->db.nc_six_strgst[3].cr_crit.c1, | |
1470 grr_data->db.nc_six_strgst[4].cr_crit.c1, | |
1471 grr_data->db.nc_six_strgst[5].cr_crit.c1 | |
1472 ); | |
1473 | |
1474 /* trace the C31 criterion */ | |
1475 for( i = grr_data->db.cnt_nc_six.strgst; i < CS_MAX_STRONG_CARRIER; i++ ) | |
1476 { | |
1477 grr_data->db.nc_six_strgst[i].cr_crit.c31 = 0; | |
1478 } | |
1479 | |
1480 TRACE_EVENT_P7 | |
1481 ( | |
1482 "C31 : %6d %6d %6d %6d %6d %6d %6d", | |
1483 | |
1484 grr_data->db.scell_info.cr_crit.c31, | |
1485 grr_data->db.nc_six_strgst[0].cr_crit.c31, | |
1486 grr_data->db.nc_six_strgst[1].cr_crit.c31, | |
1487 grr_data->db.nc_six_strgst[2].cr_crit.c31, | |
1488 grr_data->db.nc_six_strgst[3].cr_crit.c31, | |
1489 grr_data->db.nc_six_strgst[4].cr_crit.c31, | |
1490 grr_data->db.nc_six_strgst[5].cr_crit.c31 | |
1491 ); | |
1492 | |
1493 /* trace the C32 criterion */ | |
1494 for( i = grr_data->db.cnt_nc_six.strgst; i < CS_MAX_STRONG_CARRIER; i++ ) | |
1495 { | |
1496 grr_data->db.nc_six_strgst[i].cr_crit.c32 = 0; | |
1497 } | |
1498 | |
1499 TRACE_EVENT_P7 | |
1500 ( | |
1501 "C32 : %6d %6d %6d %6d %6d %6d %6d", | |
1502 grr_data->db.scell_info.cr_crit.c32, | |
1503 grr_data->db.nc_six_strgst[0].cr_crit.c32, | |
1504 grr_data->db.nc_six_strgst[1].cr_crit.c32, | |
1505 grr_data->db.nc_six_strgst[2].cr_crit.c32, | |
1506 grr_data->db.nc_six_strgst[3].cr_crit.c32, | |
1507 grr_data->db.nc_six_strgst[4].cr_crit.c32, | |
1508 grr_data->db.nc_six_strgst[5].cr_crit.c32 | |
1509 ); | |
1510 } | |
1511 | |
1512 #endif /* #if !defined (NTRACE) */ | |
1513 | |
1514 } /* cs_calc_params() */ | |
1515 | |
1516 /* | |
1517 +------------------------------------------------------------------------------ | |
1518 | Function : cs_store_meas_values | |
1519 +------------------------------------------------------------------------------ | |
1520 | Description : The function cs_store_meas_values() saves the received | |
1521 | rla_p values in the grr database | |
1522 | | |
1523 | Parameters : ... | |
1524 | | |
1525 +------------------------------------------------------------------------------ | |
1526 */ | |
1527 GLOBAL void cs_store_meas_values ( void ) | |
1528 { | |
1529 UBYTE i, j; /* used for counting */ | |
1530 | |
1531 USHORT arfcn; | |
1532 | |
1533 T_rla_p rla_p; | |
1534 | |
1535 TRACE_FUNCTION( "cs_store_meas_values" ); | |
1536 | |
1537 /* | |
1538 * store the first value as serving cell | |
1539 */ | |
1540 grr_data->db.scell_info.rla_p.stat = | |
1541 cs_get_rla_p( &nc_data->cell[0].rla_p_data, | |
1542 &grr_data->db.scell_info.rla_p.lev ); | |
1543 | |
1544 if( grr_data->db.scell_info.rla_p.stat NEQ CS_RLA_P_NOT_AVAIL ) | |
1545 { | |
1546 #ifdef FF_PS_RSSI | |
1547 RX_SetValue( grr_data->db.scell_info.rla_p.lev, | |
1548 RX_QUAL_UNAVAILABLE, | |
1549 psc_db->scell_par.cr_par_1.cr_pow_par.gprs_rxlev_access_min); | |
1550 #else | |
1551 RX_SetValue( grr_data->db.scell_info.rla_p.lev ); | |
1552 #endif | |
1553 } | |
1554 | |
1555 /* | |
1556 * store the next values as neighbour cells | |
1557 */ | |
1558 for( j = 1; j < nc_data->c_cell; j++ ) | |
1559 { | |
1560 i = 0; | |
1561 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
1562 arfcn = nc_data->cell[j].arfcn; | |
1563 #else | |
1564 arfcn = grr_l1_arfcn_to_g23( nc_data->cell[j].arfcn ); | |
1565 #endif | |
1566 rla_p.stat = cs_get_rla_p( &nc_data->cell[j].rla_p_data, &rla_p.lev ); | |
1567 | |
1568 while( i < MAX_NR_OF_NC_MVAL AND | |
1569 grr_data->db.nc_mval_list.nc_mval[i].arfcn NEQ arfcn ) | |
1570 | |
1571 { | |
1572 i++; | |
1573 } | |
1574 | |
1575 if( i < MAX_NR_OF_NC_MVAL ) | |
1576 { | |
1577 grr_data->db.nc_mval_list.nc_mval[i].rla_p = rla_p; | |
1578 } | |
1579 } | |
1580 } /* cs_store_meas_values() */ | |
1581 | |
1582 /* | |
1583 +------------------------------------------------------------------------------ | |
1584 | Function : cs_store_rxlev_values | |
1585 +------------------------------------------------------------------------------ | |
1586 | Description : The function cs_store_rxlev_values() | |
1587 | | |
1588 | Parameters : ... | |
1589 | | |
1590 +------------------------------------------------------------------------------ | |
1591 */ | |
1592 GLOBAL void cs_store_rxlev_values ( void ) | |
1593 { | |
1594 UBYTE i, j; /* used for counting */ | |
1595 | |
1596 USHORT arfcn; | |
1597 | |
1598 TRACE_FUNCTION( "cs_store_rxlev_values" ); | |
1599 | |
1600 /* | |
1601 * store the first value as serving cell | |
1602 */ | |
1603 grr_data->db.scell_info.rxlev_avg = | |
1604 cs_get_rxlev_avg( &nc_data->cell[0].rxlev_data ); | |
1605 | |
1606 /* | |
1607 * store the next values as neighbour cells | |
1608 */ | |
1609 for( j = 1; j < nc_data->c_cell; j++ ) | |
1610 { | |
1611 i = 0; | |
1612 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
1613 arfcn = nc_data->cell[j].arfcn; | |
1614 #else | |
1615 arfcn = grr_l1_arfcn_to_g23( nc_data->cell[j].arfcn ); | |
1616 #endif | |
1617 | |
1618 while( i < MAX_NR_OF_NC_MVAL AND | |
1619 grr_data->db.nc_mval_list.nc_mval[i].arfcn NEQ arfcn ) | |
1620 | |
1621 { | |
1622 i++; | |
1623 } | |
1624 | |
1625 if( i < MAX_NR_OF_NC_MVAL ) | |
1626 { | |
1627 grr_data->db.nc_mval_list.nc_mval[i].rxlev_avg = | |
1628 cs_get_rxlev_avg( &nc_data->cell[j].rxlev_data ); | |
1629 } | |
1630 } | |
1631 } /* cs_store_rxlev_values() */ | |
1632 | |
1633 /* | |
1634 +------------------------------------------------------------------------------ | |
1635 | Function : cs_find_strongest | |
1636 +------------------------------------------------------------------------------ | |
1637 | Description : The function cs_find_strongest() finds out the six strongest | |
1638 | neighbour cells and stores their indices in an array. | |
1639 | | |
1640 | Parameters : cnt_strgst - number of strongest carriers | |
1641 | cnt_candid - number of strongest plus candidate carriers | |
1642 | index - index of carriers | |
1643 | status - status of carriers | |
1644 | | |
1645 +------------------------------------------------------------------------------ | |
1646 */ | |
1647 GLOBAL BOOL cs_find_strongest ( ULONG fn_offset ) | |
1648 { | |
1649 UBYTE cnt_strgst; | |
1650 UBYTE cnt_candid; | |
1651 UBYTE index[CS_MAX_STRONG_CARRIER]; | |
1652 | |
1653 UBYTE max_nc_excl_sc_band = 0; /* maximum number of reported neighbour */ | |
1654 /* cells that should be not in the band */ | |
1655 /* of the serving cell */ | |
1656 | |
1657 TRACE_FUNCTION( "cs_find_strongest" ); | |
1658 | |
1659 #ifdef TI_PS_FF_QUAD_BAND_SUPPORT | |
1660 if( CHECK_DUAL_BANDS EQ TRUE) | |
1661 #else | |
1662 if( std EQ STD_DUAL OR std EQ STD_DUAL_EGSM OR std EQ STD_DUAL_US ) | |
1663 #endif | |
1664 { | |
1665 switch( psc_db->scell_par.multi_band_rep ) | |
1666 { | |
1667 case GRR_MULTIBAND_REPORTING_1: max_nc_excl_sc_band = 1; break; | |
1668 case GRR_MULTIBAND_REPORTING_2: max_nc_excl_sc_band = 2; break; | |
1669 case GRR_MULTIBAND_REPORTING_3: max_nc_excl_sc_band = 3; break; | |
1670 default : max_nc_excl_sc_band = 0; break; | |
1671 } | |
1672 } | |
1673 | |
1674 /* | |
1675 * look for strongest neighbour cells with a valid RLA_P value, | |
1676 * these are used for cell re-selection only | |
1677 */ | |
1678 cnt_strgst = 0; | |
1679 | |
1680 cs_consider_multiband | |
1681 ( &cnt_strgst, index, CS_RLA_P_VALID, max_nc_excl_sc_band ); | |
1682 | |
1683 /* | |
1684 * look for strongest neighbour cells with a RLA_P which is not valid | |
1685 * but available and add them to the remaining storage areas in the list | |
1686 * of strongest neighbour cells, these are used for checking the BSIC | |
1687 * in advance, these cells may become a valid RLA_P value soon | |
1688 */ | |
1689 cnt_candid = cnt_strgst; | |
1690 | |
1691 if( cnt_candid < CS_MAX_STRONG_CARRIER ) | |
1692 { | |
1693 cs_consider_multiband | |
1694 ( &cnt_candid, index, CS_RLA_P_NOT_VALID, max_nc_excl_sc_band ); | |
1695 } | |
1696 | |
1697 return(cs_update_strongest( cnt_strgst, cnt_candid, index, fn_offset )); | |
1698 } /* cs_find_strongest() */ | |
1699 | |
1700 /* | |
1701 +------------------------------------------------------------------------------ | |
1702 | Function : cs_consider_multiband | |
1703 +------------------------------------------------------------------------------ | |
1704 | Description : | |
1705 | | |
1706 | Parameters : | |
1707 | | |
1708 +------------------------------------------------------------------------------ | |
1709 */ | |
1710 LOCAL void cs_consider_multiband ( UBYTE *count, | |
1711 UBYTE *index, | |
1712 UBYTE select_status, | |
1713 UBYTE maximum ) | |
1714 { | |
1715 TRACE_FUNCTION( "cs_consider_multiband" ); | |
1716 | |
1717 if( maximum NEQ 0 ) | |
1718 { | |
1719 /* | |
1720 * A maximum of zero means that normal reporting of the six strongest | |
1721 * cell irrespective of the band used should be performed. | |
1722 * | |
1723 * A maximum greater zero means that multi band reporting should be | |
1724 * performed, so the MS shall report the strongest cells in each of the | |
1725 * frequency bands in the BA list, excluding the frequency band of the | |
1726 * serving cell. The remaining positions shall be used for reporting of | |
1727 * the cells in the band of the serving cell. | |
1728 */ | |
1729 cs_find_strongest_with_status | |
1730 ( count, index, select_status, maximum, CS_EXCLUDE_SC_BAND ); | |
1731 | |
1732 cs_find_strongest_with_status | |
1733 ( count, index, select_status, | |
1734 (UBYTE)( CS_MAX_STRONG_CARRIER - maximum ), CS_ONLY_SC_BAND ); | |
1735 } | |
1736 | |
1737 if( *count < CS_MAX_STRONG_CARRIER ) | |
1738 { | |
1739 cs_find_strongest_with_status | |
1740 ( count, index, select_status, | |
1741 (UBYTE)( CS_MAX_STRONG_CARRIER - *count ), CS_NO_BAND_LIMITATION ); | |
1742 } | |
1743 } /* cs_consider_multiband() */ | |
1744 | |
1745 /* | |
1746 +------------------------------------------------------------------------------ | |
1747 | Function : cs_find_strongest_with_status | |
1748 +------------------------------------------------------------------------------ | |
1749 | Description : The function cs_find_strongest_with_status() finds out the | |
1750 | six strongest neighbour cells with a specific status and | |
1751 | stores their indices in an array. | |
1752 | | |
1753 | Parameters : count - number of strongest carriers | |
1754 | index - index of carriers | |
1755 | status - status of carriers | |
1756 | select_status - status which should be used for selection | |
1757 | | |
1758 | | |
1759 +------------------------------------------------------------------------------ | |
1760 */ | |
1761 LOCAL void cs_find_strongest_with_status ( UBYTE *count, | |
1762 UBYTE *index, | |
1763 UBYTE select_status, | |
1764 UBYTE maximum, | |
1765 UBYTE limitation ) | |
1766 { | |
1767 UBYTE strgst_idx; /* used for counting */ | |
1768 UBYTE mval_idx; /* used for counting */ | |
1769 UBYTE k; /* used for counting */ | |
1770 BOOL cells_left = TRUE; /* indicates whether there are more cells */ | |
1771 /* which may belong to the strongest */ | |
1772 SHORT max_rla_p; /* next maximum RLA_P value */ | |
1773 UBYTE idx_next_max; /* index of the cell with the next max. */ | |
1774 /* RLA_P value */ | |
1775 BOOL one_of_six_flag; /* indicates whether a cell already */ | |
1776 /* belongs to the strongest */ | |
1777 BOOL limit; /* indicator for limitation precedence */ | |
1778 BOOL scell_is_high_band; /* serving cell is in DCS or PCS band */ | |
1779 BOOL ncell_is_high_band; /* neighbour cell is in DCS or PCS band */ | |
1780 UBYTE max_found_cell = MINIMUM( *count + maximum, CS_MAX_STRONG_CARRIER ); | |
1781 /* maximum number of strongest neighbour */ | |
1782 /* cells that should be found after */ | |
1783 /* leaving this function */ | |
1784 USHORT low_channel; | |
1785 USHORT high_channel; | |
1786 | |
1787 T_NC_MVAL *nc_mval; | |
1788 | |
1789 TRACE_FUNCTION( "cs_find_strongest_with_status" ); | |
1790 | |
1791 #ifdef TI_PS_FF_QUAD_BAND_SUPPORT | |
1792 if( std EQ STD_DUAL_US OR std EQ STD_900_1900 OR | |
1793 std EQ STD_850_900_1900 ) | |
1794 #else | |
1795 if( std EQ STD_DUAL_US ) | |
1796 #endif | |
1797 { | |
1798 low_channel = LOW_CHANNEL_1900; | |
1799 high_channel = HIGH_CHANNEL_1900; | |
1800 } | |
1801 else | |
1802 { | |
1803 low_channel = LOW_CHANNEL_1800; | |
1804 high_channel = HIGH_CHANNEL_1800; | |
1805 } | |
1806 | |
1807 for( strgst_idx = *count; | |
1808 strgst_idx < max_found_cell AND cells_left; | |
1809 strgst_idx++ ) | |
1810 { | |
1811 max_rla_p = -1; | |
1812 idx_next_max = 0xFF; | |
1813 | |
1814 for( mval_idx = 0; mval_idx < MAX_NR_OF_NC_MVAL; mval_idx++ ) | |
1815 { | |
1816 nc_mval = &grr_data->db.nc_mval_list.nc_mval[mval_idx]; | |
1817 | |
1818 if( nc_mval->status EQ NC_MVAL_STAT_ASSIGNED ) | |
1819 { | |
1820 one_of_six_flag = FALSE; | |
1821 | |
1822 for( k = 0; k < *count AND one_of_six_flag EQ FALSE; k++ ) | |
1823 { | |
1824 if( mval_idx EQ index[k] ) | |
1825 { | |
1826 one_of_six_flag = TRUE; | |
1827 } | |
1828 } | |
1829 | |
1830 if( one_of_six_flag EQ FALSE AND | |
1831 nc_mval->rla_p.stat EQ select_status AND | |
1832 | |
1833 #ifdef _TARGET_ | |
1834 nc_mval->rla_p.lev >= MIN_RXLEV_FOR_SIX_STRGST AND | |
1835 #endif /* #ifdef _TARGET_ */ | |
1836 | |
1837 nc_mval->rla_p.lev > max_rla_p ) | |
1838 { | |
1839 switch( limitation ) | |
1840 { | |
1841 default: | |
1842 TRACE_ASSERT( limitation EQ CS_NO_BAND_LIMITATION OR | |
1843 limitation EQ CS_EXCLUDE_SC_BAND OR | |
1844 limitation EQ CS_ONLY_SC_BAND ); | |
1845 | |
1846 /*lint -fallthrough*/ | |
1847 | |
1848 /* | |
1849 * fallthrough statement inserted to pass lint process, | |
1850 * error 644: (Warning -- limit may not have been initialized) | |
1851 */ | |
1852 | |
1853 case( CS_NO_BAND_LIMITATION ): | |
1854 limit = FALSE; | |
1855 break; | |
1856 | |
1857 case( CS_EXCLUDE_SC_BAND ): | |
1858 scell_is_high_band = | |
1859 ( psc_db->pbcch.bcch.arfcn >= low_channel AND | |
1860 psc_db->pbcch.bcch.arfcn <= high_channel ); | |
1861 | |
1862 ncell_is_high_band = | |
1863 ( nc_mval->arfcn >= low_channel AND | |
1864 nc_mval->arfcn <= high_channel ); | |
1865 | |
1866 limit = ( scell_is_high_band EQ ncell_is_high_band ); | |
1867 break; | |
1868 | |
1869 case( CS_ONLY_SC_BAND ): | |
1870 scell_is_high_band = | |
1871 ( psc_db->pbcch.bcch.arfcn >= low_channel AND | |
1872 psc_db->pbcch.bcch.arfcn <= high_channel ); | |
1873 | |
1874 ncell_is_high_band = | |
1875 ( nc_mval->arfcn >= low_channel AND | |
1876 nc_mval->arfcn <= high_channel ); | |
1877 | |
1878 limit = ( scell_is_high_band NEQ ncell_is_high_band ); | |
1879 break; | |
1880 } | |
1881 | |
1882 /* | |
1883 * limitation may take precedence, | |
1884 * do not consider neighbour cell in case | |
1885 */ | |
1886 if( limit EQ FALSE ) | |
1887 { | |
1888 max_rla_p = nc_mval->rla_p.lev; | |
1889 idx_next_max = mval_idx; | |
1890 } | |
1891 } | |
1892 } | |
1893 } | |
1894 | |
1895 if( idx_next_max EQ 0xFF ) | |
1896 { | |
1897 cells_left = FALSE; | |
1898 } | |
1899 else | |
1900 { | |
1901 index[strgst_idx] = idx_next_max; | |
1902 | |
1903 (*count)++; | |
1904 } | |
1905 } | |
1906 } /* cs_find_strongest_with_status() */ | |
1907 | |
1908 /* | |
1909 +------------------------------------------------------------------------------ | |
1910 | Function : cs_update_strongest | |
1911 +------------------------------------------------------------------------------ | |
1912 | Description : The function cs_update_strongest() updates the list of the | |
1913 | strongest neighbour cells stored in the database. | |
1914 | | |
1915 | Parameters : cnt_strgst - number of strongest carriers | |
1916 | cnt_candid - number of strongest plus candidate carriers | |
1917 | index - index of carriers | |
1918 | status - status of carriers | |
1919 | fn_offset - frame number offset | |
1920 | | |
1921 +------------------------------------------------------------------------------ | |
1922 */ | |
1923 LOCAL BOOL cs_update_strongest ( UBYTE cnt_strgst, | |
1924 UBYTE cnt_candid, | |
1925 UBYTE *index, | |
1926 ULONG fn_offset ) | |
1927 { | |
1928 UBYTE i, j; /* used for counting */ | |
1929 ULONG avail_time[CS_MAX_STRONG_CARRIER]; | |
1930 /* used to store the times when a cell becomes first */ | |
1931 /* a cell of the strongest carriers for a possible */ | |
1932 /* rearrangment of the list of the strongest carriers */ | |
1933 | |
1934 T_NC_SIX_STRGST *six_strgst; | |
1935 T_NC_SIX_STRGST *six_candid; | |
1936 | |
1937 BOOL has_changed = ( grr_data->db.cnt_nc_six.candid NEQ cnt_candid ); | |
1938 | |
1939 | |
1940 TRACE_FUNCTION( "cs_update_strongest" ); | |
1941 | |
1942 memset( avail_time, 0, sizeof( avail_time ) ); | |
1943 | |
1944 for( i = 0; i < cnt_candid; i++ ) | |
1945 { | |
1946 /* | |
1947 * check whether cell is already inserted in list of strongest carrier | |
1948 */ | |
1949 six_strgst = NULL; | |
1950 six_candid = NULL; | |
1951 j = 0; | |
1952 | |
1953 while( j < grr_data->db.cnt_nc_six.candid AND | |
1954 six_strgst EQ NULL AND | |
1955 six_candid EQ NULL ) | |
1956 { | |
1957 six_candid = &grr_data->db.nc_six_strgst[j]; | |
1958 | |
1959 if( index[i] EQ six_candid->idx ) | |
1960 { | |
1961 if( j < grr_data->db.cnt_nc_six.strgst ) | |
1962 { | |
1963 six_strgst = six_candid; | |
1964 } | |
1965 } | |
1966 else | |
1967 { | |
1968 six_candid = NULL; | |
1969 | |
1970 j++; | |
1971 } | |
1972 } | |
1973 | |
1974 | |
1975 if( six_strgst NEQ NULL ) | |
1976 { | |
1977 if( six_strgst->avail_time <= | |
1978 ( GPRS_PENALTY_TIME_MAX + 1 ) * 10 * CS_PERIOD_1_SEC ) | |
1979 { | |
1980 /* | |
1981 * the time how long the cell is already inserted | |
1982 * is stored up to a limited period | |
1983 */ | |
1984 avail_time[i] = six_strgst->avail_time + fn_offset; | |
1985 } | |
1986 else | |
1987 { | |
1988 avail_time[i] = six_strgst->avail_time; | |
1989 } | |
1990 } | |
1991 else | |
1992 { | |
1993 if( six_candid EQ NULL ) | |
1994 { | |
1995 has_changed = TRUE; | |
1996 } | |
1997 | |
1998 if( grr_data->db.old_scell.arfcn EQ | |
1999 grr_data->db.nc_mval_list.nc_mval[index[i]].arfcn AND | |
2000 grr_data->db.old_scell.bsic EQ | |
2001 grr_data->db.nc_mval_list.nc_mval[index[i]].sync_info.bsic ) | |
2002 { | |
2003 /* for the old serving cell timer T shall always set to status expired */ | |
2004 avail_time[i] = | |
2005 ( ( GPRS_PENALTY_TIME_MAX + 1 ) * 10 * CS_PERIOD_1_SEC ) + 1; | |
2006 } | |
2007 | |
2008 } | |
2009 } | |
2010 | |
2011 for( i = 0; i < cnt_candid; i++ ) | |
2012 { | |
2013 grr_data->db.nc_six_strgst[i].idx = index[i]; | |
2014 grr_data->db.nc_six_strgst[i].avail_time = avail_time[i]; | |
2015 | |
2016 /* | |
2017 * every time a new list of strongest carriers is build-up | |
2018 * the parameter mode should be set to CS_MODE_IDLE. | |
2019 */ | |
2020 grr_data->db.nc_six_strgst[i].mode = CS_MODE_IDLE; | |
2021 } | |
2022 | |
2023 cs_set_cnt_nc_six( cnt_strgst, cnt_candid ); | |
2024 | |
2025 /* | |
2026 * perform some tracing | |
2027 */ | |
2028 | |
2029 #if !defined (NTRACE) | |
2030 | |
2031 if( grr_data->cs.v_crp_trace EQ TRUE ) | |
2032 { | |
2033 /* trace the ARFCN */ | |
2034 { | |
2035 USHORT arfcn[CS_MAX_STRONG_CARRIER]; | |
2036 | |
2037 memset( arfcn, RRGRR_INVALID_ARFCN, sizeof( arfcn ) ); | |
2038 | |
2039 for( i = 0; i < grr_data->db.cnt_nc_six.candid; i++ ) | |
2040 { | |
2041 arfcn[i] = | |
2042 grr_data->db.nc_mval_list.nc_mval[grr_data->db.nc_six_strgst[i].idx].arfcn; | |
2043 } | |
2044 | |
2045 TRACE_EVENT_P7 | |
2046 ( | |
2047 "ARFCN: %6d %6d %6d %6d %6d %6d %6d", | |
2048 psc_db->pbcch.bcch.arfcn, | |
2049 arfcn[0], arfcn[1], arfcn[2], arfcn[3], arfcn[4], arfcn[5] | |
2050 ); | |
2051 } | |
2052 | |
2053 /* trace the BSIC */ | |
2054 { | |
2055 USHORT bsic[CS_MAX_STRONG_CARRIER]; | |
2056 | |
2057 memset( bsic, RRGRR_INVALID_BSIC, sizeof( bsic ) ); | |
2058 | |
2059 for( i = 0; i < grr_data->db.cnt_nc_six.candid; i++ ) | |
2060 { | |
2061 bsic[i] = | |
2062 grr_data->db.nc_mval_list.nc_mval[grr_data->db.nc_six_strgst[i].idx].sync_info.bsic; | |
2063 } | |
2064 | |
2065 TRACE_EVENT_P7 | |
2066 ( | |
2067 "BSIC : %6d %6d %6d %6d %6d %6d %6d", | |
2068 psc_db->pbcch.bcch.bsic, | |
2069 bsic[0], bsic[1], bsic[2], bsic[3], bsic[4], bsic[5] | |
2070 ); | |
2071 } | |
2072 | |
2073 /* trace the RLA_P */ | |
2074 { | |
2075 UBYTE rla_p[CS_MAX_STRONG_CARRIER]; | |
2076 UBYTE rxlev_avg[CS_MAX_STRONG_CARRIER]; | |
2077 | |
2078 memset( rla_p, 0, sizeof( rla_p ) ); | |
2079 memset( rxlev_avg, 0, sizeof( rxlev_avg ) ); | |
2080 | |
2081 for( i = 0; i < grr_data->db.cnt_nc_six.candid; i++ ) | |
2082 { | |
2083 rla_p[i] = | |
2084 grr_data->db.nc_mval_list.nc_mval[grr_data->db.nc_six_strgst[i].idx].rla_p.lev; | |
2085 | |
2086 | |
2087 rxlev_avg[i] = | |
2088 grr_data->db.nc_mval_list.nc_mval[grr_data->db.nc_six_strgst[i].idx].rxlev_avg; | |
2089 | |
2090 } | |
2091 | |
2092 TRACE_EVENT_P7 | |
2093 ( | |
2094 "RLA_P: %6d %6d %6d %6d %6d %6d %6d", | |
2095 grr_data->db.scell_info.rla_p.lev, | |
2096 rla_p[0], rla_p[1], rla_p[2], rla_p[3], rla_p[4], rla_p[5] | |
2097 ); | |
2098 | |
2099 TRACE_EVENT_P7 | |
2100 ( | |
2101 "RXLEV_AVG: %6d %6d %6d %6d %6d %6d %6d", | |
2102 grr_data->db.scell_info.rxlev_avg, | |
2103 rxlev_avg[0], rxlev_avg[1], rxlev_avg[2], rxlev_avg[3], rxlev_avg[4], rxlev_avg[5] | |
2104 ); | |
2105 | |
2106 } | |
2107 | |
2108 /* trace the synchronisation status */ | |
2109 { | |
2110 UBYTE sync_stat[CS_MAX_STRONG_CARRIER]; | |
2111 | |
2112 memset( sync_stat, 0xFF, sizeof( sync_stat ) ); | |
2113 | |
2114 for( i = 0; i < grr_data->db.cnt_nc_six.candid; i++ ) | |
2115 { | |
2116 sync_stat[i] = | |
2117 grr_data->db.nc_mval_list.nc_mval[grr_data->db.nc_six_strgst[i].idx].sync_info.sync.status; | |
2118 } | |
2119 | |
2120 TRACE_EVENT_P6 | |
2121 ( | |
2122 "SYNC : %6d %6d %6d %6d %6d %6d", | |
2123 sync_stat[0], sync_stat[1], sync_stat[2], | |
2124 sync_stat[3], sync_stat[4], sync_stat[5] | |
2125 ); | |
2126 } | |
2127 } | |
2128 | |
2129 #endif /* #if !defined (NTRACE) */ | |
2130 | |
2131 return( has_changed ); | |
2132 | |
2133 } /* cs_update_strongest() */ | |
2134 | |
2135 /* | |
2136 +------------------------------------------------------------------------------ | |
2137 | Function : cs_compare_bsic | |
2138 +------------------------------------------------------------------------------ | |
2139 | Description : The function cs_compare_bsic() compares the indicated BSIC | |
2140 | with the stored BSICs | |
2141 | | |
2142 | Parameters : rrgrr_check_bsic_ind - pointer to primitive | |
2143 | | |
2144 +------------------------------------------------------------------------------ | |
2145 */ | |
2146 GLOBAL void cs_compare_bsic ( T_RRGRR_NCELL_SYNC_IND *rrgrr_check_bsic_ind ) | |
2147 { | |
2148 UBYTE i = 0; | |
2149 UBYTE j; | |
2150 UBYTE nc_mval_idx; | |
2151 T_NC_MVAL *nc_mval; | |
2152 | |
2153 | |
2154 TRACE_FUNCTION( "cs_compare_bsic" ); | |
2155 | |
2156 | |
2157 | |
2158 while( i < RRGRR_MAX_RSLT_NCELL_SYNC_IND AND | |
2159 rrgrr_check_bsic_ind->sync_result[i].arfcn NEQ RRGRR_INVALID_ARFCN ) | |
2160 { | |
2161 if( ( nc_mval = grr_get_nc_mval( rrgrr_check_bsic_ind->sync_result[i].arfcn, | |
2162 RRGRR_INVALID_BSIC, &nc_mval_idx ) ) NEQ NULL ) | |
2163 { | |
2164 switch( rrgrr_check_bsic_ind->sync_result[i].sb_flag ) | |
2165 { | |
2166 case( SB_FOUND ): | |
2167 nc_mval->sync_info.bsic = rrgrr_check_bsic_ind->sync_result[i].bsic; | |
2168 nc_mval->sync_info.sync.status = STAT_SYNC_OK; | |
2169 nc_mval->sync_info.sync.sync_failed_cnt = 0; | |
2170 break; | |
2171 | |
2172 case( NO_SB_FOUND ): | |
2173 nc_mval->sync_info.bsic = RRGRR_INVALID_BSIC; | |
2174 | |
2175 if( nc_mval->sync_info.sync.sync_failed_cnt EQ MAX_SYNC_FAILED_CNT ) | |
2176 { | |
2177 nc_mval->sync_info.sync.status = STAT_SYNC_NONE; | |
2178 nc_mval->sync_info.sync.sync_failed_cnt = 0; | |
2179 | |
2180 j=0; | |
2181 while( j < grr_data->nc_data.c_cell AND | |
2182 grr_data->nc_data.cell[j].arfcn NEQ | |
2183 nc_mval->arfcn ) | |
2184 { | |
2185 j++; | |
2186 } | |
2187 | |
2188 if( j < grr_data->nc_data.c_cell ) | |
2189 { | |
2190 cs_reset_meas_result( &grr_data->nc_data.cell[j] ); | |
2191 } | |
2192 | |
2193 } | |
2194 else | |
2195 { | |
2196 nc_mval->sync_info.sync.status = STAT_SYNC_FAILED; | |
2197 nc_mval->sync_info.sync.sync_failed_cnt += 1; | |
2198 } | |
2199 break; | |
2200 | |
2201 case( SB_UNKNOWN ): | |
2202 if( nc_mval->status EQ NC_MVAL_STAT_PENDING ) | |
2203 { | |
2204 cs_init_nc_mval( nc_mval ); | |
2205 } | |
2206 else | |
2207 { | |
2208 nc_mval->sync_info.bsic = RRGRR_INVALID_BSIC; | |
2209 nc_mval->sync_info.sync.status = STAT_SYNC_NONE; | |
2210 nc_mval->sync_info.sync.sync_failed_cnt = 0; | |
2211 } | |
2212 break; | |
2213 } | |
2214 } | |
2215 | |
2216 if( nc_mval EQ NULL ) | |
2217 { | |
2218 if( ( nc_mval = grr_get_nc_mval( RRGRR_INVALID_ARFCN, | |
2219 RRGRR_INVALID_BSIC, | |
2220 &nc_mval_idx ) ) NEQ NULL ) | |
2221 { | |
2222 switch( rrgrr_check_bsic_ind->sync_result[i].sb_flag ) | |
2223 { | |
2224 case( SB_FOUND ): | |
2225 nc_mval->status = NC_MVAL_STAT_PENDING; | |
2226 nc_mval->arfcn = rrgrr_check_bsic_ind->sync_result[i].arfcn; | |
2227 nc_mval->sync_info.bsic = rrgrr_check_bsic_ind->sync_result[i].bsic; | |
2228 nc_mval->sync_info.sync.status = STAT_SYNC_OK; | |
2229 nc_mval->sync_info.sync.sync_failed_cnt = 0; | |
2230 | |
2231 grr_data->cs.is_mval_initialized = FALSE; | |
2232 break; | |
2233 | |
2234 case( NO_SB_FOUND ): | |
2235 nc_mval->status = NC_MVAL_STAT_PENDING; | |
2236 nc_mval->arfcn = rrgrr_check_bsic_ind->sync_result[i].arfcn; | |
2237 nc_mval->sync_info.bsic = RRGRR_INVALID_BSIC; | |
2238 nc_mval->sync_info.sync.status = STAT_SYNC_FAILED; | |
2239 nc_mval->sync_info.sync.sync_failed_cnt = 0; | |
2240 | |
2241 grr_data->cs.is_mval_initialized = FALSE; | |
2242 break; | |
2243 | |
2244 case( SB_UNKNOWN ): | |
2245 TRACE_EVENT_P1( "cs_compare_bsic: SB_UNKNOWN for %d which is not on measured values list, e.g. after GRR suspension", | |
2246 rrgrr_check_bsic_ind->sync_result[i].arfcn ); | |
2247 break; | |
2248 } | |
2249 } | |
2250 else | |
2251 { | |
2252 TRACE_EVENT_P1( "cs_compare_bsic: no free entry for measured values found %d", | |
2253 rrgrr_check_bsic_ind->sync_result[i].arfcn ); | |
2254 } | |
2255 } | |
2256 | |
2257 #ifdef _SIMULATION_ | |
2258 | |
2259 TRACE_EVENT_P3( "BSIC: %d %d %d", | |
2260 rrgrr_check_bsic_ind->sync_result[i].arfcn, | |
2261 rrgrr_check_bsic_ind->sync_result[i].sb_flag, | |
2262 rrgrr_check_bsic_ind->sync_result[i].bsic ); | |
2263 | |
2264 #endif /* #ifdef _SIMULATION_ */ | |
2265 | |
2266 i++; | |
2267 } | |
2268 | |
2269 cs_trace_nc_mval_lst( ); | |
2270 | |
2271 } /* cs_compare_bsic() */ | |
2272 | |
2273 | |
2274 | |
2275 | |
2276 /* | |
2277 +------------------------------------------------------------------------------ | |
2278 | Function : cs_get_best_cell | |
2279 +------------------------------------------------------------------------------ | |
2280 | Description : The function cs_get_best_cell() checks the start of | |
2281 | cell reselection. | |
2282 | Is a criterion fulfilled for cell reselction, then reading of | |
2283 | best neighbourcell is started. | |
2284 | | |
2285 | Parameters : | |
2286 | | |
2287 +------------------------------------------------------------------------------ | |
2288 */ | |
2289 GLOBAL void cs_get_best_cell ( T_NC_SIX_STRGST **nc, T_scell_info **sc ) | |
2290 { | |
2291 UBYTE strgst_idx; | |
2292 UBYTE i; | |
2293 T_NC_SIX_STRGST *next_cell; | |
2294 BOOL c31_bc; /* best neighbour cell priorized */ | |
2295 BOOL c31_nc; /* next neighbour cell priorized */ | |
2296 BOOL c31_sc; /* serving cell priorized */ | |
2297 T_ncell_info *ncell_best; /* best neighbour cell */ | |
2298 T_ncell_info *ncell_next; /* next neighbour cell */ | |
2299 T_NC_MVAL *mval_best; /* measured values for best neighbour cell */ | |
2300 T_NC_MVAL *mval_next; /* measured values for next neighbour cell */ | |
2301 | |
2302 TRACE_FUNCTION( "cs_get_best_cell" ); | |
2303 | |
2304 /* | |
2305 * start cell reselection if: | |
2306 * | |
2307 * 1. C1 for the serving cell falls below zero: C1 < 0 | |
2308 * | |
2309 * 2. A non-serving cell is evaluated to be better than the serving cell. | |
2310 * | |
2311 * a) The best cell is the cell with the highest value of C32 among those | |
2312 * cells that have the highest PRIOROTY_CLASS among those that fulfill | |
2313 * the criterion C31 >= 0. | |
2314 * | |
2315 * Interpretation: If C31 is fulfilled, take cells with highest | |
2316 * priority and then select the cell with highest | |
2317 * C32 value. | |
2318 * | |
2319 * b) The best cell is the cell with the highest value of C32 among all | |
2320 * cells if no cell fulfill the criterion C31 >= 0. | |
2321 * | |
2322 * Interpretation: If C31 is not fulfilled, take the cell with the | |
2323 * highest C32 value. | |
2324 * | |
2325 * NOTE: When selecting a neighbour cell to be the new serving cell, | |
2326 * C1 criterion of that cell shall be taken into account. | |
2327 */ | |
2328 | |
2329 /* | |
2330 * set default results | |
2331 */ | |
2332 *sc = NULL; | |
2333 *nc = NULL; | |
2334 mval_best = NULL; | |
2335 strgst_idx = 0xFF; | |
2336 | |
2337 if( grr_data->cs.is_upd_ncell_stat_needed ) | |
2338 { | |
2339 TRACE_EVENT( "cs_get_best_cell: is_upd_ncell_stat_needed EQ TRUE" ); | |
2340 | |
2341 return; | |
2342 } | |
2343 | |
2344 if( | |
2345 ( | |
2346 grr_data->db.scell_info.rla_p.stat NEQ CS_RLA_P_VALID | |
2347 ) | |
2348 OR | |
2349 ( | |
2350 grr_data->db.scell_info.rla_p.stat EQ CS_RLA_P_VALID AND | |
2351 grr_data->db.scell_info.cr_crit.c1 >= 0 AND | |
2352 grr_data->db.scell_info.cell_barred EQ FALSE | |
2353 ) | |
2354 ) | |
2355 { | |
2356 *sc = &grr_data->db.scell_info; | |
2357 } | |
2358 | |
2359 /* | |
2360 * search the best neighbour cell, | |
2361 * this cell should not be used for a cell re-selection attempt before | |
2362 */ | |
2363 for( i = 0; | |
2364 i < grr_data->db.cnt_nc_six.strgst AND *nc EQ NULL; | |
2365 i++ ) | |
2366 { | |
2367 *nc = &grr_data->db.nc_six_strgst[i]; | |
2368 mval_best = &grr_data->db.nc_mval_list.nc_mval[(*nc)->idx]; | |
2369 strgst_idx = i; | |
2370 | |
2371 if( (*nc)->mode NEQ CS_MODE_IDLE OR | |
2372 mval_best->sync_info.sync.status NEQ STAT_SYNC_OK OR | |
2373 (*nc)->cr_crit.c1 < 0 ) | |
2374 { | |
2375 *nc = NULL; | |
2376 mval_best = NULL; | |
2377 strgst_idx = 0xFF; | |
2378 } | |
2379 } | |
2380 | |
2381 /* | |
2382 * if no best neighbour cell was found inform the caller | |
2383 */ | |
2384 if( *nc EQ NULL OR mval_best EQ NULL ) | |
2385 { | |
2386 return; | |
2387 } | |
2388 | |
2389 ncell_best = | |
2390 grr_get_ncell_info( mval_best->arfcn, mval_best->sync_info.bsic ); | |
2391 | |
2392 if( ncell_best EQ NULL ) | |
2393 { | |
2394 TRACE_EVENT( "cs_get_best_cell: ncell_best EQ NULL" ); | |
2395 *nc = NULL; | |
2396 strgst_idx = 0xFF; | |
2397 | |
2398 return; | |
2399 } | |
2400 | |
2401 /* | |
2402 * check whether best neighbour cell is priorized | |
2403 */ | |
2404 c31_bc = ( (*nc)->cr_crit.c31 >= 0 AND | |
2405 ncell_best->cr_par.cr_par_1.v_hcs_par EQ TRUE ); | |
2406 | |
2407 #if !defined (NTRACE) | |
2408 | |
2409 if( grr_data->cs.v_crp_trace EQ TRUE ) | |
2410 { | |
2411 TRACE_EVENT_P4( "cs_get_best_cell: ncell_best %d %d %d %d", | |
2412 mval_best->arfcn, | |
2413 mval_best->sync_info.bsic, | |
2414 c31_bc, | |
2415 ncell_best->cr_par.cr_par_1.hcs_par.gprs_prio_class ); | |
2416 } | |
2417 | |
2418 #endif /* #if !defined (NTRACE) */ | |
2419 | |
2420 /* | |
2421 * look for a better neighbour cell | |
2422 */ | |
2423 for( i = 0; i < grr_data->db.cnt_nc_six.strgst; i++ ) | |
2424 { | |
2425 next_cell = &grr_data->db.nc_six_strgst[i]; | |
2426 mval_next = &grr_data->db.nc_mval_list.nc_mval[next_cell->idx]; | |
2427 | |
2428 if( next_cell->mode EQ CS_MODE_IDLE AND | |
2429 next_cell NEQ *nc AND | |
2430 mval_next->sync_info.sync.status EQ STAT_SYNC_OK AND | |
2431 next_cell->cr_crit.c1 >= 0 ) | |
2432 { | |
2433 ncell_next = | |
2434 grr_get_ncell_info( mval_next->arfcn, mval_next->sync_info.bsic ); | |
2435 | |
2436 if( ncell_next EQ NULL ) | |
2437 { | |
2438 TRACE_EVENT( "cs_get_best_cell: ncell_next EQ NULL" ); | |
2439 | |
2440 *nc = NULL; | |
2441 strgst_idx = 0xFF; | |
2442 | |
2443 return; | |
2444 } | |
2445 | |
2446 /* | |
2447 * check whether next neighbour cell is priorized | |
2448 */ | |
2449 c31_nc = ( next_cell->cr_crit.c31 >= 0 AND | |
2450 ncell_next->cr_par.cr_par_1.v_hcs_par EQ TRUE ); | |
2451 | |
2452 #if !defined (NTRACE) | |
2453 | |
2454 if( grr_data->cs.v_crp_trace EQ TRUE ) | |
2455 { | |
2456 TRACE_EVENT_P4( "cs_get_best_cell: ncell_next %d %d %d %d", | |
2457 mval_next->arfcn, | |
2458 mval_next->sync_info.bsic, | |
2459 c31_nc, | |
2460 ncell_next->cr_par.cr_par_1.hcs_par.gprs_prio_class ); | |
2461 } | |
2462 | |
2463 #endif /* #if !defined (NTRACE) */ | |
2464 | |
2465 if( c31_bc AND | |
2466 c31_nc AND | |
2467 ( | |
2468 ( ncell_next->cr_par.cr_par_1.hcs_par.gprs_prio_class EQ | |
2469 ncell_best->cr_par.cr_par_1.hcs_par.gprs_prio_class AND | |
2470 next_cell->cr_crit.c32 > (*nc)->cr_crit.c32 ) | |
2471 OR | |
2472 ( ncell_next->cr_par.cr_par_1.hcs_par.gprs_prio_class > | |
2473 ncell_best->cr_par.cr_par_1.hcs_par.gprs_prio_class ) | |
2474 ) | |
2475 ) | |
2476 { | |
2477 /* | |
2478 * priorized cell reselection must be done | |
2479 */ | |
2480 *nc = next_cell; | |
2481 ncell_best = ncell_next; | |
2482 strgst_idx = i; | |
2483 } | |
2484 else if ( !c31_bc ) | |
2485 { | |
2486 /* | |
2487 * check whether next neighbour cell is priorized | |
2488 */ | |
2489 if( c31_nc ) | |
2490 { | |
2491 /* | |
2492 * first priorized cell found | |
2493 */ | |
2494 c31_bc = TRUE; | |
2495 *nc = next_cell; | |
2496 ncell_best = ncell_next; | |
2497 strgst_idx = i; | |
2498 } | |
2499 else if ( next_cell->cr_crit.c32 > (*nc)->cr_crit.c32 ) | |
2500 { | |
2501 /* | |
2502 * until now, no priorized cell found | |
2503 */ | |
2504 *nc = next_cell; | |
2505 ncell_best = ncell_next; | |
2506 strgst_idx = i; | |
2507 } | |
2508 } | |
2509 } | |
2510 } | |
2511 | |
2512 /* | |
2513 * check whether serving cell is priorized | |
2514 */ | |
2515 c31_sc = ( grr_data->db.scell_info.cr_crit.c31 >= 0 AND | |
2516 psc_db->scell_par.cr_par_1.v_hcs_par EQ TRUE ); | |
2517 | |
2518 #if !defined (NTRACE) | |
2519 | |
2520 if( grr_data->cs.v_crp_trace EQ TRUE ) | |
2521 { | |
2522 TRACE_EVENT_P3( "cs_get_best_cell: scell %d %d %d", | |
2523 *sc, c31_sc, | |
2524 psc_db->scell_par.cr_par_1.hcs_par.gprs_prio_class ); | |
2525 } | |
2526 | |
2527 #endif /* #if !defined (NTRACE) */ | |
2528 | |
2529 /* | |
2530 * check whether cell reselection must be done | |
2531 */ | |
2532 if( | |
2533 ( | |
2534 *sc EQ NULL | |
2535 ) | |
2536 OR | |
2537 ( | |
2538 c31_bc AND | |
2539 c31_sc AND | |
2540 ( | |
2541 ( ncell_best->cr_par.cr_par_1.hcs_par.gprs_prio_class EQ | |
2542 psc_db->scell_par.cr_par_1.hcs_par.gprs_prio_class AND | |
2543 (*nc)->cr_crit.c32 > grr_data->db.scell_info.cr_crit.c32 ) | |
2544 OR | |
2545 ( ncell_best->cr_par.cr_par_1.hcs_par.gprs_prio_class > | |
2546 psc_db->scell_par.cr_par_1.hcs_par.gprs_prio_class ) | |
2547 ) | |
2548 ) | |
2549 OR | |
2550 ( | |
2551 !c31_bc AND | |
2552 !c31_sc AND | |
2553 (*nc)->cr_crit.c32 > grr_data->db.scell_info.cr_crit.c32 | |
2554 ) | |
2555 OR | |
2556 ( | |
2557 c31_bc AND | |
2558 !c31_sc | |
2559 ) | |
2560 ) | |
2561 { | |
2562 *sc = NULL; | |
2563 } | |
2564 else | |
2565 { | |
2566 *nc = NULL; | |
2567 strgst_idx = 0xFF; | |
2568 } | |
2569 | |
2570 #if !defined (NTRACE) | |
2571 | |
2572 if( grr_data->cs.v_crp_trace EQ TRUE ) | |
2573 { | |
2574 TRACE_EVENT_P3( "cs_get_best_cell: strong/candid %d %d %d", | |
2575 grr_data->db.cnt_nc_six.strgst, | |
2576 grr_data->db.cnt_nc_six.candid, | |
2577 strgst_idx ); | |
2578 } | |
2579 | |
2580 #endif /* #if !defined (NTRACE) */ | |
2581 | |
2582 } /* cs_get_best_cell() */ | |
2583 | |
2584 | |
2585 /* | |
2586 +------------------------------------------------------------------------------ | |
2587 | Function : cs_get_network_ctrl_order | |
2588 +------------------------------------------------------------------------------ | |
2589 | Description : The NETWORK_CONTROL_ORDER values NC1 and NC2 shall only apply | |
2590 | in Ready state. In Standby state, the MS shall always use | |
2591 | normal MS control independent of the ordered NC mode. | |
2592 | | |
2593 | Parameters : | |
2594 | | |
2595 +------------------------------------------------------------------------------ | |
2596 */ | |
2597 GLOBAL T_NC_ORDER cs_get_network_ctrl_order ( BOOL consider_gmm_state ) | |
2598 { | |
2599 T_NC_ORDER ctrl_order = NC_NC0; | |
2600 | |
2601 TRACE_FUNCTION( "cs_get_network_ctrl_order" ); | |
2602 | |
2603 if( grr_data->nc2_on ) | |
2604 { | |
2605 if( | |
2606 ( | |
2607 ( | |
2608 consider_gmm_state EQ TRUE AND | |
2609 grr_data->cs.gmm_state EQ READY_STATE | |
2610 ) | |
2611 OR | |
2612 ( | |
2613 consider_gmm_state EQ FALSE | |
2614 ) | |
2615 ) | |
2616 AND | |
2617 ( | |
2618 grr_data->db.nc_ref_lst.param NEQ NULL | |
2619 ) | |
2620 ) | |
2621 { | |
2622 ctrl_order = grr_data->db.nc_ref_lst.param->ctrl_order; | |
2623 } | |
2624 } | |
2625 | |
2626 #ifdef _SIMULATION_ | |
2627 | |
2628 TRACE_EVENT_P2( "NETWORK_CONTROL_ORDER: %d, GMM_STATE: %d", | |
2629 grr_data->db.nc_ref_lst.param EQ NULL ? | |
2630 ctrl_order : grr_data->db.nc_ref_lst.param->ctrl_order, | |
2631 grr_data->cs.gmm_state ); | |
2632 | |
2633 #endif /* #ifdef _SIMULATION_ */ | |
2634 | |
2635 return( ctrl_order ); | |
2636 | |
2637 } /* cs_get_network_ctrl_order() */ | |
2638 | |
2639 /* | |
2640 +------------------------------------------------------------------------------ | |
2641 | Function : cs_reset_nc_change_mark | |
2642 +------------------------------------------------------------------------------ | |
2643 | Description : | |
2644 | | |
2645 | Parameters : void | |
2646 | | |
2647 +------------------------------------------------------------------------------ | |
2648 */ | |
2649 GLOBAL void cs_reset_nc_change_mark ( T_SC_DATABASE *db ) | |
2650 { | |
2651 TRACE_FUNCTION( "cs_reset_nc_change_mark" ); | |
2652 | |
2653 db->nc_cw.list.chng_mrk.curr = 0; | |
2654 db->nc_cw.list.chng_mrk.prev = 0; | |
2655 db->nc_cw.param.chng_mrk.curr = 0; | |
2656 db->nc_cw.param.chng_mrk.prev = 0; | |
2657 db->nc_ms.ncmeas.list.chng_mrk.curr = 0; | |
2658 db->nc_ms.ncmeas.list.chng_mrk.prev = 0; | |
2659 db->nc_ms.ncmeas.param.chng_mrk.curr = 0; | |
2660 db->nc_ms.ncmeas.param.chng_mrk.prev = 0; | |
2661 | |
2662 } /* cs_reset_nc_change_mark() */ | |
2663 | |
2664 /* | |
2665 +------------------------------------------------------------------------------ | |
2666 | Function : cs_get_cr_meas_mode | |
2667 +------------------------------------------------------------------------------ | |
2668 | Description : The function cs_get_cr_meas_mode() returns the cell | |
2669 | re-selection measurement mode used in context of TBF | |
2670 | establishment. | |
2671 | | |
2672 | Parameters : void | |
2673 | | |
2674 +------------------------------------------------------------------------------ | |
2675 */ | |
2676 GLOBAL UBYTE cs_get_cr_meas_mode ( void ) | |
2677 { | |
2678 TRACE_FUNCTION( "cs_get_cr_meas_mode" ); | |
2679 | |
2680 return( grr_is_pbcch_present() ? CS_CRMM_BA_GPRS : CS_CRMM_BA_BCCH ); | |
2681 } /* cs_get_cr_meas_mode() */ | |
2682 | |
2683 /* | |
2684 +------------------------------------------------------------------------------ | |
2685 | Function : cs_send_cr_meas_req | |
2686 +------------------------------------------------------------------------------ | |
2687 | Description : The function cs_send_cr_meas_req() sends the cell reselection | |
2688 | measurement request to L1 (MPHP_CR_MEAS_REQ) | |
2689 | | |
2690 | Parameters : dummy - description of parameter dummy | |
2691 | | |
2692 +------------------------------------------------------------------------------ | |
2693 */ | |
2694 GLOBAL void cs_send_cr_meas_req ( UBYTE del_meas_rslt ) | |
2695 { | |
2696 BOOL is_pbcch_present = grr_is_pbcch_present( ); | |
2697 UBYTE i, j,number_of_frequencies; | |
2698 BOOL is_existing; | |
2699 BOOL v_cs_par[MAX_NR_OF_NCELL]; | |
2700 T_NC_ORDER nc_ord = cs_get_network_ctrl_order( TRUE ); | |
2701 T_NC_REF_LIST *nc_list = &grr_data->db.nc_ref_lst; | |
2702 | |
2703 TRACE_FUNCTION( "cs_send_cr_meas_req" ); | |
2704 | |
2705 { | |
2706 /* | |
2707 * first value represents the arfcn of the serving cell | |
2708 */ | |
2709 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
2710 grr_data->nc_data.cell[0].arfcn = psc_db->pbcch.bcch.arfcn; | |
2711 #else | |
2712 grr_data->nc_data.cell[0].arfcn = grr_g23_arfcn_to_l1( psc_db->pbcch.bcch.arfcn ); | |
2713 #endif | |
2714 number_of_frequencies = 1; | |
2715 | |
2716 memset( v_cs_par, ( is_pbcch_present ? FALSE : TRUE ), sizeof( v_cs_par ) ); | |
2717 | |
2718 for( i = 0; i < nc_list->number; i++ ) | |
2719 { | |
2720 if( is_pbcch_present ) | |
2721 { | |
2722 v_cs_par[i] |= nc_list->info[i]->v_cr_par; | |
2723 } | |
2724 | |
2725 for( j = i + 1, is_existing = FALSE; | |
2726 j < nc_list->number AND is_existing EQ FALSE; | |
2727 j++ ) | |
2728 { | |
2729 if( nc_list->info[j]->arfcn EQ nc_list->info[i]->arfcn ) | |
2730 { | |
2731 is_existing = TRUE; | |
2732 | |
2733 if( is_pbcch_present ) | |
2734 { | |
2735 v_cs_par[j] |= nc_list->info[i]->v_cr_par; | |
2736 } | |
2737 } | |
2738 } | |
2739 | |
2740 if( !is_existing AND | |
2741 ( nc_ord EQ NC_NC2 OR ( nc_ord NEQ NC_NC2 AND v_cs_par[i] ) ) ) | |
2742 { | |
2743 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
2744 grr_data->nc_data.cell[number_of_frequencies].arfcn = nc_list->info[i]->arfcn; | |
2745 #else | |
2746 grr_data->nc_data.cell[number_of_frequencies].arfcn = | |
2747 grr_g23_arfcn_to_l1( nc_list->info[i]->arfcn ); | |
2748 #endif | |
2749 number_of_frequencies++; | |
2750 } | |
2751 } | |
2752 | |
2753 if( del_meas_rslt EQ CS_DELETE_MEAS_RSLT ) | |
2754 { | |
2755 cs_reuse_old_cell_rxlev( ); | |
2756 } | |
2757 grr_data->nc_data.c_cell = number_of_frequencies; | |
2758 cs_req_cr_meas( ); | |
2759 } | |
2760 } /* cs_send_cr_meas_req() */ | |
2761 | |
2762 /* | |
2763 +------------------------------------------------------------------------------ | |
2764 | Function : cs_send_cr_meas_stop_req | |
2765 +------------------------------------------------------------------------------ | |
2766 | Description : The function cs_send_cr_meas_stop_req() sends the cell | |
2767 | reselection measurement stop request to L1 | |
2768 | (MPHP_CR_MEAS_STOP_REQ) | |
2769 | | |
2770 | Parameters : dummy - description of parameter dummy | |
2771 | | |
2772 +------------------------------------------------------------------------------ | |
2773 */ | |
2774 GLOBAL void cs_send_cr_meas_stop_req ( void ) | |
2775 { | |
2776 TRACE_FUNCTION( "cs_send_cr_meas_stop_req" ); | |
2777 | |
2778 | |
2779 grr_data->nc_data.c_cell = 0; | |
2780 grr_data->cs.cr_meas_mode = cs_get_cr_meas_mode( ); | |
2781 cs_stop_cr_meas( ); | |
2782 | |
2783 } /* cs_send_cr_meas_stop_req() */ | |
2784 | |
2785 /* | |
2786 +------------------------------------------------------------------------------ | |
2787 | Function : cs_send_update_ba_req | |
2788 +------------------------------------------------------------------------------ | |
2789 | Description : The function cs_send_update_ba_req() updates the BA(BCCH) list | |
2790 | by passing the lists of added and removed frequencies. | |
2791 | | |
2792 | Parameters : | |
2793 | | |
2794 +------------------------------------------------------------------------------ | |
2795 */ | |
2796 GLOBAL void cs_send_update_ba_req ( T_SC_DATABASE *db ) | |
2797 { | |
2798 UBYTE i, j; /* used for counting */ | |
2799 BOOL is_found; | |
2800 T_add_freq_list *afreq; | |
2801 T_ncell_info *ncinfo; | |
2802 T_NC_ORDER ctrl_order = cs_get_network_ctrl_order( FALSE ); | |
2803 | |
2804 TRACE_FUNCTION( "cs_send_update_ba_req" ); | |
2805 | |
2806 { | |
2807 PALLOC( rrgrr_upd_ba_req, RRGRR_UPDATE_BA_REQ ); | |
2808 | |
2809 /* process cell type */ | |
2810 rrgrr_upd_ba_req->cell_type = SYNC_SCELL; | |
2811 | |
2812 /* process NC mode */ | |
2813 switch( ctrl_order ) | |
2814 { | |
2815 case NC_NC2: rrgrr_upd_ba_req->nc_mode = NC2_USED; break; | |
2816 case NC_RESET: rrgrr_upd_ba_req->nc_mode = NC_RESET; break; | |
2817 default : rrgrr_upd_ba_req->nc_mode = NC2_NOT_USED; break; | |
2818 } | |
2819 | |
2820 /* process list of removed frequencies */ | |
2821 if( db->nc_ms.rfreq.number > RRGRR_BA_LIST_SIZE ) | |
2822 { | |
2823 TRACE_ERROR ( "Number of removed frequencies > RRGRR_BA_LIST_SIZE" ); | |
2824 } | |
2825 | |
2826 i = 0; | |
2827 while( i < db->nc_ms.rfreq.number AND i < RRGRR_BA_LIST_SIZE ) | |
2828 { | |
2829 j = 0; | |
2830 is_found = FALSE; | |
2831 while( j < db->nc_cw.list.number AND is_found EQ FALSE ) | |
2832 { | |
2833 if( db->nc_cw.list.info[j].index EQ db->nc_ms.rfreq.idx[i] ) | |
2834 { | |
2835 is_found = TRUE; | |
2836 } | |
2837 else | |
2838 { | |
2839 j++; | |
2840 } | |
2841 } | |
2842 | |
2843 if( is_found EQ TRUE ) | |
2844 { | |
2845 rrgrr_upd_ba_req->rm_freq_list[i].arfcn = db->nc_cw.list.info[j].arfcn; | |
2846 rrgrr_upd_ba_req->rm_freq_list[i].bsic = db->nc_cw.list.info[j].bsic; | |
2847 } | |
2848 else | |
2849 { | |
2850 TRACE_ERROR( "Removed frequency cannot be found in nc_cw structure" ); | |
2851 } | |
2852 | |
2853 i++; | |
2854 } | |
2855 | |
2856 if( i < RRGRR_BA_LIST_SIZE ) | |
2857 { | |
2858 rrgrr_upd_ba_req->rm_freq_list[i].arfcn = RRGRR_INVALID_ARFCN; | |
2859 rrgrr_upd_ba_req->rm_freq_list[i].bsic = RRGRR_INVALID_BSIC; | |
2860 } | |
2861 | |
2862 #ifdef _SIMULATION_ | |
2863 | |
2864 i++; | |
2865 while( i < RRGRR_BA_LIST_SIZE ) | |
2866 { | |
2867 rrgrr_upd_ba_req->rm_freq_list[i].arfcn = RRGRR_INVALID_ARFCN; | |
2868 rrgrr_upd_ba_req->rm_freq_list[i].bsic = RRGRR_INVALID_BSIC; | |
2869 i++; | |
2870 } | |
2871 | |
2872 #endif /* #ifdef _SIMULATION_ */ | |
2873 | |
2874 /* process list of added frequencies */ | |
2875 if( db->nc_ms.ncmeas.list.number > RRGRR_BA_LIST_SIZE ) | |
2876 { | |
2877 TRACE_ERROR ( "Number of added frequencies > RRGRR_BA_LIST_SIZE" ); | |
2878 } | |
2879 | |
2880 i = 0; | |
2881 while( i < db->nc_ms.ncmeas.list.number AND i < RRGRR_BA_LIST_SIZE ) | |
2882 { | |
2883 afreq = &rrgrr_upd_ba_req->add_freq_list[i]; | |
2884 ncinfo = &db->nc_ms.ncmeas.list.info[i]; | |
2885 | |
2886 afreq->arfcn = ncinfo->arfcn; | |
2887 afreq->bsic = ncinfo->bsic; | |
2888 | |
2889 if( ncinfo->v_cr_par EQ TRUE ) | |
2890 { | |
2891 afreq->v_cr_par = TRUE; | |
2892 | |
2893 afreq->cr_par.cell_bar_access_2 = ncinfo->cr_par.cell_ba; | |
2894 afreq->cr_par.exc_acc = ncinfo->cr_par.exc_acc; | |
2895 afreq->cr_par.same_ra_as_serving_cell = ncinfo->cr_par.same_ra_scell; | |
2896 afreq->cr_par.gprs_rxlev_access_min = ncinfo->cr_par.cr_par_1.cr_pow_par.gprs_rxlev_access_min; | |
2897 afreq->cr_par.gprs_ms_txpwr_max_cch = ncinfo->cr_par.cr_par_1.cr_pow_par.gprs_ms_txpwr_max_cch; | |
2898 afreq->cr_par.gprs_temporary_offset = ncinfo->cr_par.cr_offset.gprs_temp_offset; | |
2899 afreq->cr_par.gprs_penalty_time = ncinfo->cr_par.cr_offset.gprs_penalty_time; | |
2900 afreq->cr_par.gprs_reselect_offset = ncinfo->cr_par.gprs_resel_off; | |
2901 afreq->cr_par.priority_class = ncinfo->cr_par.cr_par_1.hcs_par.gprs_prio_class; | |
2902 afreq->cr_par.hcs_thr = ncinfo->cr_par.cr_par_1.hcs_par.gprs_hcs_thr; | |
2903 afreq->cr_par.si13_location = SI13_LOC_INVALID; | |
2904 afreq->cr_par.pbcch_location = PBCCH_LOC_INVALID; | |
2905 afreq->cr_par.psi1_repeat_period = PSI1_RPT_PRD_INVALID; | |
2906 | |
2907 if( ncinfo->cr_par.v_si13_pbcch ) | |
2908 { | |
2909 if( ncinfo->cr_par.si13_pbcch.v_si13_location ) | |
2910 { | |
2911 afreq->cr_par.si13_location = ncinfo->cr_par.si13_pbcch.si13_location; | |
2912 } | |
2913 else | |
2914 { | |
2915 afreq->cr_par.pbcch_location = ncinfo->cr_par.si13_pbcch.pbcch_location; | |
2916 afreq->cr_par.psi1_repeat_period = ncinfo->cr_par.si13_pbcch.psi1_repeat_period - 1; | |
2917 } | |
2918 } | |
2919 } | |
2920 else | |
2921 { | |
2922 afreq->v_cr_par = FALSE; | |
2923 } | |
2924 | |
2925 i++; | |
2926 } | |
2927 | |
2928 if( i < RRGRR_BA_LIST_SIZE ) | |
2929 { | |
2930 rrgrr_upd_ba_req->add_freq_list[i].arfcn = RRGRR_INVALID_ARFCN; | |
2931 rrgrr_upd_ba_req->add_freq_list[i].bsic = RRGRR_INVALID_BSIC; | |
2932 } | |
2933 | |
2934 #ifdef _SIMULATION_ | |
2935 | |
2936 i++; | |
2937 while( i < RRGRR_BA_LIST_SIZE ) | |
2938 { | |
2939 rrgrr_upd_ba_req->add_freq_list[i].arfcn = RRGRR_INVALID_ARFCN; | |
2940 rrgrr_upd_ba_req->add_freq_list[i].bsic = RRGRR_INVALID_BSIC; | |
2941 i++; | |
2942 } | |
2943 | |
2944 #endif /* #ifdef _SIMULATION_ */ | |
2945 | |
2946 PSEND( hCommRR, rrgrr_upd_ba_req ); | |
2947 } | |
2948 } /* cs_send_update_ba_req() */ | |
2949 | |
2950 /* | |
2951 +------------------------------------------------------------------------------ | |
2952 | Function : cs_send_meas_rep_req | |
2953 +------------------------------------------------------------------------------ | |
2954 | Description : The function cs_send_meas_rep_req() updates RR with cause | |
2955 | NC_START_MEAS or NC_REPORT_MEAS or NC_STOP_MEAS. | |
2956 | | |
2957 | Parameters : NC_START_MEAS - start the measurement | |
2958 | NC_REPORT_MEAS - report the measurement | |
2959 | NC_STOP_MEAS - stop the measurement | |
2960 | | |
2961 +------------------------------------------------------------------------------ | |
2962 */ | |
2963 GLOBAL void cs_send_meas_rep_req ( UBYTE cause ) | |
2964 { | |
2965 TRACE_FUNCTION( "cs_send_meas_rep_req" ); | |
2966 | |
2967 { | |
2968 PALLOC( rrgrr_meas_rep_req, RRGRR_MEAS_REP_REQ ); | |
2969 | |
2970 rrgrr_meas_rep_req->meas_cause = grr_data->cs_meas.nc_meas_cause = cause; | |
2971 | |
2972 PSEND( hCommRR, rrgrr_meas_rep_req ); | |
2973 } | |
2974 } /* cs_send_meas_rep_req() */ | |
2975 | |
2976 /* | |
2977 +------------------------------------------------------------------------------ | |
2978 | Function : cs_store_meas_rep_cnf | |
2979 +------------------------------------------------------------------------------ | |
2980 | Description : ... | |
2981 | | |
2982 | Parameters : ... | |
2983 | | |
2984 +------------------------------------------------------------------------------ | |
2985 */ | |
2986 GLOBAL void cs_store_meas_rep_cnf ( T_RRGRR_MEAS_REP_CNF *rrgrr_meas_rep_cnf ) | |
2987 { | |
2988 UBYTE i; /* used for counting */ | |
2989 UBYTE mval_idx; | |
2990 T_NC_MVAL *mval; | |
2991 | |
2992 TRACE_FUNCTION( "cs_store_meas_rep_cnf" ); | |
2993 | |
2994 /* | |
2995 * store the first value as serving cell | |
2996 */ | |
2997 grr_data->db.scell_info.rxlev_avg = rrgrr_meas_rep_cnf->meas_res[0].rxlev; | |
2998 | |
2999 /* | |
3000 * store the next values as neighbour cells | |
3001 */ | |
3002 cs_init_nc_mval_lst( ); | |
3003 | |
3004 for( i = 1; | |
3005 i < RRGRR_MEAS_REP_LIST_SIZE AND | |
3006 rrgrr_meas_rep_cnf->meas_res[i].arfcn NEQ RRGRR_INVALID_ARFCN; | |
3007 i++ ) | |
3008 { | |
3009 mval = grr_get_nc_mval( RRGRR_INVALID_ARFCN, RRGRR_INVALID_BSIC, &mval_idx ); | |
3010 | |
3011 if( mval NEQ NULL ) | |
3012 { | |
3013 mval->status = NC_MVAL_STAT_ASSIGNED; | |
3014 mval->arfcn = rrgrr_meas_rep_cnf->meas_res[i].arfcn; | |
3015 mval->rla_p.stat = CS_RLA_P_VALID; | |
3016 mval->rla_p.lev = | |
3017 mval->rxlev_avg = rrgrr_meas_rep_cnf->meas_res[i].rxlev; | |
3018 mval->sync_info.bsic = rrgrr_meas_rep_cnf->meas_res[i].bsic; | |
3019 mval->sync_info.sync.status = STAT_SYNC_OK; | |
3020 | |
3021 grr_data->cs.is_mval_initialized = FALSE; | |
3022 } | |
3023 else | |
3024 { | |
3025 TRACE_EVENT_P2( "No free entry for measured value found: %d %d", | |
3026 rrgrr_meas_rep_cnf->meas_res[i].arfcn, | |
3027 rrgrr_meas_rep_cnf->meas_res[i].bsic ); | |
3028 } | |
3029 } | |
3030 } /* cs_store_meas_rep_cnf() */ | |
3031 | |
3032 /* | |
3033 +------------------------------------------------------------------------------ | |
3034 | Function : cs_build_strongest | |
3035 +------------------------------------------------------------------------------ | |
3036 | Description : ... | |
3037 | | |
3038 | Parameters : ... | |
3039 | | |
3040 +------------------------------------------------------------------------------ | |
3041 */ | |
3042 GLOBAL void cs_build_strongest ( void ) | |
3043 { | |
3044 UBYTE i; | |
3045 UBYTE count = 0; | |
3046 UBYTE index[CS_MAX_STRONG_CARRIER]; | |
3047 | |
3048 TRACE_FUNCTION( "cs_build_strongest" ); | |
3049 | |
3050 cs_find_strongest_with_status | |
3051 ( &count, index, CS_RLA_P_VALID, | |
3052 (UBYTE)( CS_MAX_STRONG_CARRIER - count ), CS_NO_BAND_LIMITATION ); | |
3053 | |
3054 for( i = 0; i < count; i++ ) | |
3055 { | |
3056 grr_data->db.nc_six_strgst[i].idx = index[i]; | |
3057 } | |
3058 | |
3059 cs_set_cnt_nc_six( count, count ); | |
3060 | |
3061 } /* cs_build_strongest() */ | |
3062 | |
3063 /* | |
3064 +------------------------------------------------------------------------------ | |
3065 | Function : cs_send_meas_rpt | |
3066 +------------------------------------------------------------------------------ | |
3067 | Description : This function ... | |
3068 | | |
3069 | Parameters : void | |
3070 | | |
3071 +------------------------------------------------------------------------------ | |
3072 */ | |
3073 GLOBAL BOOL cs_send_meas_rpt ( BOOL perform_init ) | |
3074 { | |
3075 BOOL rpt_snd; | |
3076 T_U_MEAS_REPORT meas_rpt; | |
3077 | |
3078 TRACE_FUNCTION( "cs_send_meas_rpt" ); | |
3079 | |
3080 if( perform_init EQ TRUE ) | |
3081 { | |
3082 grr_data->cs_meas.pmr_snd_ref = 0; | |
3083 } | |
3084 | |
3085 memset(&meas_rpt, 0, sizeof(T_U_MEAS_REPORT)); | |
3086 | |
3087 rpt_snd = cs_build_meas_rpt( &meas_rpt ); | |
3088 | |
3089 if( rpt_snd EQ TRUE ) | |
3090 { | |
3091 sig_cs_ctrl_meas_report( &meas_rpt ); | |
3092 } | |
3093 | |
3094 return( rpt_snd ); | |
3095 } /* cs_send_meas_rpt() */ | |
3096 | |
3097 | |
3098 /* | |
3099 +------------------------------------------------------------------------------ | |
3100 | Function : cs_start_t_reselect | |
3101 +------------------------------------------------------------------------------ | |
3102 | Description : ... | |
3103 | | |
3104 | Parameters : void | |
3105 | | |
3106 +------------------------------------------------------------------------------ | |
3107 */ | |
3108 GLOBAL void cs_start_t_reselect ( void ) | |
3109 { | |
3110 TRACE_FUNCTION( "cs_start_t_reselect" ); | |
3111 | |
3112 if( grr_t_status( T_RESELECT ) EQ 0 ) | |
3113 { | |
3114 vsi_t_start( GRR_handle, T_RESELECT, T_RESELECT_VALUE ); | |
3115 | |
3116 TRACE_EVENT( "Timer T_RESELECT started" ); | |
3117 } | |
3118 } /* cs_start_t_reselect() */ | |
3119 | |
3120 /* | |
3121 +------------------------------------------------------------------------------ | |
3122 | Function : cs_stop_t_reselect | |
3123 +------------------------------------------------------------------------------ | |
3124 | Description : ... | |
3125 | | |
3126 | Parameters : void | |
3127 | | |
3128 +------------------------------------------------------------------------------ | |
3129 */ | |
3130 GLOBAL void cs_stop_t_reselect ( void ) | |
3131 { | |
3132 TRACE_FUNCTION( "cs_stop_t_reselect" ); | |
3133 | |
3134 if( grr_t_status( T_RESELECT ) NEQ 0 ) | |
3135 { | |
3136 vsi_t_stop( GRR_handle, T_RESELECT ); | |
3137 | |
3138 TRACE_EVENT( "Timer T_RESELECT stopped" ); | |
3139 } | |
3140 } /* cs_stop_t_reselect() */ | |
3141 | |
3142 /* | |
3143 +------------------------------------------------------------------------------ | |
3144 | Function : cs_process_t3158 | |
3145 +------------------------------------------------------------------------------ | |
3146 | Description : ... | |
3147 | | |
3148 | Parameters : void | |
3149 | | |
3150 +------------------------------------------------------------------------------ | |
3151 */ | |
3152 GLOBAL void cs_process_t3158 ( void ) | |
3153 { | |
3154 T_TIME reporting_period; | |
3155 T_TIME time_to_go; | |
3156 BOOL tmr_3158_rng_le_rp = FALSE; | |
3157 | |
3158 TRACE_FUNCTION( "cs_process_t3158" ); | |
3159 | |
3160 if( cs_is_meas_reporting( ) ) | |
3161 /* Implies NC measurement conditions are satisfied. May mean Enhanced | |
3162 measurement conditions are also satisfied */ | |
3163 { | |
3164 switch( grr_data->cs_meas.packet_mode ) | |
3165 { | |
3166 case( PACKET_MODE_PIM ): | |
3167 case( PACKET_MODE_PAM ): | |
3168 reporting_period = cs_get_nc_rpt_prd_idle( ); | |
3169 break; | |
3170 | |
3171 case( PACKET_MODE_PTM ): | |
3172 /* | |
3173 * In packet transfer mode, the reporting period is indicated in | |
3174 * NC_REPORTING_PERIOD_T. | |
3175 */ | |
3176 reporting_period = | |
3177 GET_NC_RPT_PRD( grr_data->db.nc_ref_lst.param->rep_per_t ); | |
3178 break; | |
3179 | |
3180 default: | |
3181 if( GET_STATE( CS ) EQ CS_CR_NETWORK ) | |
3182 { | |
3183 /* | |
3184 * In case timer T3158 expires during processing of Packet Cell Change | |
3185 * Order, the timer should be re-started and not stopped at all. | |
3186 */ | |
3187 reporting_period = cs_get_nc_rpt_prd_idle( ); | |
3188 } | |
3189 else | |
3190 { | |
3191 reporting_period = 0; | |
3192 } | |
3193 break; | |
3194 } | |
3195 | |
3196 time_to_go = grr_t_status( T3158 ); | |
3197 | |
3198 if( time_to_go > 0 ) | |
3199 { | |
3200 if( time_to_go > reporting_period ) | |
3201 { | |
3202 cs_stop_t3158( ); | |
3203 | |
3204 if( grr_is_pbcch_present( ) EQ FALSE AND | |
3205 grr_data->cs_meas.nc_meas_cause NEQ NC_STOP_MEAS ) | |
3206 { | |
3207 cs_send_meas_rep_req ( NC_STOP_MEAS ); | |
3208 } | |
3209 } | |
3210 else | |
3211 { | |
3212 tmr_3158_rng_le_rp = TRUE; | |
3213 } | |
3214 } | |
3215 | |
3216 if( reporting_period NEQ 0 ) | |
3217 { | |
3218 if( tmr_3158_rng_le_rp EQ FALSE ) | |
3219 { | |
3220 cs_reset_all_rxlev_results( ); | |
3221 cs_start_t3158( reporting_period ); | |
3222 /* | |
3223 * Start rx_lev averaging when NC=1 or NC=2 in ALR | |
3224 */ | |
3225 if( grr_is_pbcch_present( ) EQ FALSE AND | |
3226 grr_data->cs_meas.nc_meas_cause EQ NC_STOP_MEAS ) | |
3227 { | |
3228 cs_send_meas_rep_req ( NC_START_MEAS ) ; | |
3229 } | |
3230 } | |
3231 } | |
3232 else | |
3233 { | |
3234 cs_reset_all_rxlev_results( ); | |
3235 } | |
3236 } | |
3237 else | |
3238 { | |
3239 cs_reset_all_rxlev_results( ); | |
3240 cs_stop_t3158( ); | |
3241 /* | |
3242 * Stop rx_lev averaging when NC=1 or NC=2 in ALR | |
3243 */ | |
3244 if( grr_is_pbcch_present( ) EQ FALSE AND | |
3245 grr_data->cs_meas.nc_meas_cause NEQ NC_STOP_MEAS ) | |
3246 { | |
3247 cs_send_meas_rep_req ( NC_STOP_MEAS ); | |
3248 } | |
3249 } | |
3250 } /* cs_process_t3158() */ | |
3251 | |
3252 /* | |
3253 +------------------------------------------------------------------------------ | |
3254 | Function : cs_start_t3158 | |
3255 +------------------------------------------------------------------------------ | |
3256 | Description : | |
3257 | | |
3258 | Parameters : | |
3259 | | |
3260 +------------------------------------------------------------------------------ | |
3261 */ | |
3262 LOCAL void cs_start_t3158 ( T_TIME time ) | |
3263 { | |
3264 TRACE_FUNCTION( "cs_start_t3158" ); | |
3265 | |
3266 vsi_t_start( GRR_handle, T3158, time ); | |
3267 | |
3268 TRACE_EVENT_P1( "T3158: %d", time ); | |
3269 | |
3270 } /* cs_start_t3158() */ | |
3271 | |
3272 /* | |
3273 +------------------------------------------------------------------------------ | |
3274 | Function : cs_stop_t3158 | |
3275 +------------------------------------------------------------------------------ | |
3276 | Description : | |
3277 | | |
3278 | Parameters : | |
3279 | | |
3280 +------------------------------------------------------------------------------ | |
3281 */ | |
3282 GLOBAL void cs_stop_t3158 ( void ) | |
3283 { | |
3284 TRACE_FUNCTION( "cs_stop_t3158" ); | |
3285 | |
3286 if( grr_t_status( T3158 ) > 0 ) | |
3287 { | |
3288 vsi_t_stop( GRR_handle, T3158 ); | |
3289 | |
3290 TRACE_EVENT( "T3158 stopped" ); | |
3291 } | |
3292 } /* cs_stop_t3158() */ | |
3293 | |
3294 /* | |
3295 +------------------------------------------------------------------------------ | |
3296 | Function : cs_cancel_meas_report | |
3297 +------------------------------------------------------------------------------ | |
3298 | Description : ... | |
3299 | | |
3300 | Parameters : void | |
3301 | | |
3302 +------------------------------------------------------------------------------ | |
3303 */ | |
3304 GLOBAL void cs_cancel_meas_report ( void ) | |
3305 { | |
3306 TRACE_FUNCTION( "cs_cancel_meas_report" ); | |
3307 | |
3308 switch( GET_STATE( CS_MEAS ) ) | |
3309 { | |
3310 case CS_MEAS_REP_REQ: | |
3311 SET_STATE( CS_MEAS, CS_NULL ); | |
3312 break; | |
3313 case CS_MEAS_PMR_SENDING: | |
3314 sig_cs_ctrl_cancel_meas_report( ); | |
3315 break; | |
3316 default: | |
3317 /* do nothing */ | |
3318 break; | |
3319 } | |
3320 } /* cs_cancel_meas_report() */ | |
3321 | |
3322 /* | |
3323 +------------------------------------------------------------------------------ | |
3324 | Function : cs_build_nc_ref_list | |
3325 +------------------------------------------------------------------------------ | |
3326 | Description : | |
3327 | | |
3328 | Parameters : db - pointer to serving cell database | |
3329 | | |
3330 +------------------------------------------------------------------------------ | |
3331 */ | |
3332 GLOBAL void cs_build_nc_ref_list ( T_SC_DATABASE *db, BOOL is_dsf ) | |
3333 { | |
3334 TRACE_FUNCTION( "cs_build_nc_ref_list" ); | |
3335 | |
3336 cs_init_nc_ref_list( &grr_data->db.nc_ref_lst ); | |
3337 | |
3338 if( | |
3339 grr_data->cs.gmm_state EQ READY_STATE AND | |
3340 is_dsf EQ FALSE AND | |
3341 ( | |
3342 db->nc_ms.ncmeas.param.ctrl_order EQ NC_NC0 OR | |
3343 db->nc_ms.ncmeas.param.ctrl_order EQ NC_NC1 OR | |
3344 db->nc_ms.ncmeas.param.ctrl_order EQ NC_NC2 | |
3345 ) | |
3346 ) | |
3347 { | |
3348 grr_data->db.nc_ref_lst.param = &db->nc_ms.ncmeas.param; | |
3349 | |
3350 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
3351 grr_data->db.nc_ref_lst.enh_param = &db->enh_ms; | |
3352 #endif | |
3353 } | |
3354 else if( db->nc_cw.param.ctrl_order EQ NC_NC0 OR | |
3355 db->nc_cw.param.ctrl_order EQ NC_NC1 OR | |
3356 db->nc_cw.param.ctrl_order EQ NC_NC2 ) | |
3357 { | |
3358 grr_data->db.nc_ref_lst.param = &db->nc_cw.param; | |
3359 | |
3360 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
3361 grr_data->db.nc_ref_lst.enh_param = &db->enh_cw; | |
3362 #endif | |
3363 } | |
3364 | |
3365 cs_build_nc_freq_list( db ); | |
3366 cs_reorg_nc_mval_lst( ); | |
3367 | |
3368 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
3369 if( !grr_is_pbcch_present() AND | |
3370 grr_data->db.nc_ref_lst.enh_param->rept_type EQ REPORT_TYPE_ENH_REP) | |
3371 { | |
3372 cs_init_ba_bcch_nc_ref_list(); | |
3373 cs_build_ba_bcch_nc_freq_list(); | |
3374 } | |
3375 #endif | |
3376 | |
3377 }/* cs_build_nc_ref_list */ | |
3378 | |
3379 /* | |
3380 +------------------------------------------------------------------------------ | |
3381 | Function : cs_init_nc_ref_list | |
3382 +------------------------------------------------------------------------------ | |
3383 | Description : | |
3384 | | |
3385 | Parameters : list - pointer to NC measurement pointer list | |
3386 | | |
3387 +------------------------------------------------------------------------------ | |
3388 */ | |
3389 GLOBAL void cs_init_nc_ref_list ( T_NC_REF_LIST *list ) | |
3390 { | |
3391 TRACE_FUNCTION( "cs_init_nc_ref_list" ); | |
3392 | |
3393 list->number = 0; | |
3394 list->param = NULL; | |
3395 | |
3396 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
3397 list->enh_param = NULL; | |
3398 #endif | |
3399 | |
3400 }/* cs_init_nc_ref_list */ | |
3401 | |
3402 | |
3403 /* | |
3404 +------------------------------------------------------------------------------ | |
3405 | Function : cs_init_nc_mval_lst | |
3406 +------------------------------------------------------------------------------ | |
3407 | Description : | |
3408 | | |
3409 | Parameters : | |
3410 | | |
3411 +------------------------------------------------------------------------------ | |
3412 */ | |
3413 GLOBAL void cs_init_nc_mval_lst ( void ) | |
3414 { | |
3415 UBYTE i; | |
3416 | |
3417 TRACE_FUNCTION( "cs_init_nc_mval_lst" ); | |
3418 | |
3419 if( grr_data->cs.is_mval_initialized EQ FALSE ) | |
3420 { | |
3421 for( i = 0; i < MAX_NR_OF_NC_MVAL; i++ ) | |
3422 { | |
3423 cs_init_nc_mval( &grr_data->db.nc_mval_list.nc_mval[i] ); | |
3424 } | |
3425 | |
3426 grr_data->cs.is_mval_initialized = TRUE; | |
3427 | |
3428 #if !defined (NTRACE) | |
3429 | |
3430 if( grr_data->cs.v_crp_trace EQ TRUE ) | |
3431 { | |
3432 TRACE_EVENT( "cs_init_nc_mval_lst: now initialized" ); | |
3433 } | |
3434 | |
3435 #endif /* #if !defined (NTRACE) */ | |
3436 | |
3437 } | |
3438 else | |
3439 { | |
3440 | |
3441 #if !defined (NTRACE) | |
3442 | |
3443 if( grr_data->cs.v_crp_trace EQ TRUE ) | |
3444 { | |
3445 TRACE_EVENT( "cs_init_nc_mval_lst: already initialized" ); | |
3446 } | |
3447 | |
3448 #endif /* #if !defined (NTRACE) */ | |
3449 | |
3450 } | |
3451 }/* cs_init_nc_mval_lst */ | |
3452 | |
3453 /* | |
3454 +------------------------------------------------------------------------------ | |
3455 | Function : cs_init_nc_mval | |
3456 +------------------------------------------------------------------------------ | |
3457 | Description : | |
3458 | | |
3459 | Parameters : mval - pointer to NC measured value | |
3460 | | |
3461 +------------------------------------------------------------------------------ | |
3462 */ | |
3463 LOCAL void cs_init_nc_mval ( T_NC_MVAL *mval ) | |
3464 { | |
3465 TRACE_FUNCTION( "cs_init_nc_mval" ); | |
3466 | |
3467 mval->arfcn = RRGRR_INVALID_ARFCN; | |
3468 mval->sync_info.bsic = RRGRR_INVALID_BSIC; | |
3469 mval->sync_info.sync.status = STAT_SYNC_NONE; | |
3470 mval->sync_info.sync.sync_failed_cnt = 0; | |
3471 mval->rla_p.stat = CS_RLA_P_NOT_AVAIL; | |
3472 mval->rxlev_avg = RXLEV_AVG_INVALID; | |
3473 mval->status = NC_MVAL_STAT_NONE; | |
3474 }/* cs_init_nc_mval */ | |
3475 | |
3476 | |
3477 /* | |
3478 +------------------------------------------------------------------------------ | |
3479 | Function : cs_update_bsic | |
3480 +------------------------------------------------------------------------------ | |
3481 | Description : | |
3482 | | |
3483 | Parameters : | |
3484 | | |
3485 +------------------------------------------------------------------------------ | |
3486 */ | |
3487 GLOBAL void cs_update_bsic ( void ) | |
3488 { | |
3489 UBYTE i | |
3490 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
3491 ,j, k | |
3492 #endif | |
3493 ; | |
3494 /* used for counting */ | |
3495 #if defined (TI_PS_FF_RTD) AND defined (REL99) | |
3496 UBYTE i_max,rtd_index,rtd_count; | |
3497 #else | |
3498 UBYTE i_max; | |
3499 #endif /* #if defined (TI_PS_FF_RTD) AND defined (REL99) */ | |
3500 | |
3501 | |
3502 TRACE_FUNCTION( "cs_update_bsic" ); | |
3503 | |
3504 i = 0; | |
3505 i_max = MINIMUM( grr_data->db.cnt_nc_six.candid, CS_MAX_STRONG_CARRIER ); | |
3506 i_max = MINIMUM( i_max, RRGRR_MAX_ARFCN_NCELL_SYNC_REQ ); | |
3507 | |
3508 if( i_max NEQ 0 ) | |
3509 { | |
3510 PALLOC( rrgrr_check_bsic_req, RRGRR_NCELL_SYNC_REQ ); | |
3511 | |
3512 while( i < i_max ) | |
3513 { | |
3514 #if defined (TI_PS_FF_RTD) AND defined (REL99) | |
3515 rrgrr_check_bsic_req->ncell_sync_list[i].arfcn = grr_data->db.nc_mval_list.nc_mval[grr_data->db.nc_six_strgst[i].idx].arfcn; | |
3516 #else | |
3517 rrgrr_check_bsic_req->arfcn[i] = grr_data->db.nc_mval_list.nc_mval[grr_data->db.nc_six_strgst[i].idx].arfcn; | |
3518 #endif /* #if defined (TI_PS_FF_RTD) AND defined (REL99) */ | |
3519 | |
3520 | |
3521 i++; | |
3522 } | |
3523 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
3524 /* Extend the ARFCN list only if ENH reporting is requested */ | |
3525 if(cs_is_enh_meas_reporting()) | |
3526 { | |
3527 T_ENH_STRNG_ARFCN_LIST f_bin;/* Stores the ARFCN-RXLEV pair in descending | |
3528 order of RXLEV */ | |
3529 BOOL found; /* Will be set, if ARFCN in f_bin is found in NC_MVAL */ | |
3530 | |
3531 memset(&f_bin, 0, sizeof(T_ENH_STRNG_ARFCN_LIST)); | |
3532 | |
3533 /* Form a ARFCN-RXLEV pair list in descending order of RXLEV */ | |
3534 cs_build_enh_sorted_strng_arfcn_list(&f_bin); | |
3535 | |
3536 /* Fill the NCELL_SYNC_REQ with ARFCNs from the above list. This list | |
3537 will be filled without disturbing the six strongest cells for | |
3538 cell reselection or PMR. The request for SYNC is now done for a | |
3539 max of 12 cells with 1st few cells upto a max of six for cell | |
3540 reselection and the remaining will be filled with ARFCNs from | |
3541 the ENH list in the order of serving band, multiband and the rest | |
3542 contains the excess from the above bands, each group containing | |
3543 cells in descending order of RXLEV */ | |
3544 j = 0; | |
3545 while(i_max < RRGRR_MAX_ARFCN_NCELL_SYNC_REQ AND j < f_bin.num) | |
3546 { | |
3547 found = FALSE; | |
3548 for(k = 0; k < grr_data->db.cnt_nc_six.candid; k++) | |
3549 { | |
3550 if(f_bin.meas[j].arfcn EQ | |
3551 grr_data->db.nc_mval_list.nc_mval[grr_data->db.nc_six_strgst[k].idx].arfcn) | |
3552 { | |
3553 found = TRUE; | |
3554 break; | |
3555 } | |
3556 } | |
3557 | |
3558 if(!found) | |
3559 { | |
3560 #if defined (TI_PS_FF_RTD) AND defined (REL99) | |
3561 rrgrr_check_bsic_req->ncell_sync_list[i_max].arfcn = f_bin.meas[j].arfcn; | |
3562 #else | |
3563 rrgrr_check_bsic_req->arfcn[i_max] = f_bin.meas[j].arfcn; | |
3564 #endif /* #if defined (TI_PS_FF_RTD) AND defined (REL99) */ | |
3565 | |
3566 i_max++; | |
3567 } | |
3568 j++; | |
3569 } | |
3570 } | |
3571 | |
3572 if( i_max < RRGRR_MAX_ARFCN_NCELL_SYNC_REQ ) | |
3573 { | |
3574 #if defined (TI_PS_FF_RTD) AND defined (REL99) | |
3575 rrgrr_check_bsic_req->ncell_sync_list[i_max].arfcn = RRGRR_INVALID_ARFCN; | |
3576 #else | |
3577 rrgrr_check_bsic_req->arfcn[i_max] = RRGRR_INVALID_ARFCN; | |
3578 #endif /* #if defined (TI_PS_FF_RTD) AND defined (REL99) */ | |
3579 } /*if*/ | |
3580 #if defined (TI_PS_FF_RTD) AND defined (REL99) | |
3581 i=0; | |
3582 while (i < i_max) | |
3583 { | |
3584 j = 0; | |
3585 rtd_count = 0; | |
3586 /*More than 3 RTD values is not acceptable */ | |
3587 while( j < grr_data->db.nc_ref_lst.number AND rtd_count < MAX_NUM_OF_RTD_VALUES ) | |
3588 { | |
3589 /* Check the NC ARFCN in the BA-list to get the index of that ARFCN in BA-list*/ | |
3590 if(rrgrr_check_bsic_req->ncell_sync_list[i].arfcn EQ (grr_data->db.nc_ref_lst.info[j])->arfcn) | |
3591 { | |
3592 /* Pickup the right RTD value for that ARFCN */ | |
3593 rtd_index = (grr_data->db.nc_ref_lst.info[j])->index; | |
3594 /*Maximum number of ncell is 32 if it exceeds then store RTD_NOT_AVAILABLE for that ARFCN*/ | |
3595 if(rtd_index < MAX_NR_OF_NCELL AND psc_db->rtd[rtd_index] NEQ RTD_NOT_AVAILABLE ) | |
3596 { | |
3597 rrgrr_check_bsic_req->ncell_sync_list[i].v_rtd = 1; | |
3598 rrgrr_check_bsic_req->ncell_sync_list[i].rtd[rtd_count] = psc_db->rtd[rtd_index]; | |
3599 rtd_count++; | |
3600 }/*if*/ | |
3601 } /*if*/ | |
3602 j++; | |
3603 } /*while*/ | |
3604 rrgrr_check_bsic_req->ncell_sync_list[i].c_rtd = rtd_count; | |
3605 i++; | |
3606 } /*while*/ | |
3607 #endif /* #if defined (TI_PS_FF_RTD) AND defined (REL99) */ | |
3608 | |
3609 | |
3610 #ifdef _SIMULATION_ | |
3611 | |
3612 i_max = i_max + 1; | |
3613 while( i_max < RRGRR_MAX_ARFCN_NCELL_SYNC_REQ ) | |
3614 { | |
3615 #if defined (TI_PS_FF_RTD) AND defined (REL99) | |
3616 rrgrr_check_bsic_req->ncell_sync_list[i_max].arfcn = RRGRR_INVALID_ARFCN; | |
3617 #else | |
3618 rrgrr_check_bsic_req->arfcn[i_max] = RRGRR_INVALID_ARFCN; | |
3619 #endif /* #if defined (TI_PS_FF_RTD) AND defined (REL99) */ | |
3620 | |
3621 i_max++; | |
3622 } | |
3623 #endif | |
3624 #else | |
3625 | |
3626 if( i < RRGRR_MAX_ARFCN_NCELL_SYNC_REQ ) | |
3627 { | |
3628 rrgrr_check_bsic_req->arfcn[i] = RRGRR_INVALID_ARFCN; | |
3629 } | |
3630 | |
3631 #ifdef _SIMULATION_ | |
3632 | |
3633 i = i + 1; | |
3634 while( i < RRGRR_MAX_ARFCN_NCELL_SYNC_REQ ) | |
3635 { | |
3636 rrgrr_check_bsic_req->arfcn[i] = RRGRR_INVALID_ARFCN; | |
3637 i++; | |
3638 } | |
3639 | |
3640 #endif /* #ifdef _SIMULATION_ */ | |
3641 | |
3642 #endif /* REL99 AND TI_PS_FF_EMR */ | |
3643 | |
3644 rrgrr_check_bsic_req->sync_type = SYNC_INITIAL; | |
3645 PSEND( hCommRR, rrgrr_check_bsic_req ); | |
3646 } | |
3647 }/* cs_update_bsic */ | |
3648 | |
3649 | |
3650 /* | |
3651 +------------------------------------------------------------------------------ | |
3652 | Function : cs_find_candidate | |
3653 +------------------------------------------------------------------------------ | |
3654 | Description : | |
3655 | | |
3656 | Parameters : | |
3657 | | |
3658 +------------------------------------------------------------------------------ | |
3659 */ | |
3660 GLOBAL BOOL cs_find_candidate ( void ) | |
3661 { | |
3662 BOOL is_new_candidate = FALSE; | |
3663 T_scell_info *sc; | |
3664 | |
3665 TRACE_FUNCTION( "cs_find_candidate" ); | |
3666 | |
3667 if( grr_data->cs.reselect_cause EQ CS_RESELECT_CAUSE_CTRL_ABNORMAL AND | |
3668 psc_db->gen_cell_par.rab_acc_re EQ GRR_RA_RETRY_DISABLED ) | |
3669 { | |
3670 grr_data->db.cr_cell = NULL; | |
3671 | |
3672 #if !defined (NTRACE) | |
3673 | |
3674 if( grr_data->cs.v_crp_trace EQ TRUE ) | |
3675 { | |
3676 TRACE_EVENT( "no candidate found, RA retry bit for abnormal cell re-selection not set" ); | |
3677 } | |
3678 | |
3679 #endif /* #if !defined (NTRACE) */ | |
3680 | |
3681 } | |
3682 else if( grr_data->cs.reselect_cause EQ CS_RESELECT_CAUSE_CTRL_SCELL ) | |
3683 { | |
3684 if( cs_create_cr_cell( psc_db->pbcch.bcch.arfcn, | |
3685 psc_db->pbcch.bcch.bsic ) NEQ NULL ) | |
3686 { | |
3687 | |
3688 #if !defined (NTRACE) | |
3689 | |
3690 if( grr_data->cs.v_crp_trace EQ TRUE ) | |
3691 { | |
3692 TRACE_EVENT( "serving cell found as candidate" ); | |
3693 } | |
3694 | |
3695 #endif /* #if !defined (NTRACE) */ | |
3696 | |
3697 /* | |
3698 * the cell re-selection process will be started | |
3699 */ | |
3700 is_new_candidate = TRUE; | |
3701 } | |
3702 } | |
3703 else | |
3704 { | |
3705 cs_get_best_cell( &grr_data->db.cr_cell, &sc ); | |
3706 | |
3707 if( grr_data->db.cr_cell NEQ NULL ) | |
3708 { | |
3709 | |
3710 #if !defined (NTRACE) | |
3711 | |
3712 if( grr_data->cs.v_crp_trace EQ TRUE ) | |
3713 { | |
3714 TRACE_EVENT( "candidate found" ); | |
3715 } | |
3716 | |
3717 #endif /* #if !defined (NTRACE) */ | |
3718 | |
3719 /* | |
3720 * the cell re-selection process will be started | |
3721 */ | |
3722 is_new_candidate = TRUE; | |
3723 } | |
3724 else if( sc NEQ NULL ) | |
3725 { | |
3726 | |
3727 #if !defined (NTRACE) | |
3728 | |
3729 if( grr_data->cs.v_crp_trace EQ TRUE ) | |
3730 { | |
3731 TRACE_EVENT( "no candidate found, serving cell good" ); | |
3732 } | |
3733 | |
3734 #endif /* #if !defined (NTRACE) */ | |
3735 | |
3736 /* | |
3737 * the serving cell becomes good again or is still good | |
3738 */ | |
3739 cs_stop_t_reselect( ); | |
3740 } | |
3741 else | |
3742 { | |
3743 | |
3744 #if !defined (NTRACE) | |
3745 | |
3746 if( grr_data->cs.v_crp_trace EQ TRUE ) | |
3747 { | |
3748 TRACE_EVENT( "no candidate found, serving cell bad" ); | |
3749 } | |
3750 | |
3751 #endif /* #if !defined (NTRACE) */ | |
3752 | |
3753 /* | |
3754 * the serving cell becomes bad but | |
3755 * no suitable neighbour cell is available | |
3756 */ | |
3757 cs_start_t_reselect( ); | |
3758 } | |
3759 } | |
3760 | |
3761 return( is_new_candidate ); | |
3762 }/* cs_find_candidate */ | |
3763 | |
3764 /* | |
3765 +------------------------------------------------------------------------------ | |
3766 | Function : cs_cr_decision | |
3767 +------------------------------------------------------------------------------ | |
3768 | Description : | |
3769 | | |
3770 | Parameters : | |
3771 | | |
3772 +------------------------------------------------------------------------------ | |
3773 */ | |
3774 GLOBAL BOOL cs_cr_decision ( T_CRDM mode ) | |
3775 { | |
3776 T_NC_ORDER ctrl_order; | |
3777 BOOL cr_initiated = FALSE; | |
3778 | |
3779 TRACE_FUNCTION( "cs_cr_decision" ); | |
3780 | |
3781 switch( mode ) | |
3782 { | |
3783 case( CRDM_T_RESELECT ): | |
3784 sig_cs_ctrl_no_more_candidate( grr_data->cs.reselect_cause ); | |
3785 | |
3786 cr_initiated = TRUE; | |
3787 break; | |
3788 | |
3789 case( CRDM_CR_CTRL ): | |
3790 ctrl_order = cs_get_network_ctrl_order( TRUE ); | |
3791 | |
3792 if( ctrl_order EQ NC_NC0 OR | |
3793 ctrl_order EQ NC_NC1 OR | |
3794 grr_data->cs.reselect_cause EQ CS_RESELECT_CAUSE_CTRL_SCELL OR | |
3795 ( grr_data->cs.reselect_cause EQ CS_RESELECT_CAUSE_CTRL_DL_SIG_FAIL AND | |
3796 ctrl_order EQ NC_NC2 ) ) | |
3797 { | |
3798 /* | |
3799 * Only in case the NETWORK_CONTROL_ORDER is either equal to | |
3800 * NC0 or NC1 the MS shall perform automomous cell re-selection | |
3801 */ | |
3802 | |
3803 if( cs_find_candidate( ) ) | |
3804 { | |
3805 sig_cs_ctrl_new_candidate( grr_data->cs.reselect_cause ); | |
3806 } | |
3807 else | |
3808 { | |
3809 sig_cs_ctrl_no_more_candidate( grr_data->cs.reselect_cause ); | |
3810 } | |
3811 } | |
3812 else | |
3813 { | |
3814 sig_cs_ctrl_no_more_candidate( grr_data->cs.reselect_cause ); | |
3815 } | |
3816 | |
3817 cr_initiated = TRUE; | |
3818 break; | |
3819 | |
3820 case( CRDM_CR_INITIAL ): | |
3821 ctrl_order = cs_get_network_ctrl_order( TRUE ); | |
3822 | |
3823 if( ctrl_order EQ NC_NC0 OR ctrl_order EQ NC_NC1 ) | |
3824 { | |
3825 /* | |
3826 * Only in case the NETWORK_CONTROL_ORDER is either equal to | |
3827 * NC0 or NC1 the MS shall perform automomous cell re-selection | |
3828 */ | |
3829 | |
3830 grr_data->db.cr_cell = NULL; | |
3831 | |
3832 cs_calc_params( ); | |
3833 | |
3834 if( cs_find_candidate( ) ) | |
3835 { | |
3836 sig_cs_ctrl_new_candidate( grr_data->cs.reselect_cause ); | |
3837 | |
3838 cr_initiated = TRUE; | |
3839 } | |
3840 } | |
3841 break; | |
3842 | |
3843 case( CRDM_CR_CONT ): | |
3844 if( cs_find_candidate( ) ) | |
3845 { | |
3846 sig_cs_ctrl_new_candidate( grr_data->cs.reselect_cause ); | |
3847 } | |
3848 else | |
3849 { | |
3850 sig_cs_ctrl_no_more_candidate( grr_data->cs.reselect_cause ); | |
3851 } | |
3852 | |
3853 cr_initiated = TRUE; | |
3854 break; | |
3855 | |
3856 default: | |
3857 TRACE_ASSERT( mode EQ CRDM_T_RESELECT OR | |
3858 mode EQ CRDM_CR_CTRL OR | |
3859 mode EQ CRDM_CR_INITIAL OR | |
3860 mode EQ CRDM_CR_CONT ); | |
3861 break; | |
3862 } | |
3863 | |
3864 if( cr_initiated EQ TRUE ) | |
3865 { | |
3866 TRACE_EVENT_P2( "cs_cr_decision: mode %d, reselect_cause %d", | |
3867 mode, grr_data->cs.reselect_cause ); | |
3868 } | |
3869 | |
3870 return( cr_initiated ); | |
3871 | |
3872 }/* cs_cr_decision */ | |
3873 | |
3874 | |
3875 | |
3876 | |
3877 | |
3878 /* | |
3879 +------------------------------------------------------------------------------ | |
3880 | Function : cs_trace_nc_mval_lst | |
3881 +------------------------------------------------------------------------------ | |
3882 | Description : | |
3883 | | |
3884 | Parameters : void | |
3885 | | |
3886 +------------------------------------------------------------------------------ | |
3887 */ | |
3888 LOCAL void cs_trace_nc_mval_lst ( void ) | |
3889 { | |
3890 | |
3891 #if !defined (NTRACE) | |
3892 | |
3893 UBYTE read, write; | |
3894 USHORT arfcn[8]; | |
3895 UBYTE bsic[8]; | |
3896 T_NC_MVAL_STATUS status[8]; | |
3897 T_RXLEV_AVG rxlev_avg[8]; | |
3898 UBYTE rla_p_lev[8]; | |
3899 UBYTE rla_p_stat[8]; | |
3900 | |
3901 | |
3902 TRACE_FUNCTION( "cs_trace_nc_mval_lst" ); | |
3903 | |
3904 if( grr_data->cs.v_crp_trace EQ TRUE ) | |
3905 { | |
3906 memset( arfcn, 0xFF, sizeof( arfcn ) ); | |
3907 memset( bsic, 0xFF, sizeof( bsic ) ); | |
3908 memset( status, 0xFF, sizeof( status ) ); | |
3909 memset( rxlev_avg, 0xFF, sizeof( rxlev_avg ) ); | |
3910 memset( rla_p_lev, 0xFF, sizeof( rla_p_lev ) ); | |
3911 memset( rla_p_stat, 0xFF, sizeof( rla_p_stat ) ); | |
3912 | |
3913 write = 0; | |
3914 | |
3915 for( read = 0; read < MAX_NR_OF_NC_MVAL; read++ ) | |
3916 { | |
3917 if( grr_data->db.nc_mval_list.nc_mval[read].status NEQ NC_MVAL_STAT_NONE ) | |
3918 { | |
3919 arfcn[write] = grr_data->db.nc_mval_list.nc_mval[read].arfcn; | |
3920 bsic[write] = grr_data->db.nc_mval_list.nc_mval[read].sync_info.bsic; | |
3921 status[write] = grr_data->db.nc_mval_list.nc_mval[read].status; | |
3922 rla_p_lev [write] = grr_data->db.nc_mval_list.nc_mval[read].rla_p.lev; | |
3923 rla_p_stat [write] = grr_data->db.nc_mval_list.nc_mval[read].rla_p.stat; | |
3924 rxlev_avg [write] = grr_data->db.nc_mval_list.nc_mval[read].rxlev_avg; | |
3925 | |
3926 write++; | |
3927 } | |
3928 | |
3929 if( write EQ 8 ) | |
3930 { | |
3931 TRACE_EVENT_P8 | |
3932 ( "NC_MVAL_LIST ARFCN: %5d %5d %5d %5d %5d %5d %5d %5d", | |
3933 arfcn[0], arfcn[1], arfcn[2], arfcn[3], | |
3934 arfcn[4], arfcn[5], arfcn[6], arfcn[7] ); | |
3935 | |
3936 TRACE_EVENT_P8 | |
3937 ( "NC_MVAL_LIST BSIC: %5d %5d %5d %5d %5d %5d %5d %5d", | |
3938 bsic[0], bsic[1], bsic[2], bsic[3], | |
3939 bsic[4], bsic[5], bsic[6], bsic[7] ); | |
3940 | |
3941 TRACE_EVENT_P8 | |
3942 ( "NC_MVAL_LIST STATUS: %5d %5d %5d %5d %5d %5d %5d %5d", | |
3943 status[0], status[1], status[2], status[3], | |
3944 status[4], status[5], status[6], status[7] ); | |
3945 | |
3946 TRACE_EVENT_P8 | |
3947 ( "NC_MVAL_LIST T_RXLEV_AVG: %5d %5d %5d %5d %5d %5d %5d %5d", | |
3948 rxlev_avg[0], rxlev_avg[1], rxlev_avg[2], rxlev_avg[3], | |
3949 rxlev_avg[4], rxlev_avg[5], rxlev_avg[6], rxlev_avg[7] ); | |
3950 | |
3951 TRACE_EVENT_P8 | |
3952 ( "NC_MVAL_LIST rla_p.stat: %5d %5d %5d %5d %5d %5d %5d %5d", | |
3953 rla_p_stat[0], rla_p_stat[1], rla_p_stat[2], rla_p_stat[3], | |
3954 rla_p_stat[4], rla_p_stat[5], rla_p_stat[6], rla_p_stat[7] ); | |
3955 | |
3956 TRACE_EVENT_P8 | |
3957 ( "NC_MVAL_LIST rla_p.lev: %5d %5d %5d %5d %5d %5d %5d %5d", | |
3958 rla_p_lev[0], rla_p_lev[1], rla_p_lev[2], rla_p_lev[3], | |
3959 rla_p_lev[4], rla_p_lev[5], rla_p_lev[6], rla_p_lev[7] ); | |
3960 | |
3961 memset( arfcn, 0xFF, sizeof( arfcn ) ); | |
3962 memset( bsic, 0xFF, sizeof( bsic ) ); | |
3963 memset( status, 0xFF, sizeof( status ) ); | |
3964 memset( rxlev_avg, 0xFF, sizeof( rxlev_avg ) ); | |
3965 memset( rla_p_lev, 0xFF, sizeof( rla_p_lev ) ); | |
3966 memset( rla_p_stat, 0xFF, sizeof( rla_p_stat ) ); | |
3967 | |
3968 write = 0; | |
3969 } | |
3970 } | |
3971 | |
3972 if( write NEQ 0 ) | |
3973 { | |
3974 TRACE_EVENT_P8 | |
3975 ( "NC_MVAL_LIST ARFCN: %5d %5d %5d %5d %5d %5d %5d %5d", | |
3976 arfcn[0], arfcn[1], arfcn[2], arfcn[3], | |
3977 arfcn[4], arfcn[5], arfcn[6], arfcn[7] ); | |
3978 | |
3979 TRACE_EVENT_P8 | |
3980 ( "NC_MVAL_LIST BSIC: %5d %5d %5d %5d %5d %5d %5d %5d", | |
3981 bsic[0], bsic[1], bsic[2], bsic[3], | |
3982 bsic[4], bsic[5], bsic[6], bsic[7] ); | |
3983 | |
3984 TRACE_EVENT_P8 | |
3985 ( "NC_MVAL_LIST STATUS: %5d %5d %5d %5d %5d %5d %5d %5d", | |
3986 status[0], status[1], status[2], status[3], | |
3987 status[4], status[5], status[6], status[7] ); | |
3988 | |
3989 TRACE_EVENT_P8 | |
3990 ( "NC_MVAL_LIST T_RXLEV_AVG: %5d %5d %5d %5d %5d %5d %5d %5d", | |
3991 rxlev_avg[0], rxlev_avg[1], rxlev_avg[2], rxlev_avg[3], | |
3992 rxlev_avg[4], rxlev_avg[5], rxlev_avg[6], rxlev_avg[7] ); | |
3993 | |
3994 TRACE_EVENT_P8 | |
3995 ( "NC_MVAL_LIST rla_p.stat: %5d %5d %5d %5d %5d %5d %5d %5d", | |
3996 rla_p_stat[0], rla_p_stat[1], rla_p_stat[2], rla_p_stat[3], | |
3997 rla_p_stat[4], rla_p_stat[5], rla_p_stat[6], rla_p_stat[7] ); | |
3998 | |
3999 TRACE_EVENT_P8 | |
4000 ( "NC_MVAL_LIST rla_p.lev: %5d %5d %5d %5d %5d %5d %5d %5d", | |
4001 rla_p_lev[0], rla_p_lev[1], rla_p_lev[2], rla_p_lev[3], | |
4002 rla_p_lev[4], rla_p_lev[5], rla_p_lev[6], rla_p_lev[7] ); | |
4003 } | |
4004 } | |
4005 | |
4006 #endif /* #if !defined (NTRACE) */ | |
4007 | |
4008 } /* cs_trace_nc_mval_lst( ) */ | |
4009 | |
4010 | |
4011 /* | |
4012 +------------------------------------------------------------------------------ | |
4013 | Function : cs_stop_cr_meas | |
4014 +------------------------------------------------------------------------------ | |
4015 | Description : The function cs_stop_cr_meas () .... | |
4016 | | |
4017 | Parameters : void | |
4018 | | |
4019 +------------------------------------------------------------------------------ | |
4020 */ | |
4021 GLOBAL void cs_stop_cr_meas( void ) | |
4022 { | |
4023 TRACE_FUNCTION( "cs_stop_cr_meas" ); | |
4024 | |
4025 switch( grr_data->cs.cr_meas_mode ) | |
4026 { | |
4027 case( CS_CRMM_BA_GPRS ): | |
4028 if( grr_data->cs.stop_req EQ FALSE ) | |
4029 { | |
4030 PALLOC( mphp_cr_meas_stop_req, MPHP_CR_MEAS_STOP_REQ ); | |
4031 | |
4032 #if 0 | |
4033 | |
4034 /* | |
4035 * the timing for the MPHP_CR_MEAS_STOP_CON is not correct on | |
4036 * layer 1 side, so we are no longer consider the confirmation | |
4037 */ | |
4038 | |
4039 grr_data->cs.stop_req = TRUE; | |
4040 | |
4041 #endif /* #if 0 */ | |
4042 | |
4043 PSEND( hCommL1, mphp_cr_meas_stop_req ); | |
4044 } | |
4045 break; | |
4046 case( CS_CRMM_BA_BCCH ): | |
4047 grr_data->cs.cr_meas_update = FALSE; | |
4048 break; | |
4049 } | |
4050 } /* cs_stop_cr_meas() */ | |
4051 | |
4052 | |
4053 /* | |
4054 +------------------------------------------------------------------------------ | |
4055 | Function : cs_req_cr_meas | |
4056 +------------------------------------------------------------------------------ | |
4057 | Description : The function cs_req_cr_meas () .... | |
4058 | | |
4059 | Parameters : void | |
4060 | | |
4061 +------------------------------------------------------------------------------ | |
4062 */ | |
4063 GLOBAL void cs_req_cr_meas ( void ) | |
4064 { | |
4065 TRACE_FUNCTION( "cs_req_cr_meas" ); | |
4066 | |
4067 if( nc_data->c_cell NEQ 0 ) | |
4068 { | |
4069 if( grr_data->cs_meas.packet_mode NEQ PACKET_MODE_PTM ) | |
4070 { | |
4071 PALLOC( mphp_cr_meas_req, MPHP_CR_MEAS_REQ ); | |
4072 | |
4073 cs_fill_cr_meas_req( mphp_cr_meas_req, grr_data->cs.list_id ); | |
4074 | |
4075 grr_data->cs.list_id++; | |
4076 | |
4077 PSEND( hCommL1, mphp_cr_meas_req ); | |
4078 } | |
4079 else | |
4080 { | |
4081 PALLOC( mphp_tcr_meas_req, MPHP_TCR_MEAS_REQ ); | |
4082 | |
4083 grr_data->cs.last_assignment_id++; | |
4084 grr_data->cs.cr_meas_update = TRUE; | |
4085 | |
4086 cs_fill_cr_meas_req( (T_MPHP_CR_MEAS_REQ*)mphp_tcr_meas_req, | |
4087 grr_data->cs.last_assignment_id ); | |
4088 | |
4089 PSEND( hCommL1, mphp_tcr_meas_req ); | |
4090 } | |
4091 | |
4092 grr_data->cs.stop_req = FALSE; | |
4093 } | |
4094 } /* cs_req_cr_meas() */ | |
4095 | |
4096 | |
4097 /* | |
4098 +------------------------------------------------------------------------------ | |
4099 | Function : cs_fill_cr_meas_req | |
4100 +------------------------------------------------------------------------------ | |
4101 | Description : ... | |
4102 | | |
4103 | Parameters : prim - Pointer to primitive buffer | |
4104 | | |
4105 +------------------------------------------------------------------------------ | |
4106 */ | |
4107 GLOBAL void cs_fill_cr_meas_req ( T_MPHP_CR_MEAS_REQ *prim, UBYTE id ) | |
4108 { | |
4109 UBYTE i; /* used for counting */ | |
4110 | |
4111 TRACE_FUNCTION( "cs_fill_cr_meas_req" ); | |
4112 | |
4113 prim->nb_carrier = nc_data->c_cell; | |
4114 prim->list_id = id; | |
4115 | |
4116 for( i = 0; i < nc_data->c_cell; i++ ) | |
4117 { | |
4118 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
4119 prim->carrier_list[i] = grr_g23_arfcn_to_l1(nc_data->cell[i].arfcn); | |
4120 #else | |
4121 prim->carrier_list[i] = nc_data->cell[i].arfcn; | |
4122 #endif | |
4123 } | |
4124 | |
4125 #ifdef _SIMULATION_ | |
4126 | |
4127 for( i = nc_data->c_cell; i < MPHP_NUMC_BA_GPRS_SC; i++ ) | |
4128 { | |
4129 prim->carrier_list[i] = 0xFFFF; | |
4130 } | |
4131 | |
4132 #endif /* #ifdef _SIMULATION_ */ | |
4133 | |
4134 } /* cs_fill_cr_meas_req() */ | |
4135 | |
4136 | |
4137 /* | |
4138 +------------------------------------------------------------------------------ | |
4139 | Function : cs_reset_all_cell_results | |
4140 +------------------------------------------------------------------------------ | |
4141 | Description : The function cs_reset_all_cell_results() .... | |
4142 | | |
4143 | Parameters : void | |
4144 | | |
4145 +------------------------------------------------------------------------------ | |
4146 */ | |
4147 GLOBAL void cs_reset_all_cell_results ( void ) | |
4148 { | |
4149 UBYTE i; /* used for counting */ | |
4150 | |
4151 TRACE_FUNCTION( "cs_reset_all_cell_results" ); | |
4152 | |
4153 for( i = 0; i < MPHP_NUMC_BA_GPRS_SC; i++ ) | |
4154 { | |
4155 cs_reset_meas_result( &nc_data->cell[i] ); | |
4156 } | |
4157 } /* cs_reset_all_cell_results () */ | |
4158 | |
4159 /* | |
4160 +------------------------------------------------------------------------------ | |
4161 | Function : cs_reset_all_rxlev_results | |
4162 +------------------------------------------------------------------------------ | |
4163 | Description : The function cs_reset_all_rxlev_results() .... | |
4164 | | |
4165 | Parameters : ... | |
4166 | | |
4167 +------------------------------------------------------------------------------ | |
4168 */ | |
4169 GLOBAL void cs_reset_all_rxlev_results ( void ) | |
4170 { | |
4171 UBYTE i; /* used for counting */ | |
4172 | |
4173 TRACE_FUNCTION( "cs_reset_all_rxlev_results" ); | |
4174 | |
4175 for( i = 0; i < MPHP_NUMC_BA_GPRS_SC; i++ ) | |
4176 { | |
4177 nc_data->cell[i].rxlev_data.acc = 0; | |
4178 nc_data->cell[i].rxlev_data.nbr = 0; | |
4179 } | |
4180 } /* cs_reset_all_rxlev_results () */ | |
4181 | |
4182 /* | |
4183 +------------------------------------------------------------------------------ | |
4184 | Function : cs_reset_meas_result | |
4185 +------------------------------------------------------------------------------ | |
4186 | Description : The function cs_reset_meas_result() .... | |
4187 | | |
4188 | Parameters : ... | |
4189 | | |
4190 +------------------------------------------------------------------------------ | |
4191 */ | |
4192 GLOBAL void cs_reset_meas_result ( T_CELL *cell ) | |
4193 { | |
4194 T_RLA_P_DATA *rla_p_data = &cell->rla_p_data; | |
4195 T_RXLEV_DATA *rxlev_data = &cell->rxlev_data; | |
4196 | |
4197 UBYTE i; /* used for counting */ | |
4198 | |
4199 TRACE_FUNCTION( "cs_reset_meas_result" ); | |
4200 TRACE_EVENT_P2( "cs_reset_meas_result arfcn =%ld LOI=%ld",cell->arfcn,rla_p_data->loi ); | |
4201 | |
4202 rla_p_data->loi = CS_IDX_NOT_USED; | |
4203 rla_p_data->ovrflw = FALSE; | |
4204 | |
4205 for( i = 0; i < CS_MAX_MEAS_RSLT; i++ ) | |
4206 { | |
4207 rla_p_data->meas[i].cnt = 0; | |
4208 rla_p_data->meas[i].acc = 0; | |
4209 rla_p_data->meas[i].rpt_prd = 0; | |
4210 } | |
4211 | |
4212 rxlev_data->acc = 0; | |
4213 rxlev_data->nbr = 0; | |
4214 } /* cs_reset_meas_result () */ | |
4215 | |
4216 /* | |
4217 +------------------------------------------------------------------------------ | |
4218 | Function : cs_fill_meas_rslt | |
4219 +------------------------------------------------------------------------------ | |
4220 | Description : ... | |
4221 | | |
4222 | Parameters : ... | |
4223 | | |
4224 +------------------------------------------------------------------------------ | |
4225 */ | |
4226 GLOBAL void cs_fill_meas_rslt ( T_MPHP_CR_MEAS_IND *mphp_cr_meas_ind, | |
4227 T_MPHP_TCR_MEAS_IND *mphp_tcr_meas_ind ) | |
4228 { | |
4229 T_RLA_P_DATA *rla_p_data; | |
4230 T_RXLEV_DATA *rxlev_data; | |
4231 | |
4232 T_RXLEV_DATA_NBR del_nbr; | |
4233 | |
4234 UBYTE i; | |
4235 UBYTE index = 0; | |
4236 BOOL ovrflw = FALSE; | |
4237 | |
4238 UBYTE cnt; | |
4239 SHORT acc; | |
4240 USHORT rpt_prd; | |
4241 | |
4242 TRACE_FUNCTION( "cs_fill_meas_rslt" ); | |
4243 | |
4244 if( mphp_cr_meas_ind NEQ NULL ) | |
4245 { | |
4246 rpt_prd = mphp_cr_meas_ind->reporting_period; | |
4247 } | |
4248 else | |
4249 { | |
4250 rpt_prd = CS_RPT_PRD_PTM; | |
4251 } | |
4252 | |
4253 /* | |
4254 * Process all data relevant for RLA_P derivation | |
4255 */ | |
4256 | |
4257 for( i = 0; i < nc_data->c_cell; i++ ) | |
4258 { | |
4259 rla_p_data = &nc_data->cell[i].rla_p_data; | |
4260 rxlev_data = &nc_data->cell[i].rxlev_data; | |
4261 | |
4262 if( mphp_cr_meas_ind NEQ NULL ) | |
4263 { | |
4264 cnt = 1; | |
4265 if((signed char)mphp_cr_meas_ind->p_ncell_meas[i].rxlev <0) | |
4266 { | |
4267 acc = 0; | |
4268 } | |
4269 else | |
4270 { | |
4271 acc = (signed char)mphp_cr_meas_ind->p_ncell_meas[i].rxlev; | |
4272 } | |
4273 } | |
4274 else | |
4275 { | |
4276 cnt = mphp_tcr_meas_ind->acc_nbr[i]; | |
4277 if((SHORT)mphp_tcr_meas_ind->acc_level[i] <0) | |
4278 { | |
4279 acc = 0; | |
4280 } | |
4281 else | |
4282 { | |
4283 acc = mphp_tcr_meas_ind->acc_level[i]; | |
4284 } | |
4285 } | |
4286 | |
4287 if( rla_p_data->loi NEQ CS_IDX_NOT_USED ) | |
4288 { | |
4289 if( rla_p_data->loi EQ CS_MAX_MEAS_RSLT - 1 ) | |
4290 { | |
4291 ovrflw = TRUE; | |
4292 } | |
4293 else | |
4294 { | |
4295 index = rla_p_data->loi + 1; | |
4296 } | |
4297 } | |
4298 | |
4299 if( cnt EQ 0 ) | |
4300 { | |
4301 if( rla_p_data->meas[index].cnt EQ 0 ) | |
4302 { | |
4303 rla_p_data->meas[index].rpt_prd += rpt_prd; | |
4304 } | |
4305 else | |
4306 { | |
4307 rla_p_data->meas[index].cnt = 0; | |
4308 rla_p_data->meas[index].acc = 0; | |
4309 rla_p_data->meas[index].rpt_prd = rpt_prd; | |
4310 } | |
4311 } | |
4312 else | |
4313 { | |
4314 rla_p_data->meas[index].cnt = cnt; | |
4315 rla_p_data->meas[index].acc = acc; | |
4316 rla_p_data->meas[index].rpt_prd = rpt_prd; | |
4317 | |
4318 rla_p_data->loi = index; | |
4319 | |
4320 /* if an overflow once occured it will be forever */ | |
4321 if( rla_p_data->ovrflw EQ FALSE ) | |
4322 { | |
4323 rla_p_data->ovrflw = ovrflw; | |
4324 } | |
4325 } | |
4326 | |
4327 /* | |
4328 * Process all data relevant for average RXLEV derivation | |
4329 */ | |
4330 | |
4331 if( cnt NEQ 0 ) | |
4332 { | |
4333 if( rxlev_data->nbr > RXLEV_MAX_NBR - cnt ) | |
4334 { | |
4335 del_nbr = cnt - ( RXLEV_MAX_NBR - rxlev_data->nbr ); | |
4336 rxlev_data->acc -= del_nbr * ( rxlev_data->acc / rxlev_data->nbr ); | |
4337 rxlev_data->nbr -= del_nbr; | |
4338 } | |
4339 | |
4340 rxlev_data->acc += ( acc * RXLEV_ACRCY ); | |
4341 rxlev_data->nbr += cnt; | |
4342 } | |
4343 } | |
4344 } /* cs_fill_meas_rslt() */ | |
4345 | |
4346 /* | |
4347 +------------------------------------------------------------------------------ | |
4348 | Function : cs_get_rla_p | |
4349 +------------------------------------------------------------------------------ | |
4350 | Description : The function cs_get_rla_p() .... | |
4351 | | |
4352 | Parameters : rla_p_data - pointer to RLA_P raw data | |
4353 | | |
4354 +------------------------------------------------------------------------------ | |
4355 */ | |
4356 GLOBAL BOOL cs_get_rla_p( T_RLA_P_DATA *rla_p_data, UBYTE *rla_p ) | |
4357 { | |
4358 BOOL s_avg; /* status of average RXLEV value */ | |
4359 LONG avg; /* average RXLEV value used for cell re-selection */ | |
4360 LONG cnt = 0; /* number of accumulated measurement samples */ | |
4361 LONG acc = 0; /* accumulated receive level values */ | |
4362 ULONG run_avg_prd = 0; /* running average period */ | |
4363 UBYTE c_meas = 0; /* number of measurements */ | |
4364 UBYTE index = rla_p_data->loi; | |
4365 /* index to actual used measurement result */ | |
4366 BOOL v_meas_left = rla_p_data->loi NEQ CS_IDX_NOT_USED; | |
4367 /* indicates whether more measurement results */ | |
4368 /* are not yet considered */ | |
4369 | |
4370 TRACE_FUNCTION( "cs_get_rla_p" ); | |
4371 | |
4372 while( | |
4373 ( | |
4374 c_meas < CS_MIN_RLA_P_SAMPLES OR | |
4375 run_avg_prd < CS_MIN_RUN_AVG_PRD | |
4376 ) | |
4377 AND | |
4378 ( | |
4379 v_meas_left EQ TRUE | |
4380 ) | |
4381 ) | |
4382 { | |
4383 /* | |
4384 * check whether valid measurement results are available | |
4385 */ | |
4386 if( rla_p_data->meas[index].cnt NEQ 0 AND | |
4387 c_meas < CS_MAX_MEAS_RSLT ) | |
4388 { | |
4389 c_meas++; | |
4390 | |
4391 /* | |
4392 * accumulate individual measurement results | |
4393 */ | |
4394 run_avg_prd += rla_p_data->meas[index].rpt_prd; | |
4395 cnt += rla_p_data->meas[index].cnt; | |
4396 acc += rla_p_data->meas[index].acc; | |
4397 | |
4398 /* determine the next index to be used for RLA_P calculation */ | |
4399 if( index EQ 0 ) | |
4400 { | |
4401 if( rla_p_data->ovrflw EQ TRUE ) | |
4402 { | |
4403 index = CS_MAX_MEAS_RSLT - 1; | |
4404 } | |
4405 else | |
4406 { | |
4407 v_meas_left= FALSE; | |
4408 } | |
4409 } | |
4410 else | |
4411 { | |
4412 index--; | |
4413 } | |
4414 | |
4415 | |
4416 } | |
4417 else | |
4418 { | |
4419 v_meas_left = FALSE; | |
4420 } | |
4421 } | |
4422 | |
4423 /* | |
4424 * calculate status of RLA_P | |
4425 */ | |
4426 if( cnt EQ 0 ) | |
4427 { | |
4428 s_avg = CS_RLA_P_NOT_AVAIL; | |
4429 } | |
4430 else if( | |
4431 ( | |
4432 c_meas < CS_MIN_RLA_P_SAMPLES | |
4433 ) | |
4434 OR | |
4435 ( | |
4436 run_avg_prd < CS_MIN_RUN_AVG_PRD | |
4437 AND | |
4438 c_meas < CS_MAX_MEAS_RSLT | |
4439 ) | |
4440 ) | |
4441 { | |
4442 s_avg = CS_RLA_P_NOT_VALID; | |
4443 } | |
4444 else | |
4445 { | |
4446 s_avg = CS_RLA_P_VALID; | |
4447 } | |
4448 | |
4449 if( cnt > 0 ) | |
4450 { | |
4451 /* | |
4452 * calculate RLA_P | |
4453 */ | |
4454 avg = acc / cnt; | |
4455 | |
4456 | |
4457 /* | |
4458 * clip RLA_P to values between 0 and 63 | |
4459 */ | |
4460 if( (signed char)( avg ) < CGRLC_RXLEV_MIN ) | |
4461 { | |
4462 avg = CGRLC_RXLEV_MIN; | |
4463 } | |
4464 else if ( (signed char)( avg ) > CGRLC_RXLEV_MAX ) | |
4465 { | |
4466 avg = CGRLC_RXLEV_MAX; | |
4467 } | |
4468 } | |
4469 else | |
4470 { | |
4471 avg = CGRLC_RXLEV_NONE; | |
4472 } | |
4473 | |
4474 | |
4475 *rla_p = (UBYTE)avg; | |
4476 | |
4477 return( s_avg ); | |
4478 | |
4479 } /* cs_get_rla_p () */ | |
4480 | |
4481 /* | |
4482 +------------------------------------------------------------------------------ | |
4483 | Function : cs_get_rxlev_avg | |
4484 +------------------------------------------------------------------------------ | |
4485 | Description : The function cs_get_rxlev_avg() .... | |
4486 | | |
4487 | Parameters : rxlev_data - pointer to RXLEV raw data | |
4488 | | |
4489 +------------------------------------------------------------------------------ | |
4490 */ | |
4491 GLOBAL T_RXLEV_AVG cs_get_rxlev_avg( T_RXLEV_DATA *rxlev_data ) | |
4492 { | |
4493 T_RXLEV_AVG rxlev_avg; | |
4494 | |
4495 TRACE_FUNCTION( "cs_get_rxlev_avg" ); | |
4496 | |
4497 | |
4498 if( rxlev_data->nbr EQ 0 ) | |
4499 { | |
4500 rxlev_avg = RXLEV_AVG_INVALID; | |
4501 } | |
4502 else | |
4503 { | |
4504 rxlev_avg = | |
4505 ( T_RXLEV_AVG )( rxlev_data->acc / ( rxlev_data->nbr * RXLEV_ACRCY ) ); | |
4506 } | |
4507 | |
4508 TRACE_EVENT_P2("1_cs_get_rxlev_avg: nbr=%ld rx_avg=%ld",rxlev_data->nbr,rxlev_avg); | |
4509 | |
4510 return( rxlev_avg ); | |
4511 } /* cs_get_rxlev_avg () */ | |
4512 | |
4513 /* | |
4514 +------------------------------------------------------------------------------ | |
4515 | Function : cs_tcr_meas_ind_to_pl | |
4516 +------------------------------------------------------------------------------ | |
4517 | Description : The function cs_tcr_meas_ind_to_pl () forwards the cell | |
4518 | re-selection measurement results catched during packet transfer | |
4519 | mode to ALR. | |
4520 | | |
4521 | Parameters : prim - pointer to primitive payload | |
4522 | | |
4523 +------------------------------------------------------------------------------ | |
4524 */ | |
4525 GLOBAL void cs_tcr_meas_ind_to_pl ( T_MPHP_TCR_MEAS_IND * prim ) | |
4526 { | |
4527 UBYTE i; /* used for counting */ | |
4528 | |
4529 TRACE_FUNCTION( "cs_tcr_meas_ind_to_pl" ); | |
4530 | |
4531 { | |
4532 PALLOC( tb_meas_ind, TB_MEAS_IND ); | |
4533 | |
4534 for( i = 0; i < TB_BA_LIST_SIZE; i++ ) | |
4535 { | |
4536 if(( grr_data->cs.cr_meas_update EQ TRUE) AND | |
4537 (nc_data->cell[i].arfcn NEQ 0)) | |
4538 { | |
4539 if(nc_data->cell[i].arfcn NEQ 0) | |
4540 { | |
4541 tb_meas_ind->tb_meas_result[i].arfcn = grr_g23_arfcn_to_l1(nc_data->cell[i].arfcn); | |
4542 } | |
4543 else | |
4544 { | |
4545 tb_meas_ind->tb_meas_result[i].arfcn = TB_INVALID_ARFCN; | |
4546 } | |
4547 } | |
4548 else | |
4549 { | |
4550 tb_meas_ind->tb_meas_result[i].arfcn = TB_INVALID_ARFCN; | |
4551 } | |
4552 | |
4553 tb_meas_ind->tb_meas_result[i].rxlev = prim->acc_level[i]; | |
4554 tb_meas_ind->tb_meas_result[i].num_meas = prim->acc_nbr[i]; | |
4555 } | |
4556 | |
4557 PSEND( hCommPL, tb_meas_ind ); | |
4558 } | |
4559 } /* cs_tcr_meas_ind_to_pl() */ | |
4560 | |
4561 /* | |
4562 +------------------------------------------------------------------------------ | |
4563 | Function : cs_create_cr_cell | |
4564 +------------------------------------------------------------------------------ | |
4565 | Description : | |
4566 | | |
4567 | Parameters : | |
4568 | | |
4569 +------------------------------------------------------------------------------ | |
4570 */ | |
4571 GLOBAL T_NC_MVAL* cs_create_cr_cell ( USHORT arfcn, UBYTE bsic ) | |
4572 { | |
4573 T_NC_MVAL *nc_mval; | |
4574 UBYTE nc_mval_idx; | |
4575 | |
4576 TRACE_FUNCTION( "cs_create_cr_cell" ); | |
4577 | |
4578 /* if the new selected cell is not found in the neighbour cell list */ | |
4579 nc_mval = grr_get_nc_mval( RRGRR_INVALID_ARFCN, RRGRR_INVALID_BSIC, &nc_mval_idx ); | |
4580 | |
4581 if( nc_mval NEQ NULL ) | |
4582 { | |
4583 nc_mval->arfcn = arfcn; | |
4584 nc_mval->sync_info.bsic = bsic; | |
4585 | |
4586 /* | |
4587 * The function cs_create_cr_cell is only called in case of processing a | |
4588 * packet cell change order. If the packet cell change order has been | |
4589 * received on a cell without PBCCH, GRR should forward the RRGRR_CR_REQ | |
4590 * with parameter CR_NEW in all cases. This is forced by setting the | |
4591 * synchronisation status to STAT_SYNC_OK. | |
4592 */ | |
4593 if( grr_is_pbcch_present( ) ) | |
4594 { | |
4595 TRACE_EVENT( "cs_create_cr_cell: cell not part of neighbour cell list" ); | |
4596 | |
4597 nc_mval->sync_info.sync.status = STAT_SYNC_NONE; | |
4598 } | |
4599 else | |
4600 { | |
4601 nc_mval->sync_info.sync.status = STAT_SYNC_OK; | |
4602 } | |
4603 | |
4604 grr_data->db.cr_cell = &grr_data->db.nc_nw_slctd.strgst; | |
4605 grr_data->db.cr_cell->idx = nc_mval_idx; | |
4606 grr_data->db.cr_cell->mode = CS_MODE_IDLE; | |
4607 grr_data->db.cr_cell->avail_time = 0; | |
4608 } | |
4609 | |
4610 return( nc_mval ); | |
4611 | |
4612 } /* cs_create_cr_cell() */ | |
4613 | |
4614 /* | |
4615 +------------------------------------------------------------------------------ | |
4616 | Function : cs_get_nc_rpt_prd_idle | |
4617 +------------------------------------------------------------------------------ | |
4618 | Description : | |
4619 | | |
4620 | Parameters : | |
4621 | | |
4622 +------------------------------------------------------------------------------ | |
4623 */ | |
4624 LOCAL T_TIME cs_get_nc_rpt_prd_idle ( void ) | |
4625 { | |
4626 T_TIME reporting_period; | |
4627 ULONG small_int_multi; /* smallest integer multiple of DRX period */ | |
4628 ULONG drx_period; /* DRX period in milliseconds */ | |
4629 | |
4630 TRACE_FUNCTION( "cs_get_nc_rpt_prd_idle" ); | |
4631 | |
4632 reporting_period = GET_NC_RPT_PRD( grr_data->db.nc_ref_lst.param->rep_per_i ); | |
4633 drx_period = meas_im_get_drx_period_seconds( ); | |
4634 drx_period = M_ROUND_UP( drx_period, DRX_NORM_FACTOR ); | |
4635 | |
4636 /* | |
4637 * In packet idle mode, the reporting period is NC_REPORTING_PERIOD_I | |
4638 * rounded off to the nearest smaller integer multiple of DRX period | |
4639 * if NC_REPORTING_PERIOD_I is greater than DRX period, else, the | |
4640 * reporting period is DRX period. | |
4641 */ | |
4642 if( drx_period NEQ NO_PAGING ) | |
4643 { | |
4644 if( reporting_period > drx_period ) | |
4645 { | |
4646 small_int_multi = reporting_period / drx_period; | |
4647 reporting_period = drx_period * small_int_multi; | |
4648 } | |
4649 else | |
4650 { | |
4651 reporting_period = drx_period; | |
4652 } | |
4653 } | |
4654 | |
4655 return( reporting_period ); | |
4656 | |
4657 } /* cs_get_nc_rpt_prd_idle() */ | |
4658 | |
4659 | |
4660 /* | |
4661 +------------------------------------------------------------------------------ | |
4662 | Function : cs_reset_meas_rep_params | |
4663 +------------------------------------------------------------------------------ | |
4664 | Description : This function will reset measurement reporting parameters | |
4665 | | |
4666 | Parameters : db - pointer to serving cell database | |
4667 | | |
4668 +------------------------------------------------------------------------------ | |
4669 */ | |
4670 GLOBAL void cs_reset_meas_rep_params ( T_SC_DATABASE *db ) | |
4671 { | |
4672 TRACE_FUNCTION( "cs_reset_meas_rep_params" ); | |
4673 | |
4674 db->nc_ms.ncmeas.param.ctrl_order = NC_RESET; | |
4675 db->nc_ms.ncmeas.param.rep_per_i = 0; | |
4676 db->nc_ms.ncmeas.param.rep_per_t = 0; | |
4677 | |
4678 } /* cs_reset_meas_rep_params() */ | |
4679 | |
4680 /* | |
4681 +------------------------------------------------------------------------------ | |
4682 | Function : cs_check_nc_sync_timer | |
4683 +------------------------------------------------------------------------------ | |
4684 | Description : Handles the nc sync timer of 10 sec in case of PIM_PBCCH and | |
4685 | PTM_PBCCH | |
4686 | | |
4687 | Parameters : reporting_period | |
4688 | | |
4689 +------------------------------------------------------------------------------ | |
4690 */ | |
4691 | |
4692 | |
4693 GLOBAL void cs_check_nc_sync_timer(USHORT reporting_pd) | |
4694 { | |
4695 if(!grr_data->db.cnt_nc_six.candid) return; | |
4696 grr_data->cs.nc_sync_rep_pd += reporting_pd; | |
4697 | |
4698 | |
4699 if(grr_data->cs.nc_sync_rep_pd >= CS_NCSYNC_RPT_PRD_PIM) | |
4700 { | |
4701 PALLOC( rrgrr_check_bsic_req, RRGRR_NCELL_SYNC_REQ ); | |
4702 rrgrr_check_bsic_req->sync_type = SYNC_RECONFIRM; | |
4703 PSEND( hCommRR, rrgrr_check_bsic_req ); | |
4704 /*subtracting nc_sync_rep_pd from CS_NCSYNC_RPT_PRD_PIM wil provide take care | |
4705 of periodicity of non-uniform reporting_period values*/ | |
4706 TRACE_EVENT_P1("GRR_NC_SYNC:EXPIRY: nc_sync_rep_pd=%d", grr_data->cs.nc_sync_rep_pd); | |
4707 grr_data->cs.nc_sync_rep_pd -= CS_NCSYNC_RPT_PRD_PIM; | |
4708 } | |
4709 return; | |
4710 | |
4711 } | |
4712 | |
4713 /* | |
4714 +------------------------------------------------------------------------------ | |
4715 | Function : cs_process_serving_cell_data | |
4716 +------------------------------------------------------------------------------ | |
4717 | Description : This function is used to fill rxlev and interference measurements | |
4718 | of the serving cell | |
4719 | | |
4720 | Parameters : rxlev, iscell | |
4721 | | |
4722 +------------------------------------------------------------------------------ | |
4723 */ | |
4724 LOCAL BOOL cs_process_serving_cell_data ( UBYTE *rxlev_scell, UBYTE *v_i_scell, | |
4725 UBYTE *i_scell, UBYTE *used_bits, | |
4726 BOOL *rsc_avail, BOOL *isc_avail ) | |
4727 | |
4728 { | |
4729 TRACE_FUNCTION( "cs_process_serving_cell_data" ); | |
4730 | |
4731 *used_bits += NC_RXLEV_SCELL_LEN; | |
4732 | |
4733 if( grr_data->db.scell_info.rxlev_avg EQ RXLEV_AVG_INVALID ) | |
4734 { | |
4735 TRACE_ERROR( "cs_build_xxx_meas_rpt no RXLEV of serving cell" ); | |
4736 return( FALSE ); | |
4737 } | |
4738 else | |
4739 { | |
4740 *rsc_avail = TRUE; | |
4741 *rxlev_scell = grr_data->db.scell_info.rxlev_avg; | |
4742 } | |
4743 | |
4744 /* process interference measurement of serving cell */ | |
4745 *used_bits += PMR_FLAG_LEN; | |
4746 *v_i_scell = FALSE; | |
4747 | |
4748 if( grr_is_pbcch_present( ) EQ TRUE AND | |
4749 psc_db->paging_group.kc NEQ 0 AND | |
4750 grr_data->cs_meas.packet_mode EQ PACKET_MODE_PIM ) | |
4751 { | |
4752 T_p_frequency_par freq_par; | |
4753 | |
4754 if( grr_get_pccch_freq_par | |
4755 ( ( UBYTE )( grr_imsi_mod( ) % psc_db->paging_group.kc ), | |
4756 &freq_par.p_chan_sel, &freq_par.p_freq_list ) ) | |
4757 { | |
4758 T_MEAS_IM_CARRIER ma; | |
4759 UBYTE written_bits; | |
4760 T_ilev_abs i_level; | |
4761 | |
4762 meas_im_set_carrier( &ma, &freq_par ); | |
4763 | |
4764 written_bits = meas_im_get_abs_i_level( &ma, &i_level ); | |
4765 | |
4766 if( written_bits > CGRLC_MAX_TIMESLOTS * PMR_FLAG_LEN ) | |
4767 { | |
4768 *v_i_scell = TRUE; | |
4769 *used_bits += NC_IF_SCELL_LEN; | |
4770 | |
4771 if ( i_level.v_ilevabs0 EQ TRUE ) | |
4772 { | |
4773 *i_scell = i_level.ilevabs0; | |
4774 *isc_avail = TRUE; | |
4775 } | |
4776 else if( i_level.v_ilevabs1 EQ TRUE ) | |
4777 { | |
4778 *i_scell = i_level.ilevabs1; | |
4779 *isc_avail = TRUE; | |
4780 } | |
4781 else if( i_level.v_ilevabs2 EQ TRUE ) | |
4782 { | |
4783 *i_scell = i_level.ilevabs2; | |
4784 *isc_avail = TRUE; | |
4785 } | |
4786 else if( i_level.v_ilevabs3 EQ TRUE ) | |
4787 { | |
4788 *i_scell = i_level.ilevabs3; | |
4789 *isc_avail = TRUE; | |
4790 } | |
4791 else if( i_level.v_ilevabs4 EQ TRUE ) | |
4792 { | |
4793 *i_scell = i_level.ilevabs4; | |
4794 *isc_avail = TRUE; | |
4795 } | |
4796 else if( i_level.v_ilevabs5 EQ TRUE ) | |
4797 { | |
4798 *i_scell = i_level.ilevabs5; | |
4799 *isc_avail = TRUE; | |
4800 } | |
4801 else if( i_level.v_ilevabs6 EQ TRUE ) | |
4802 { | |
4803 *i_scell = i_level.ilevabs6; | |
4804 *isc_avail = TRUE; | |
4805 } | |
4806 else if( i_level.v_ilevabs7 EQ TRUE ) | |
4807 { | |
4808 *i_scell = i_level.ilevabs7; | |
4809 *isc_avail = TRUE; | |
4810 } | |
4811 else | |
4812 { | |
4813 TRACE_ERROR( "cs_process_serving_cell_data corrupted I_LEVEL data" ); | |
4814 return( FALSE ); | |
4815 } | |
4816 } | |
4817 } | |
4818 } | |
4819 return(TRUE); | |
4820 }/* cs_process_serving_cell_data */ | |
4821 | |
4822 #if defined (REL99) AND defined (TI_PS_FF_EMR) | |
4823 /* | |
4824 +------------------------------------------------------------------------------ | |
4825 | Function : cs_send_enh_meas_rpt | |
4826 +------------------------------------------------------------------------------ | |
4827 | Description : This function is used to send enh meas report to the network | |
4828 | | |
4829 | Parameters : void | |
4830 | | |
4831 +------------------------------------------------------------------------------ | |
4832 */ | |
4833 GLOBAL BOOL cs_send_enh_meas_rpt (void) | |
4834 { | |
4835 T_U_ENHNC_MEAS_REPORT enh_meas_rpt; | |
4836 BOOL rpt_send; | |
4837 | |
4838 TRACE_FUNCTION( "cs_send_enh_meas_rpt" ); | |
4839 | |
4840 if(grr_is_pbcch_present()) | |
4841 { | |
4842 cs_form_enh_cell_list(); | |
4843 } | |
4844 else | |
4845 { | |
4846 cs_form_ba_bcch_enh_cell_list(); | |
4847 } | |
4848 | |
4849 cs_nc_sort_and_update_emr_info(); | |
4850 | |
4851 memset (&enh_meas_rpt, 0, sizeof(T_U_ENHNC_MEAS_REPORT)); | |
4852 | |
4853 rpt_send = cs_build_enh_meas_rpt(&enh_meas_rpt); | |
4854 | |
4855 if( rpt_send EQ TRUE ) | |
4856 { | |
4857 sig_cs_ctrl_enh_meas_report(&enh_meas_rpt); | |
4858 } | |
4859 | |
4860 return(rpt_send); | |
4861 | |
4862 } /* cs_send_enh_meas_rpt() */ | |
4863 | |
4864 | |
4865 /* | |
4866 +------------------------------------------------------------------------------ | |
4867 | Function : cs_form_enh_cell_list | |
4868 +------------------------------------------------------------------------------ | |
4869 | Description : This function is used to form enhanced cell list from BA list | |
4870 | (nc_ref_lst) and Measured values list(nc_mval_list) | |
4871 | | |
4872 | | |
4873 | Parameters : Nil | |
4874 | | |
4875 +------------------------------------------------------------------------------ | |
4876 */ | |
4877 LOCAL void cs_form_enh_cell_list(void) | |
4878 { | |
4879 UBYTE i = 0, n = 0, j; | |
4880 UBYTE nc_ref_index_arfcn, nc_ref_index_bsic; | |
4881 | |
4882 TRACE_FUNCTION( "cs_form_enh_cell_list" ); | |
4883 | |
4884 memset((grr_data->db.enh_cell_list), 0xFF, sizeof(T_ENH_CELL_LIST)*MAX_NR_OF_NCELL); | |
4885 | |
4886 grr_data->db.cnt_enh_cell_list = 0; | |
4887 | |
4888 /* Check one entry of Measured values list against all entries of BA list */ | |
4889 while(i < MAX_NR_OF_NC_MVAL AND n < MAX_NR_OF_NCELL) | |
4890 { | |
4891 if( (grr_data->db.nc_mval_list.nc_mval[i].status EQ NC_MVAL_STAT_ASSIGNED) | |
4892 AND | |
4893 (grr_data->db.nc_mval_list.nc_mval[i].arfcn NEQ RRGRR_INVALID_ARFCN) | |
4894 AND | |
4895 (grr_data->db.nc_mval_list.nc_mval[i].sync_info.sync.status EQ | |
4896 STAT_SYNC_OK) | |
4897 AND | |
4898 (grr_data->db.nc_mval_list.nc_mval[i].rla_p.stat EQ CS_RLA_P_VALID) ) | |
4899 { | |
4900 nc_ref_index_arfcn = NOT_SET; /* Will be set the 1st time ARFCN matches | |
4901 in the BA list */ | |
4902 nc_ref_index_bsic = NOT_SET; /* Will be set the 1st time ARFCN-BSIC pair | |
4903 matches in the BA list */ | |
4904 | |
4905 /* Comparison with BA list */ | |
4906 for (j = 0; j < grr_data->db.nc_ref_lst.number; j++) | |
4907 { | |
4908 if(grr_data->db.nc_mval_list.nc_mval[i].arfcn EQ | |
4909 grr_data->db.nc_ref_lst.info[j]->arfcn) | |
4910 { | |
4911 if(nc_ref_index_arfcn EQ NOT_SET) | |
4912 { | |
4913 /* ARFCN matched for the 1st time in BA list */ | |
4914 nc_ref_index_arfcn = j; | |
4915 } | |
4916 | |
4917 /* In case the same cell (ARFCN+BSIC) or the same ARFCN without BSIC | |
4918 occur more than once in the resulting GSM Neighbour Cell list, | |
4919 each occurrence shall be assigned an index but only the cell with | |
4920 the highest index shall be used for cell re-selection and referred | |
4921 to in measurement reports. */ | |
4922 if(grr_data->db.nc_ref_lst.info[j]->index > | |
4923 grr_data->db.nc_ref_lst.info[nc_ref_index_arfcn]->index) | |
4924 { | |
4925 nc_ref_index_arfcn = j; | |
4926 } | |
4927 | |
4928 if(grr_data->db.nc_mval_list.nc_mval[i].sync_info.bsic EQ | |
4929 grr_data->db.nc_ref_lst.info[j]->bsic) | |
4930 { | |
4931 nc_ref_index_bsic = nc_ref_index_arfcn; | |
4932 } | |
4933 } | |
4934 } | |
4935 | |
4936 /* Store ARFCN, BSIC, RLA_P and RXLEV, if ARFCN and/or BSIC matches */ | |
4937 if(nc_ref_index_arfcn NEQ NOT_SET) | |
4938 { | |
4939 grr_data->db.enh_cell_list[n].arfcn = | |
4940 grr_data->db.nc_mval_list.nc_mval[i].arfcn; | |
4941 | |
4942 grr_data->db.enh_cell_list[n].bsic.bsic = | |
4943 grr_data->db.nc_mval_list.nc_mval[i].sync_info.bsic; | |
4944 | |
4945 grr_data->db.enh_cell_list[n].rla_p = | |
4946 grr_data->db.nc_mval_list.nc_mval[i].rla_p.lev; | |
4947 | |
4948 grr_data->db.enh_cell_list[n].rxlev_avg = | |
4949 grr_data->db.nc_mval_list.nc_mval[i].rxlev_avg; | |
4950 } | |
4951 | |
4952 /* Store in the enhanced cell list as Valid and Invalid BSICs */ | |
4953 if (nc_ref_index_bsic NEQ NOT_SET) | |
4954 { | |
4955 grr_data->db.enh_cell_list[n].index = | |
4956 grr_data->db.nc_ref_lst.info[nc_ref_index_bsic]->index; | |
4957 | |
4958 grr_data->db.enh_cell_list[n].rept_prio = | |
4959 grr_data->db.nc_ref_lst.enh_param->gprs_rept_prio_desc. | |
4960 rept_prio[grr_data->db.nc_ref_lst.info[nc_ref_index_bsic]->index]; | |
4961 | |
4962 grr_data->db.enh_cell_list[n++].bsic.status = BSIC_VALID; | |
4963 } | |
4964 else if(nc_ref_index_arfcn NEQ NOT_SET) | |
4965 { | |
4966 grr_data->db.enh_cell_list[n].index = | |
4967 grr_data->db.nc_ref_lst.info[nc_ref_index_arfcn]->index; | |
4968 /* Set the reporting priority to high for invalid BSICs and allowed | |
4969 NCC part. Refer Section 8.4.8.1 of 3GPP TS 05.08 V8.15.0 (2002-06) */ | |
4970 grr_data->db.enh_cell_list[n].rept_prio = HIGH_PRIO; | |
4971 grr_data->db.enh_cell_list[n++].bsic.status = BSIC_INVALID; | |
4972 } | |
4973 } | |
4974 i++; | |
4975 } | |
4976 grr_data->db.cnt_enh_cell_list = n; | |
4977 }/* cs_form_enh_cell_list */ | |
4978 | |
4979 /* | |
4980 +------------------------------------------------------------------------------ | |
4981 | Function : cs_form_ba_bcch_enh_cell_list | |
4982 +------------------------------------------------------------------------------ | |
4983 | Description : This function is used to form enhanced cell list from BA list | |
4984 | (nc_ref_lst) and Measured values list(nc_mval_list) | |
4985 | | |
4986 | | |
4987 | Parameters : Nil | |
4988 | | |
4989 +------------------------------------------------------------------------------ | |
4990 */ | |
4991 LOCAL void cs_form_ba_bcch_enh_cell_list(void) | |
4992 { | |
4993 UBYTE i = 0, n = 0, j; | |
4994 UBYTE nc_ref_index_arfcn, nc_ref_index_bsic; | |
4995 | |
4996 TRACE_FUNCTION( "cs_form_ba_bcch_enh_cell_list" ); | |
4997 | |
4998 memset((grr_data->db.enh_cell_list), 0xFF, sizeof(T_ENH_CELL_LIST)*MAX_NR_OF_NCELL); | |
4999 | |
5000 grr_data->db.cnt_enh_cell_list = 0; | |
5001 | |
5002 /* Check one entry of Measured values list against all entries of BA list */ | |
5003 while(i < MAX_NR_OF_NC_MVAL AND n < MAX_NR_OF_NCELL) | |
5004 { | |
5005 if( (grr_data->db.nc_mval_list.nc_mval[i].status EQ NC_MVAL_STAT_ASSIGNED) | |
5006 AND | |
5007 (grr_data->db.nc_mval_list.nc_mval[i].arfcn NEQ RRGRR_INVALID_ARFCN) | |
5008 AND | |
5009 (grr_data->db.nc_mval_list.nc_mval[i].sync_info.sync.status EQ | |
5010 STAT_SYNC_OK) | |
5011 AND | |
5012 (grr_data->db.nc_mval_list.nc_mval[i].rla_p.stat EQ CS_RLA_P_VALID) ) | |
5013 { | |
5014 nc_ref_index_arfcn = NOT_SET; /* Will be set the 1st time ARFCN matches | |
5015 in the BA list */ | |
5016 nc_ref_index_bsic = NOT_SET; /* Will be set the 1st time ARFCN-BSIC pair | |
5017 matches in the BA list */ | |
5018 | |
5019 /* Comparison with BA list */ | |
5020 for (j = 0; j < grr_data->db.ba_bcch_nc_ref_lst.number; j++) | |
5021 { | |
5022 if(grr_data->db.nc_mval_list.nc_mval[i].arfcn EQ | |
5023 grr_data->db.ba_bcch_nc_ref_lst.info[j]->arfcn) | |
5024 { | |
5025 if(nc_ref_index_arfcn EQ NOT_SET) | |
5026 { | |
5027 /* ARFCN matched for the 1st time in BA list */ | |
5028 nc_ref_index_arfcn = j; | |
5029 } | |
5030 | |
5031 /* In case the same cell (ARFCN+BSIC) or the same ARFCN without BSIC | |
5032 occur more than once in the resulting GSM Neighbour Cell list, | |
5033 each occurrence shall be assigned an index but only the cell with | |
5034 the highest index shall be used for cell re-selection and referred | |
5035 to in measurement reports. */ | |
5036 if(grr_data->db.ba_bcch_nc_ref_lst.info[j]->index > | |
5037 grr_data->db.ba_bcch_nc_ref_lst.info[nc_ref_index_arfcn]->index) | |
5038 { | |
5039 nc_ref_index_arfcn = j; | |
5040 } | |
5041 | |
5042 if(grr_data->db.nc_mval_list.nc_mval[i].sync_info.bsic EQ | |
5043 grr_data->db.ba_bcch_nc_ref_lst.info[j]->bsic) | |
5044 { | |
5045 nc_ref_index_bsic = nc_ref_index_arfcn; | |
5046 } | |
5047 } | |
5048 } | |
5049 | |
5050 /* Store ARFCN, BSIC, RLA_P AND RXLEV, if ARFCN and/or BSIC matches */ | |
5051 if(nc_ref_index_arfcn NEQ NOT_SET) | |
5052 { | |
5053 grr_data->db.enh_cell_list[n].arfcn = | |
5054 grr_data->db.nc_mval_list.nc_mval[i].arfcn; | |
5055 | |
5056 grr_data->db.enh_cell_list[n].bsic.bsic = | |
5057 grr_data->db.nc_mval_list.nc_mval[i].sync_info.bsic; | |
5058 | |
5059 grr_data->db.enh_cell_list[n].rla_p = | |
5060 grr_data->db.nc_mval_list.nc_mval[i].rla_p.lev; | |
5061 | |
5062 grr_data->db.enh_cell_list[n].rxlev_avg = | |
5063 grr_data->db.nc_mval_list.nc_mval[i].rxlev_avg; | |
5064 } | |
5065 | |
5066 /* Store in the enhanced cell list as Valid and Invalid BSICs */ | |
5067 if (nc_ref_index_bsic NEQ NOT_SET) | |
5068 { | |
5069 grr_data->db.enh_cell_list[n].index = | |
5070 grr_data->db.ba_bcch_nc_ref_lst.info[nc_ref_index_bsic]->index; | |
5071 | |
5072 grr_data->db.enh_cell_list[n].rept_prio = | |
5073 grr_data->db.nc_ref_lst.enh_param->gprs_rept_prio_desc. | |
5074 rept_prio[grr_data->db.ba_bcch_nc_ref_lst.info[nc_ref_index_bsic]->index]; | |
5075 | |
5076 grr_data->db.enh_cell_list[n++].bsic.status = BSIC_VALID; | |
5077 } | |
5078 else if(nc_ref_index_arfcn NEQ NOT_SET) | |
5079 { | |
5080 grr_data->db.enh_cell_list[n].index = | |
5081 grr_data->db.ba_bcch_nc_ref_lst.info[nc_ref_index_arfcn]->index; | |
5082 /* Set the reporting priority to high for invalid BSICs and allowed | |
5083 NCC part. Refer Section 8.4.8.1 of 3GPP TS 05.08 V8.15.0 (2002-06) */ | |
5084 grr_data->db.enh_cell_list[n].rept_prio = HIGH_PRIO; | |
5085 grr_data->db.enh_cell_list[n++].bsic.status = BSIC_INVALID; | |
5086 } | |
5087 } | |
5088 i++; | |
5089 } | |
5090 grr_data->db.cnt_enh_cell_list = n; | |
5091 }/* cs_form_ba_bcch_enh_cell_list */ | |
5092 | |
5093 /* | |
5094 +------------------------------------------------------------------------------ | |
5095 | Function : cs_nc_sort_and_update_emr_info | |
5096 +------------------------------------------------------------------------------ | |
5097 | Description : The purpose of this function is to handle all the specific | |
5098 | requirements for EMR - sorting according to priority as given | |
5099 | in 5.08 V8.16.0, sec.8.4.8.1, and scaling of rxlev values. | |
5100 | | |
5101 | | |
5102 | Parameters : Nil | |
5103 | | |
5104 +------------------------------------------------------------------------------ | |
5105 */ | |
5106 | |
5107 LOCAL void cs_nc_sort_and_update_emr_info(void) | |
5108 { | |
5109 T_ENH_BIN sc_bin; | |
5110 T_ENH_BIN mband_bin[5]; /* 0 - 900, 1 - 1800, 2 - 400, 3 - 1900, 4 - 850*/ | |
5111 T_ENH_BIN rest_bin; | |
5112 UBYTE i; | |
5113 UBYTE temp; | |
5114 T_GRR_ENH_PARA *p_enh = grr_data->db.nc_ref_lst.enh_param; | |
5115 T_ENH_CELL_LIST *enh_cell_list = &(grr_data->db.enh_cell_list[0]); | |
5116 BOOL include_cell = FALSE; | |
5117 grr_data->db.sorted_enh_cell_list.num_valid = 0; | |
5118 | |
5119 TRACE_FUNCTION( "cs_nc_sort_and_update_emr_info" ); | |
5120 | |
5121 /* Flush off the old sorted ENH cell list before forming a new one */ | |
5122 memset(&grr_data->db.sorted_enh_cell_list,0,sizeof(T_ENH_BIN)); | |
5123 | |
5124 /* Step 1: Sort cells into different bins - serving cell band bin, | |
5125 non-serving cell band bin, and the rest which can contain invalid BSIC | |
5126 cells */ | |
5127 cs_nc_sort_cells_into_bins(&sc_bin, mband_bin, &rest_bin); | |
5128 | |
5129 /* Step 2: Fill the cells from each bin, after sorting in descending order | |
5130 of RXLEV, in the order of : sc_bin, mband_bin and rest_bin. | |
5131 Further number of cells from sc_bin and mband_bin is restricted by SERVING_BAND | |
5132 and MULTIBAND reporting parameters */ | |
5133 if ( (sc_bin.num_valid > 0) AND (p_enh->servingband_rep > 0) ) | |
5134 { | |
5135 cs_nc_sort_and_store_meas_results(&sc_bin, p_enh->servingband_rep); | |
5136 if (sc_bin.num_valid > p_enh->servingband_rep) | |
5137 { | |
5138 cs_nc_update_rest_bin(&rest_bin, &sc_bin, p_enh->servingband_rep); | |
5139 } | |
5140 } | |
5141 | |
5142 /* Fill cells from multi band after sorting*/ | |
5143 for ( i = 0; i < MAX_NUM_BANDS AND | |
5144 grr_data->db.sorted_enh_cell_list.num_valid | |
5145 < grr_data->db.cnt_enh_cell_list; i++) | |
5146 { | |
5147 if ( (mband_bin[i].num_valid > 0) AND (p_enh->multiband_rep > 0) ) | |
5148 { | |
5149 cs_nc_sort_and_store_meas_results(&mband_bin[i], p_enh->multiband_rep); | |
5150 if (mband_bin[i].num_valid > p_enh->multiband_rep) | |
5151 { | |
5152 cs_nc_update_rest_bin(&rest_bin, &mband_bin[i], p_enh->multiband_rep ); | |
5153 } | |
5154 } | |
5155 } | |
5156 | |
5157 /* Now sort cells in the rest bin which may contain both valid and | |
5158 invalid BSIC cells. Here we use the reporting offset along with measured RXLEV, | |
5159 for sorting. According to 5.08, sec.8.4.8.1 we need to find those cells whose sum of | |
5160 RXLEV and xxx_reporting_offset is maximum. This can be acheived by sorting the cells | |
5161 in the order of their rxlevm, where rxlevm = rxlev + offset */ | |
5162 if ( (rest_bin.num_valid > 0) AND (grr_data->db.sorted_enh_cell_list.num_valid | |
5163 < grr_data->db.cnt_enh_cell_list) ) | |
5164 { | |
5165 UBYTE j; | |
5166 UBYTE max_rxlevm; | |
5167 UBYTE band; | |
5168 UBYTE rxlevm; | |
5169 UBYTE k; | |
5170 T_ncell_info *ncell; | |
5171 | |
5172 for (i = 0; i < rest_bin.num_valid; i++) | |
5173 { | |
5174 band = cs_get_band_index_for_emr (enh_cell_list[rest_bin.enh_index[i]].arfcn); | |
5175 max_rxlevm = enh_cell_list[rest_bin.enh_index[i]].rla_p + | |
5176 (p_enh->enh_rep_data[band].rep_offset * 6); | |
5177 k = i; | |
5178 for ( j = i+1; j < rest_bin.num_valid ; j++ ) | |
5179 { | |
5180 band = cs_get_band_index_for_emr (enh_cell_list[rest_bin.enh_index[j]].arfcn); | |
5181 rxlevm = enh_cell_list[rest_bin.enh_index[j]].rla_p + | |
5182 (p_enh->enh_rep_data[band].rep_offset * 6) ; | |
5183 if ( rxlevm > max_rxlevm ) | |
5184 { | |
5185 k = j; | |
5186 max_rxlevm = rxlevm; | |
5187 } | |
5188 } | |
5189 include_cell = TRUE; | |
5190 /* When reduced reporting is enabled we have to report low priority cell | |
5191 once in 4 reporting periods. The RXLEV then should be average of previous | |
5192 two periods */ | |
5193 if ( (enh_cell_list[rest_bin.enh_index[k]].rept_prio EQ NORMAL_PRIO) AND | |
5194 (p_enh->rep_rate EQ REPORTING_RATE_REDUCED) ) | |
5195 { | |
5196 /* ncell cannot be NULL since the loop will be entered only for a | |
5197 valid BSIC */ | |
5198 ncell = grr_get_ncell_info(enh_cell_list[rest_bin.enh_index[k]].arfcn, | |
5199 enh_cell_list[rest_bin.enh_index[k]].bsic.bsic); | |
5200 | |
5201 /* For every 4th time, we include this cell in the report */ | |
5202 if ( (ncell->rep_count & (0x03)) EQ 0 ) | |
5203 { | |
5204 /* For those cells that are not reported in every measurement report, | |
5205 the MS shall average the measurements of the current and the previous | |
5206 reporting period (i.e. over two reporting periods). */ | |
5207 enh_cell_list[rest_bin.enh_index[k]].rxlev_avg = | |
5208 (enh_cell_list[rest_bin.enh_index[k]].rxlev_avg + ncell->last_rxlev) >> 1; | |
5209 /* division by 2 */ | |
5210 } | |
5211 else | |
5212 { | |
5213 ncell->last_rxlev = enh_cell_list[rest_bin.enh_index[k]].rxlev_avg; | |
5214 include_cell = FALSE; | |
5215 } | |
5216 /* modulo 4 addition */ | |
5217 ncell->rep_count = (ncell->rep_count + 1) & 0x03; | |
5218 } | |
5219 | |
5220 if (include_cell EQ TRUE) | |
5221 { | |
5222 grr_data->db.sorted_enh_cell_list. | |
5223 enh_index[grr_data->db.sorted_enh_cell_list.num_valid] = | |
5224 rest_bin.enh_index[k]; | |
5225 grr_data->db.sorted_enh_cell_list.num_valid++; | |
5226 } | |
5227 | |
5228 if(k NEQ i) | |
5229 { | |
5230 temp = rest_bin.enh_index[k]; | |
5231 rest_bin.enh_index[k] = rest_bin.enh_index[i]; | |
5232 rest_bin.enh_index[i] = temp; | |
5233 } | |
5234 } | |
5235 } | |
5236 /* This leaves us with final step in neighbour cell measurement reporting - scaling.*/ | |
5237 grr_data->db.pemr_params.scale_used = cs_nc_scale_rxlev (); | |
5238 }/* cs_nc_sort_and_update_emr_info */ | |
5239 | |
5240 /* | |
5241 +------------------------------------------------------------------------------ | |
5242 | Function : cs_nc_sort_cells_into_bins | |
5243 +------------------------------------------------------------------------------ | |
5244 | Description : The purpose of this function is to sort the cells into various | |
5245 | bins. This is the first step in handling reporting priority | |
5246 | as given in 5.08 sec.8.4.8.1 | |
5247 | | |
5248 | | |
5249 | Parameters : Pointers to the three bins | |
5250 | | |
5251 +------------------------------------------------------------------------------ | |
5252 */ | |
5253 LOCAL void cs_nc_sort_cells_into_bins(T_ENH_BIN *p_sbin,T_ENH_BIN *p_mbin, | |
5254 T_ENH_BIN *p_rbin) | |
5255 { | |
5256 UBYTE i, j; | |
5257 UBYTE band; | |
5258 UBYTE sc_band; | |
5259 UBYTE rth; | |
5260 T_ENH_CELL_LIST *enh_cell_list = &(grr_data->db.enh_cell_list[0]); | |
5261 T_GRR_ENH_PARA *p_enh = grr_data->db.nc_ref_lst.enh_param; | |
5262 | |
5263 TRACE_FUNCTION( "cs_nc_sort_cells_into_bins" ); | |
5264 | |
5265 memset(p_sbin, 0xFF, sizeof(T_ENH_BIN)); | |
5266 p_sbin->num_valid = 0; | |
5267 | |
5268 memset(p_rbin, 0xFF, sizeof(T_ENH_BIN)); | |
5269 p_rbin->num_valid = 0; | |
5270 | |
5271 for( i = 0; i < MAX_NUM_BANDS; i++) | |
5272 { | |
5273 memset(&p_mbin[i], 0xFF, sizeof(T_ENH_BIN)); | |
5274 p_mbin[i].num_valid = 0; | |
5275 } | |
5276 | |
5277 sc_band = cs_get_band_index_for_emr (psc_db->pbcch.bcch.arfcn); | |
5278 | |
5279 for ( j = 0; j < grr_data->db.cnt_enh_cell_list; j++ ) | |
5280 { | |
5281 if(enh_cell_list[j].bsic.status EQ BSIC_VALID) /* Valid BSIC */ | |
5282 { | |
5283 /*Find the band of this arfcn*/ | |
5284 band = cs_get_band_index_for_emr(enh_cell_list[j].arfcn); | |
5285 rth = p_enh->enh_rep_data[band].rep_threshold; | |
5286 if (band EQ sc_band ) | |
5287 { | |
5288 /* Apply the threshold criteria for this band*/ | |
5289 if ( rth NEQ REP_THRESHOLD_INF ) | |
5290 { | |
5291 if((rth EQ REP_THRESHOLD_DEF) OR | |
5292 (enh_cell_list[j].rla_p >= (rth * 6))) | |
5293 { | |
5294 p_sbin->enh_index[p_sbin->num_valid++] = j; | |
5295 } | |
5296 else | |
5297 { | |
5298 p_rbin->enh_index[p_rbin->num_valid++] = j; | |
5299 } | |
5300 } /*otherwise report-never*/ | |
5301 } /* otherwise cell in non-serving band*/ | |
5302 else | |
5303 { | |
5304 /* Apply the threshold criteria for this band*/ | |
5305 if ( rth NEQ REP_THRESHOLD_INF ) | |
5306 { | |
5307 if((rth EQ REP_THRESHOLD_DEF) OR | |
5308 (enh_cell_list[j].rla_p >= (rth * 6))) | |
5309 { | |
5310 p_mbin[band].enh_index[p_mbin[band].num_valid++] = j; | |
5311 } | |
5312 else | |
5313 { | |
5314 p_rbin->enh_index[p_rbin->num_valid++] = j; | |
5315 } | |
5316 } /*otherwise report never*/ | |
5317 } | |
5318 } | |
5319 else /* If there's no cell with the given BSIC, then it falls under Invalid | |
5320 BSIC category */ | |
5321 { | |
5322 /* check whether Invalid BSIC reporting is enabled or not and NCC part is | |
5323 permitted or not */ | |
5324 if ( (p_enh->inv_bsic_enabled EQ TRUE) AND | |
5325 ((BOOL)((UBYTE)(p_enh->ncc_permitted & | |
5326 ncc_bit_mask[(enh_cell_list[j].bsic.bsic & BSIC_NCC_MASK) >> 3])) NEQ 0) ) | |
5327 { | |
5328 /* put it in rest bin */ | |
5329 p_rbin->enh_index[p_rbin->num_valid++] = j; | |
5330 } | |
5331 } /* if enh_cell_list.index */ | |
5332 } /* end of for */ | |
5333 }/* cs_nc_sort_cells_into_bins */ | |
5334 | |
5335 /* | |
5336 +------------------------------------------------------------------------------ | |
5337 | Function : cs_get_band_index_for_emr | |
5338 +------------------------------------------------------------------------------ | |
5339 | Description : This is implementation specific function. This is used to | |
5340 | get index into emr reporting data (reporting threshold and | |
5341 | offset) array, which is band specific. | |
5342 | | |
5343 | | |
5344 | Parameters : ARFCN | |
5345 | | |
5346 +------------------------------------------------------------------------------ | |
5347 */ | |
5348 | |
5349 LOCAL UBYTE cs_get_band_index_for_emr (USHORT arfcn) | |
5350 { | |
5351 | |
5352 TRACE_FUNCTION( "cs_get_band_index_for_emr" ); | |
5353 | |
5354 if ( INRANGE(LOW_CHANNEL_900, arfcn, HIGH_CHANNEL_900) ) | |
5355 { | |
5356 return 0; | |
5357 } | |
5358 else if ( INRANGE(LOW_CHANNEL_1800, arfcn, HIGH_CHANNEL_1800)) | |
5359 { | |
5360 return 1; | |
5361 } | |
5362 else if (INRANGE(LOW_CHANNEL_1900, arfcn, HIGH_CHANNEL_1900)) | |
5363 { | |
5364 return 3; | |
5365 } | |
5366 else if ( INRANGE(LOW_CHANNEL_850, arfcn, HIGH_CHANNEL_850)) | |
5367 { | |
5368 return 4; | |
5369 } | |
5370 else | |
5371 { | |
5372 return 2; | |
5373 } | |
5374 }/* cs_get_band_index_for_emr */ | |
5375 | |
5376 /* | |
5377 +------------------------------------------------------------------------------ | |
5378 | Function : cs_nc_sort_and_store_meas_results | |
5379 +------------------------------------------------------------------------------ | |
5380 | Description : This function sorts the cells collected in each bin, in | |
5381 | descending order of RXLEV | |
5382 | | |
5383 | | |
5384 | Parameters : Pointer to bin, Number of cells to be reported | |
5385 | | |
5386 +------------------------------------------------------------------------------ | |
5387 */ | |
5388 | |
5389 LOCAL void cs_nc_sort_and_store_meas_results(T_ENH_BIN *p_bin, UBYTE nbr_rpt) | |
5390 { | |
5391 UBYTE i; | |
5392 UBYTE j; | |
5393 UBYTE max_rxlev; | |
5394 UBYTE k; | |
5395 UBYTE temp; | |
5396 T_ENH_CELL_LIST *enh_cell_list = &(grr_data->db.enh_cell_list[0]); | |
5397 | |
5398 TRACE_FUNCTION( "cs_nc_sort_and_store_meas_results" ); | |
5399 | |
5400 for (i = 0; (i < p_bin->num_valid AND nbr_rpt > 0); i++,nbr_rpt--) | |
5401 { | |
5402 max_rxlev = enh_cell_list[p_bin->enh_index[i]].rla_p; | |
5403 | |
5404 k = i; | |
5405 | |
5406 for ( j = i+1; j < p_bin->num_valid ; j++ ) | |
5407 { | |
5408 if ( enh_cell_list[p_bin->enh_index[j]].rla_p > max_rxlev ) | |
5409 { | |
5410 | |
5411 k = j; | |
5412 | |
5413 max_rxlev = enh_cell_list[p_bin->enh_index[j]].rla_p; | |
5414 } | |
5415 } | |
5416 | |
5417 grr_data->db.sorted_enh_cell_list. | |
5418 enh_index[grr_data->db.sorted_enh_cell_list.num_valid] = | |
5419 p_bin->enh_index[k]; | |
5420 grr_data->db.sorted_enh_cell_list.num_valid++; | |
5421 | |
5422 if(k NEQ i) | |
5423 { | |
5424 temp = p_bin->enh_index[k]; | |
5425 p_bin->enh_index[k] = p_bin->enh_index[i]; | |
5426 p_bin->enh_index[i] = temp; | |
5427 } | |
5428 | |
5429 } | |
5430 }/* cs_nc_sort_and_store_meas_results */ | |
5431 | |
5432 /* | |
5433 +------------------------------------------------------------------------------ | |
5434 | Function : cs_nc_update_rest_bin | |
5435 +------------------------------------------------------------------------------ | |
5436 | Description : This function updates the rest bin by appending the left out | |
5437 | cells in the other bins. These may also have to be reported | |
5438 | along with the cells in rest bin. | |
5439 | | |
5440 | | |
5441 | Parameters : Pointers to the rest and a bin, Number of cells to be reported | |
5442 | | |
5443 +------------------------------------------------------------------------------ | |
5444 */ | |
5445 LOCAL void cs_nc_update_rest_bin(T_ENH_BIN *p_rbin, T_ENH_BIN *p_bin, | |
5446 UBYTE nbr_rpt) | |
5447 { | |
5448 UBYTE i, count; | |
5449 | |
5450 TRACE_FUNCTION( "cs_nc_update_rest_bin" ); | |
5451 | |
5452 count = p_bin->num_valid - nbr_rpt; | |
5453 | |
5454 for ( i = 0; i < count; i++) | |
5455 { | |
5456 p_rbin->enh_index[p_rbin->num_valid++] = p_bin->enh_index[nbr_rpt++]; | |
5457 p_bin->num_valid--; | |
5458 } | |
5459 | |
5460 }/* cs_nc_update_rest_bin */ | |
5461 | |
5462 /* | |
5463 +------------------------------------------------------------------------------ | |
5464 | Function : cs_nc_scale_rxlev | |
5465 +------------------------------------------------------------------------------ | |
5466 | Description : This function performs the scaling of RXLEV. | |
5467 | | |
5468 | | |
5469 | Parameters : Nil | |
5470 | | |
5471 +------------------------------------------------------------------------------ | |
5472 */ | |
5473 LOCAL UBYTE cs_nc_scale_rxlev (void) | |
5474 { | |
5475 UBYTE i; | |
5476 UBYTE no_of_cells = grr_data->db.cnt_enh_cell_list; | |
5477 UBYTE scale; | |
5478 T_ENH_CELL_LIST *enh_cell_list = &(grr_data->db.enh_cell_list[0]); | |
5479 UBYTE scale_order = grr_data->db.nc_ref_lst.enh_param->scale_order; | |
5480 | |
5481 TRACE_FUNCTION( "cs_nc_scale_rxlev" ); | |
5482 | |
5483 /*If scaling is automatic, then we find the scaling as below: | |
5484 If the maximum RXLEV is greater than 63 (MAX_RXLEV), then we add 10dB | |
5485 and check whether it falls into the range after scaling*/ | |
5486 /* Note: The assumption is L1 reports values in the following way - | |
5487 if actual value of rxlev (x) is between y and y+1 dBm, then the reported value | |
5488 is 110+x rounded off to next integer. */ | |
5489 if ( scale_order EQ SCALE_AUTO ) | |
5490 { | |
5491 UBYTE max = 0; | |
5492 | |
5493 if( grr_data->db.scell_info.rxlev_avg NEQ RXLEV_AVG_INVALID ) | |
5494 { | |
5495 max = grr_data->db.scell_info.rxlev_avg; | |
5496 } | |
5497 | |
5498 for ( i = 0; i < no_of_cells ; i++ ) | |
5499 { | |
5500 if (enh_cell_list[i].rxlev_avg > max ) | |
5501 { | |
5502 max = enh_cell_list[i].rxlev_avg; | |
5503 } | |
5504 } | |
5505 | |
5506 if ( max > 63 ) | |
5507 { | |
5508 /* If the max value is greater than 63, we scale by 10 so that | |
5509 rxlev values of maximum cells will come into range(0 - 63) */ | |
5510 scale = 10; | |
5511 } | |
5512 else | |
5513 { | |
5514 scale = 0; | |
5515 } | |
5516 } | |
5517 else | |
5518 { | |
5519 scale = scale_order * 10; | |
5520 } | |
5521 | |
5522 /* Apply the scale to the values to be reported for SCELL and NCELLs */ | |
5523 | |
5524 if( grr_data->db.scell_info.rxlev_avg NEQ RXLEV_AVG_INVALID ) | |
5525 { | |
5526 grr_data->db.scell_info.rxlev_avg -= scale; | |
5527 } | |
5528 | |
5529 for ( i = 0; i < no_of_cells ; i++ ) | |
5530 { | |
5531 if (enh_cell_list[i].rxlev_avg > scale) | |
5532 { | |
5533 enh_cell_list[i].rxlev_avg -= scale; | |
5534 } | |
5535 else | |
5536 { | |
5537 enh_cell_list[i].rxlev_avg = 0; | |
5538 } | |
5539 | |
5540 if (enh_cell_list[i].rxlev_avg > 63) | |
5541 { | |
5542 enh_cell_list[i].rxlev_avg = 63; | |
5543 } | |
5544 } | |
5545 return (scale/10); | |
5546 }/* cs_nc_scale_rxlev */ | |
5547 | |
5548 /* | |
5549 +------------------------------------------------------------------------------ | |
5550 | Function : cs_build_enh_meas_rpt | |
5551 +------------------------------------------------------------------------------ | |
5552 | Description : This function is used to build PEMR | |
5553 | | |
5554 | Parameters : u_enh_meas_report - Pointer to ENH measurement report | |
5555 | | |
5556 +------------------------------------------------------------------------------ | |
5557 */ | |
5558 LOCAL BOOL cs_build_enh_meas_rpt ( T_U_ENHNC_MEAS_REPORT *u_enh_meas_report ) | |
5559 { | |
5560 T_NC_ORDER nc_ord = cs_get_network_ctrl_order( TRUE ); | |
5561 /*UBYTE size_avail = MSG_SIZE_PEMR - MAND_SIZE_PEMR;*/ | |
5562 BOOL pbcch_present = grr_is_pbcch_present( ); | |
5563 UBYTE psi3_cm = grr_get_psi3_cm(); | |
5564 T_nc_meas_rep_enh *nc_meas_rep_enh = &(u_enh_meas_report->nc_meas_rep_enh); | |
5565 UBYTE used_bits = 0; /* for formality sake only, not used here */ | |
5566 UBYTE rxlev_scell; | |
5567 UBYTE v_i_scell; | |
5568 UBYTE i_scell; | |
5569 BOOL rsc_avail = FALSE; | |
5570 BOOL isc_avail = FALSE; | |
5571 | |
5572 TRACE_FUNCTION( "cs_build_enh_meas_rpt" ); | |
5573 | |
5574 /* process message type */ | |
5575 u_enh_meas_report->msg_type = U_ENHNC_MEAS_REPORT_c; | |
5576 | |
5577 /* process TLLI */ | |
5578 grr_set_buf_tlli( &u_enh_meas_report->tlli_value, grr_get_tlli( ) ); | |
5579 | |
5580 /* Process NC Measurements */ | |
5581 | |
5582 /* process NC mode */ | |
5583 switch( nc_ord ) | |
5584 { | |
5585 case NC_NC1: nc_meas_rep_enh->nc_mode = NCMODE_NC1; break; | |
5586 case NC_NC2: nc_meas_rep_enh->nc_mode = NCMODE_NC2; break; | |
5587 | |
5588 default: | |
5589 TRACE_ERROR( "cs_build_enh_meas_rpt no valid NC mode" ); | |
5590 return( FALSE ); | |
5591 } | |
5592 | |
5593 /* process BA used, PSI3 change mark and PMO used */ | |
5594 if( pbcch_present EQ FALSE ) | |
5595 { | |
5596 u_enh_meas_report->nc_meas_rep_enh.ba_psi3_str.flag = FALSE; | |
5597 u_enh_meas_report->nc_meas_rep_enh.ba_psi3_str.v_ba_ind_used = TRUE; | |
5598 u_enh_meas_report->nc_meas_rep_enh.ba_psi3_str.v_ba_ind_used_3g = TRUE; | |
5599 u_enh_meas_report->nc_meas_rep_enh.ba_psi3_str.ba_ind_used = | |
5600 psc_db->ba_ind; | |
5601 } | |
5602 else | |
5603 { | |
5604 u_enh_meas_report->nc_meas_rep_enh.ba_psi3_str.flag = TRUE; | |
5605 u_enh_meas_report->nc_meas_rep_enh.ba_psi3_str.v_psi3_cm = TRUE; | |
5606 u_enh_meas_report->nc_meas_rep_enh.ba_psi3_str.psi3_cm = psi3_cm; | |
5607 } | |
5608 | |
5609 u_enh_meas_report->nc_meas_rep_enh.ba_psi3_str.pmo_ind_used = | |
5610 psc_db->nc_ms.pmo_ind; | |
5611 | |
5612 /* process serving cell data - rxlev and ilev */ | |
5613 cs_process_serving_cell_data(&rxlev_scell, &v_i_scell, &i_scell, &used_bits, | |
5614 &rsc_avail, &isc_avail); | |
5615 | |
5616 if((rsc_avail EQ TRUE) AND (isc_avail EQ FALSE)) | |
5617 { | |
5618 /* Only RXLEV of SCELL avalable. ILEV of SCELL not available */ | |
5619 nc_meas_rep_enh->v_serv_cell_data = TRUE; | |
5620 nc_meas_rep_enh->serv_cell_data.v_i_scell = FALSE; | |
5621 nc_meas_rep_enh->serv_cell_data.rxlev_scell = rxlev_scell; | |
5622 } | |
5623 else if(rsc_avail EQ FALSE) | |
5624 { | |
5625 /* RXLEV of SCELL not avalable. Hence SCELL info is not reported */ | |
5626 nc_meas_rep_enh->v_serv_cell_data = FALSE; | |
5627 } | |
5628 else if((rsc_avail EQ TRUE) AND (isc_avail EQ TRUE)) | |
5629 { | |
5630 /* Both RXLEV and ILEV of SCELL available and reported */ | |
5631 nc_meas_rep_enh->v_serv_cell_data = TRUE; | |
5632 nc_meas_rep_enh->serv_cell_data.v_i_scell = TRUE; | |
5633 nc_meas_rep_enh->serv_cell_data.rxlev_scell = rxlev_scell; | |
5634 nc_meas_rep_enh->serv_cell_data.i_scell = i_scell; | |
5635 } | |
5636 | |
5637 /* process NC measurement results */ | |
5638 if(cs_fill_nc_enh_meas_results(nc_meas_rep_enh) EQ FALSE) | |
5639 { | |
5640 nc_meas_rep_enh->v_nc_rep_quan = FALSE; | |
5641 } | |
5642 | |
5643 /* process BSIC_SEEN and SCALE */ | |
5644 if(nc_meas_rep_enh->c_rep_invalid_bsic_info NEQ 0) | |
5645 { | |
5646 nc_meas_rep_enh->bsic_seen = TRUE; | |
5647 } | |
5648 else | |
5649 { | |
5650 nc_meas_rep_enh->bsic_seen = FALSE; | |
5651 } | |
5652 | |
5653 nc_meas_rep_enh->scale = grr_data->db.pemr_params.scale_used; | |
5654 | |
5655 return(TRUE); | |
5656 | |
5657 } /* cs_build_enh_meas_rpt() */ | |
5658 | |
5659 | |
5660 /* | |
5661 +------------------------------------------------------------------------------ | |
5662 | Function : cs_fill_nc_meas_results | |
5663 +------------------------------------------------------------------------------ | |
5664 | Description : This function is used to fill ENH measurements of neighbour | |
5665 | cells in the PEMR message | |
5666 | | |
5667 | | |
5668 | Parameters : Pointer to ENH meas parameters struct | |
5669 | | |
5670 +------------------------------------------------------------------------------ | |
5671 */ | |
5672 | |
5673 LOCAL BOOL cs_fill_nc_enh_meas_results(T_nc_meas_rep_enh *nc_meas_rep_enh) | |
5674 { | |
5675 UBYTE size_avail = MSG_SIZE_PEMR - MAND_SIZE_PEMR; | |
5676 UBYTE i; | |
5677 UBYTE highest_index = 0; | |
5678 T_ENH_CELL_LIST *enh_cell_list = &(grr_data->db.enh_cell_list[0]); | |
5679 T_ENH_BIN *sorted_list = &grr_data->db.sorted_enh_cell_list; | |
5680 UBYTE index_0 = 1; | |
5681 | |
5682 nc_meas_rep_enh->nc_rep_quan.c_reporting_quantity_bmp = 0; | |
5683 nc_meas_rep_enh->c_rep_invalid_bsic_info = 0; | |
5684 | |
5685 | |
5686 TRACE_FUNCTION( "cs_fill_nc_meas_results" ); | |
5687 | |
5688 /*lint -e{437} Passing struct '' to ellipsis */ | |
5689 TRACE_EVENT_P1("dump=%x",grr_data->db.enh_cell_list[0]); | |
5690 | |
5691 if(grr_data->db.sorted_enh_cell_list.num_valid EQ 0) | |
5692 { | |
5693 return(FALSE); | |
5694 } | |
5695 | |
5696 nc_meas_rep_enh->v_nc_rep_quan = TRUE; | |
5697 | |
5698 for(i = 0; i < sorted_list->num_valid; i++) | |
5699 { | |
5700 if(enh_cell_list[sorted_list->enh_index[i]].bsic.status EQ BSIC_VALID) | |
5701 { | |
5702 /*Fill it in valid BSIC bit map reporting, enh_cell_list[i]->index | |
5703 corresponds to the bit in the report. Find whether size permits */ | |
5704 TRACE_EVENT_P2("I%x = %x",i,enh_cell_list[sorted_list->enh_index[i]].index); | |
5705 nc_meas_rep_enh->nc_rep_quan. | |
5706 reporting_quantity_bmp[enh_cell_list[sorted_list->enh_index[i]].index]. | |
5707 v_reporting_quantity = TRUE; | |
5708 nc_meas_rep_enh->nc_rep_quan. | |
5709 reporting_quantity_bmp[enh_cell_list[sorted_list->enh_index[i]].index]. | |
5710 reporting_quantity = enh_cell_list[sorted_list->enh_index[i]].rxlev_avg; | |
5711 | |
5712 size_avail = size_avail - index_0; | |
5713 index_0 = 0; | |
5714 | |
5715 if ( enh_cell_list[sorted_list->enh_index[i]].index > highest_index ) | |
5716 { | |
5717 /* When the place where the RXLEV has to be filled requires | |
5718 additional bits in bit map, then we have to account for | |
5719 these single bits and additional 6 bits for RXLEV */ | |
5720 if ( size_avail >= (enh_cell_list[sorted_list->enh_index[i]].index | |
5721 - highest_index) + NC_RXLEV_N_LEN ) | |
5722 { | |
5723 /* This means we require atleast enh_cell_list[i]->index - | |
5724 highest_index+6 bits in bit map to include this rxlev */ | |
5725 /* 6 bits for RXLEV itself */ | |
5726 size_avail = size_avail - | |
5727 (enh_cell_list[sorted_list->enh_index[i]].index - highest_index | |
5728 + NC_RXLEV_N_LEN); | |
5729 highest_index = enh_cell_list[sorted_list->enh_index[i]].index; | |
5730 nc_meas_rep_enh->nc_rep_quan. | |
5731 c_reporting_quantity_bmp = | |
5732 enh_cell_list[sorted_list->enh_index[i]].index + 1; /* counter is index+1 */ | |
5733 continue; | |
5734 } | |
5735 else if (size_avail >= NC_RXLEV_N_LEN) | |
5736 { | |
5737 continue; | |
5738 } | |
5739 else | |
5740 break; /* No more filling possible */ | |
5741 } | |
5742 else if (size_avail >= NC_RXLEV_N_LEN) | |
5743 { | |
5744 size_avail -= NC_RXLEV_N_LEN; /* size for bit map is already accounted for*/ | |
5745 nc_meas_rep_enh->nc_rep_quan. | |
5746 c_reporting_quantity_bmp = highest_index +1; | |
5747 continue; | |
5748 } | |
5749 else | |
5750 { | |
5751 break; /*no more inclusion of results is possible*/ | |
5752 } | |
5753 } | |
5754 else | |
5755 { | |
5756 /* fill in invalid BSIC list since cell is not present in the neighbour cell | |
5757 list. Here the index that needs to be filled is index of the ARFCN in BA(list)*/ | |
5758 if ( size_avail > NC_INVBSIC_PEMR ) | |
5759 { | |
5760 nc_meas_rep_enh->v_rep_invalid_bsic_info = TRUE; | |
5761 nc_meas_rep_enh->rep_invalid_bsic_info | |
5762 [nc_meas_rep_enh->c_rep_invalid_bsic_info].bcch_freq_ncell | |
5763 = enh_cell_list[sorted_list->enh_index[i]].index; | |
5764 nc_meas_rep_enh->rep_invalid_bsic_info | |
5765 [nc_meas_rep_enh->c_rep_invalid_bsic_info].bsic | |
5766 = enh_cell_list[sorted_list->enh_index[i]].bsic.bsic; | |
5767 nc_meas_rep_enh->rep_invalid_bsic_info | |
5768 [nc_meas_rep_enh->c_rep_invalid_bsic_info].rxlev_ncell | |
5769 = enh_cell_list[sorted_list->enh_index[i]].rxlev_avg; | |
5770 nc_meas_rep_enh->c_rep_invalid_bsic_info++; | |
5771 size_avail -= NC_INVBSIC_PEMR; | |
5772 } | |
5773 } | |
5774 } | |
5775 | |
5776 return(TRUE); | |
5777 | |
5778 }/* cs_fill_nc_enh_meas_results */ | |
5779 | |
5780 /* | |
5781 +------------------------------------------------------------------------------ | |
5782 | Function : cs_build_enh_sorted_strng_arfcn_list | |
5783 +------------------------------------------------------------------------------ | |
5784 | Description : The purpose of this function is to sort the cells into various | |
5785 | bins and in desc order of RXLEV in each of the bin. The ARFCNs | |
5786 | in the sorted bin are finally sent to RR for decoding purpose | |
5787 | | |
5788 | | |
5789 | Parameters : Pointers to the final sorted bin for storage | |
5790 | | |
5791 +------------------------------------------------------------------------------ | |
5792 */ | |
5793 LOCAL void cs_build_enh_sorted_strng_arfcn_list(T_ENH_STRNG_ARFCN_LIST *f_bin) | |
5794 { | |
5795 T_ENH_STRNG_ARFCN_LIST s_bin, r_bin; | |
5796 | |
5797 UBYTE total_arfcns; | |
5798 | |
5799 f_bin->num = 0; | |
5800 | |
5801 TRACE_FUNCTION( "cs_build_enh_sorted_strng_arfcn_list" ); | |
5802 | |
5803 /* Sort ARFCNs into Serving, Non-serving or the Rest*/ | |
5804 total_arfcns = cs_sort_arfcns_into_bins(&s_bin, &r_bin); | |
5805 | |
5806 /* Sort the ARFCNs in desc order of RXLEV and store them in the final bin */ | |
5807 if(total_arfcns NEQ 0) | |
5808 { | |
5809 cs_sort_store_in_desc_order_rxlev(&s_bin, f_bin); | |
5810 cs_sort_store_in_desc_order_rxlev(&r_bin, f_bin); | |
5811 } | |
5812 } | |
5813 | |
5814 /* | |
5815 +------------------------------------------------------------------------------ | |
5816 | Function : cs_sort_arfcns_into_bins | |
5817 +------------------------------------------------------------------------------ | |
5818 | Description : The purpose of this function is to sort the ARFCNs into various | |
5819 | bins. | |
5820 | | |
5821 | | |
5822 | Parameters : Pointers to the the bins | |
5823 | | |
5824 +------------------------------------------------------------------------------ | |
5825 */ | |
5826 LOCAL UBYTE cs_sort_arfcns_into_bins(T_ENH_STRNG_ARFCN_LIST *p_s_bin, | |
5827 T_ENH_STRNG_ARFCN_LIST *p_r_bin) | |
5828 { | |
5829 UBYTE i; | |
5830 UBYTE band, sc_band; | |
5831 UBYTE total_cells = 0; | |
5832 | |
5833 p_s_bin->num = 0; | |
5834 p_r_bin->num = 0; | |
5835 | |
5836 TRACE_FUNCTION( "cs_sort_arfcns_into_bins" ); | |
5837 | |
5838 sc_band = cs_get_band_index_for_emr (psc_db->pbcch.bcch.arfcn); | |
5839 | |
5840 /* Check the ARFCNs in the NC_MVAL and store them in Serving or | |
5841 Rest bins according to their bands */ | |
5842 i = 0; | |
5843 while( (i < MAX_NR_OF_NC_MVAL) AND (total_cells <= MAX_NR_OF_NCELL) ) | |
5844 { | |
5845 if( (grr_data->db.nc_mval_list.nc_mval[i].arfcn NEQ RRGRR_INVALID_ARFCN) | |
5846 AND (grr_data->db.nc_mval_list.nc_mval[i].status EQ NC_MVAL_STAT_ASSIGNED) ) | |
5847 { | |
5848 band = cs_get_band_index_for_emr(grr_data->db.nc_mval_list.nc_mval[i].arfcn); | |
5849 if (band EQ sc_band) | |
5850 { | |
5851 p_s_bin->meas[p_s_bin->num].arfcn = | |
5852 grr_data->db.nc_mval_list.nc_mval[i].arfcn; | |
5853 p_s_bin->meas[p_s_bin->num].rxlev = | |
5854 grr_data->db.nc_mval_list.nc_mval[i].rla_p.lev; | |
5855 p_s_bin->num++; | |
5856 | |
5857 } | |
5858 else /* Process the non-serving bands */ | |
5859 { | |
5860 p_r_bin->meas[p_r_bin->num].arfcn = | |
5861 grr_data->db.nc_mval_list.nc_mval[i].arfcn; | |
5862 p_r_bin->meas[p_r_bin->num].rxlev = | |
5863 grr_data->db.nc_mval_list.nc_mval[i].rla_p.lev; | |
5864 p_r_bin->num++; | |
5865 } | |
5866 total_cells = p_s_bin->num + p_r_bin->num; | |
5867 } | |
5868 i++; | |
5869 } /* end of while */ | |
5870 return(total_cells); | |
5871 }/* cs_sort_arfcns_into_bins */ | |
5872 | |
5873 /* | |
5874 +------------------------------------------------------------------------------ | |
5875 | Function : cs_sort_in_desc_order_rxlev | |
5876 +------------------------------------------------------------------------------ | |
5877 | Description : This function sorts the cells collected in each bin, in | |
5878 | descending order of RXLEV. It will be stored in the final bin | |
5879 | as and when sorted. | |
5880 | | |
5881 | | |
5882 | Parameters : Pointer to serving or multiband bin, Pointer to final bin | |
5883 | | |
5884 +------------------------------------------------------------------------------ | |
5885 */ | |
5886 | |
5887 LOCAL void cs_sort_store_in_desc_order_rxlev(T_ENH_STRNG_ARFCN_LIST *p_bin, | |
5888 T_ENH_STRNG_ARFCN_LIST *p_f_bin) | |
5889 { | |
5890 UBYTE i; | |
5891 UBYTE j; | |
5892 UBYTE max_rxlev; | |
5893 UBYTE k; | |
5894 T_MEAS temp; | |
5895 | |
5896 TRACE_FUNCTION( "cs_sort_store_in_desc_order_rxlev" ); | |
5897 | |
5898 for (i = 0; i < p_bin->num; i++) | |
5899 { | |
5900 max_rxlev = p_bin->meas[i].rxlev; | |
5901 k = i; | |
5902 for ( j = i + 1; j < p_bin->num; j++ ) | |
5903 { | |
5904 if ( p_bin->meas[j].rxlev > max_rxlev ) | |
5905 { | |
5906 k = j; | |
5907 max_rxlev = p_bin->meas[j].rxlev; | |
5908 } | |
5909 } | |
5910 | |
5911 /* Store the ARFCN-RXLEV pair in the final bin in desc order of RXLEV */ | |
5912 p_f_bin->meas[p_f_bin->num++] = p_bin->meas[k]; | |
5913 | |
5914 if(k NEQ i) | |
5915 { | |
5916 temp = p_bin->meas[k]; | |
5917 p_bin->meas[k] = p_bin->meas[i]; | |
5918 p_bin->meas[i] = temp; | |
5919 } | |
5920 } | |
5921 }/* cs_sort_store_in_desc_order_rxlev */ | |
5922 | |
5923 /* | |
5924 +------------------------------------------------------------------------------ | |
5925 | Function : cs_init_ba_bcch_nc_ref_list | |
5926 +------------------------------------------------------------------------------ | |
5927 | Description : | |
5928 | | |
5929 | Parameters : list - pointer to NC measurement pointer list | |
5930 | | |
5931 +------------------------------------------------------------------------------ | |
5932 */ | |
5933 GLOBAL void cs_init_ba_bcch_nc_ref_list () | |
5934 { | |
5935 TRACE_FUNCTION( "cs_init_ba_bcch_nc_ref_list" ); | |
5936 | |
5937 grr_data->db.ba_bcch_nc_ref_lst.number = 0; | |
5938 | |
5939 }/* cs_init_ba_bcch_nc_ref_list */ | |
5940 | |
5941 /* | |
5942 +------------------------------------------------------------------------------ | |
5943 | Function : cs_build_ba_bcch_nc_freq_list | |
5944 +------------------------------------------------------------------------------ | |
5945 | Description : | |
5946 | | |
5947 | Parameters : db - pointer to serving cell database | |
5948 | | |
5949 +------------------------------------------------------------------------------ | |
5950 */ | |
5951 LOCAL void cs_build_ba_bcch_nc_freq_list () | |
5952 { | |
5953 UBYTE i; | |
5954 | |
5955 TRACE_FUNCTION( "cs_build_ba_bcch_nc_freq_list" ); | |
5956 | |
5957 /* | |
5958 * add neighbour cell information of SI2 and PMO to reference list | |
5959 */ | |
5960 for( i = 0; i < psc_db->nc_ba_bcch_cw.number; i++ ) | |
5961 { | |
5962 grr_data->db.ba_bcch_nc_ref_lst.info[i] = &psc_db->nc_ba_bcch_cw.info[i]; | |
5963 grr_data->db.ba_bcch_nc_ref_lst.number++; | |
5964 } | |
5965 | |
5966 if(use_ba_gprs EQ FALSE) | |
5967 { | |
5968 UBYTE number = psc_db->nc_ba_bcch_cw.number; | |
5969 for(i = 0; i < psc_db->nc_ms.ncmeas.list.number; i++) | |
5970 { | |
5971 grr_data->db.ba_bcch_nc_ref_lst.info[number] = | |
5972 &psc_db->nc_ms.ncmeas.list.info[i]; | |
5973 grr_data->db.ba_bcch_nc_ref_lst.info[number]->index = number; | |
5974 grr_data->db.ba_bcch_nc_ref_lst.number++; | |
5975 number++; | |
5976 } | |
5977 } | |
5978 } | |
5979 | |
5980 #endif | |
5981 /* | |
5982 +------------------------------------------------------------------------------ | |
5983 | Function : cs_copy_rxlev_from_avg | |
5984 +------------------------------------------------------------------------------ | |
5985 | Description : The function cs_copy_rxlev_from_avg() helps to retain the old | |
5986 | rxlev data obtained for the neighbour cells before the cell | |
5987 | change. | |
5988 | Parameters : Index of the nc_data->cell,nc_mval->rxlev_avg | |
5989 | | |
5990 +------------------------------------------------------------------------------ | |
5991 */ | |
5992 LOCAL void cs_copy_rxlev_from_avg(UBYTE rxlev_avg,T_CELL *cell) | |
5993 { | |
5994 #define INITIAL_ACC_MEAS 4 | |
5995 UBYTE i; /* used for counting */ | |
5996 T_RLA_P_DATA *rla_p_data = &cell->rla_p_data; | |
5997 T_RXLEV_DATA *rxlev_data = &cell->rxlev_data; | |
5998 | |
5999 TRACE_FUNCTION( "cs_copy_rxlev_from_avg" ); | |
6000 TRACE_EVENT_P3( "cs_copy_rxlev_from_avg arfcn=%ld LOI=%ld rxlev_avg=%ld", cell->arfcn,rla_p_data->loi,rxlev_avg); | |
6001 | |
6002 rla_p_data->loi = INITIAL_ACC_MEAS - 1 ; | |
6003 rla_p_data->ovrflw = FALSE; | |
6004 | |
6005 for( i = 0; i < INITIAL_ACC_MEAS; i++ ) | |
6006 { | |
6007 rla_p_data->meas[i].cnt = 1; | |
6008 rla_p_data->meas[i].acc = (USHORT)rxlev_avg; | |
6009 rla_p_data->meas[i].rpt_prd = 208; | |
6010 } | |
6011 | |
6012 rxlev_data->acc = rxlev_avg*INITIAL_ACC_MEAS*RXLEV_ACRCY; | |
6013 rxlev_data->nbr = INITIAL_ACC_MEAS; | |
6014 } | |
6015 /* | |
6016 +------------------------------------------------------------------------------ | |
6017 | Function : cs_reuse_old_cell_rxlev | |
6018 +------------------------------------------------------------------------------ | |
6019 | Description : The function cs_reuse_old_cell_rxlev() helps to reuse rxlev data | |
6020 | obtained for the neighbour cells in the old cell before the cell | |
6021 | change. | |
6022 | Parameters : void | |
6023 | | |
6024 +------------------------------------------------------------------------------ | |
6025 */ | |
6026 LOCAL void cs_reuse_old_cell_rxlev() | |
6027 { | |
6028 T_NC_MVAL *nc_mval; | |
6029 UBYTE i,found,mval_idx ; | |
6030 UBYTE mval_index=0; | |
6031 | |
6032 TRACE_FUNCTION( "cs_reuse_old_cell_rxlev" ); | |
6033 TRACE_EVENT( "cs_reuse_old_cell_rxlev" ); | |
6034 | |
6035 for( i = 0; i < MPHP_NUMC_BA_GPRS_SC; i++ ) | |
6036 { | |
6037 #if 0 | |
6038 mval_index = 0; | |
6039 nc_mval = grr_get_nc_mval( nc_data->cell[i].arfcn, RRGRR_INVALID_BSIC, &mval_index ); | |
6040 if(nc_mval NEQ 0) | |
6041 { | |
6042 if(nc_mval->rla_p.stat EQ CS_RLA_P_VALID) | |
6043 { | |
6044 cs_copy_rxlev_from_avg( (UBYTE)nc_mval->rxlev_avg,&nc_data->cell[i] ); | |
6045 } | |
6046 else | |
6047 { | |
6048 cs_reset_meas_result( &nc_data->cell[i] ); | |
6049 } | |
6050 } | |
6051 else | |
6052 { | |
6053 cs_reset_meas_result( &nc_data->cell[i] ); | |
6054 } | |
6055 #else | |
6056 found=0; | |
6057 for( mval_idx = 0; mval_idx < MAX_NR_OF_NC_MVAL; mval_idx++ ) | |
6058 { | |
6059 nc_mval = &grr_data->db.nc_mval_list.nc_mval[mval_idx]; | |
6060 if((UBYTE)nc_mval->rxlev_avg EQ 0xFF AND | |
6061 nc_mval->rla_p.stat EQ CS_RLA_P_VALID) | |
6062 { | |
6063 TRACE_EVENT_P4("PATCH: arfcn=%ld avg_lev=%ld rla_p_lev=%ld stat=%ld " | |
6064 ,nc_mval->arfcn,nc_mval->rxlev_avg,nc_mval->rla_p.lev,nc_mval->rla_p.stat); | |
6065 } | |
6066 if( | |
6067 (nc_mval->arfcn EQ nc_data->cell[i].arfcn) | |
6068 AND | |
6069 (nc_mval->rla_p.stat EQ CS_RLA_P_VALID) | |
6070 AND | |
6071 ((UBYTE)nc_mval->rxlev_avg NEQ 0xFF) | |
6072 ) | |
6073 { | |
6074 cs_copy_rxlev_from_avg( (UBYTE)nc_mval->rxlev_avg,&nc_data->cell[i] ); | |
6075 found=1; | |
6076 } | |
6077 } | |
6078 if(!found) | |
6079 cs_reset_meas_result( &nc_data->cell[i] ); | |
6080 #endif | |
6081 } | |
6082 } | |
6083 | |
6084 | |
6085 | |
6086 | |
6087 | |
6088 | |
6089 |