1 /*
2 * Copyright (C) 2010 NXP Semiconductors
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17 /*!
18 * \file phLlcNfc_Timer.c
19 * \brief To create, start, stop and destroy timer.
20 *
21 * Project: NFC-FRI-1.1
22 *
23 * $Date: Mon Jun 14 11:47:54 2010 $
24 * $Author: ing02260 $
25 * $Revision: 1.55 $
26 * $Aliases: NFC_FRI1.1_WK1023_R35_2,NFC_FRI1.1_WK1023_R35_1 $
27 *
28 */
29
30 /*************************** Includes *******************************/
31 #include <phNfcTypes.h>
32 #include <phNfcStatus.h>
33 #include <phOsalNfc.h>
34 #include <phOsalNfc_Timer.h>
35 #include <phNfcInterface.h>
36 #include <phLlcNfc.h>
37 #include <phLlcNfc_DataTypes.h>
38 #include <phLlcNfc_Interface.h>
39 #include <phLlcNfc_Frame.h>
40 #include <phLlcNfc_Timer.h>
41
42 /*********************** End of includes ****************************/
43
44 /***************************** Macros *******************************/
45 /**< Timer for connection timer index */
46 #define PH_LLCNFC_CONNECTION_TO_INDEX (0x00)
47 /**< Maximum guard timer can be present */
48 #define PH_LLCNFC_MAX_GUARD_TIMER (0x04)
49 /** Connection time out bit to set */
50 #define PH_LLCNFC_CON_TO_BIT (0)
51 /** Guard time out bit to set */
52 #define PH_LLCNFC_GUARD_TO_BIT (1)
53 /** Ack time out bit to set */
54 #define PH_LLCNFC_ACK_TO_BIT (2)
55 /** No of bits to set */
56 #define PH_LLCNFC_TO_NOOFBITS (1)
57 /** Connection time out bit value */
58 #define PH_LLCNFC_CON_TO_BIT_VAL (0x01)
59 /** Guard time out bit to set */
60 #define PH_LLCNFC_GUARD_TO_BIT_VAL (0x02)
61 /** ACK time out bit to set */
62 #define PH_LLCNFC_ACK_TO_BIT_VAL (0x04)
63
64 #define GUARD_TO_URSET
65
66
67 /************************ End of macros *****************************/
68
69 /*********************** Local functions ****************************/
70 /* This callback is for guard time out */
71 #ifdef LLC_TIMER_ENABLE
72 static
73 void
74 phLlcNfc_GuardTimeoutCb (
75 uint32_t TimerId,
76 void *pContext
77 );
78
79
80 #ifdef PIGGY_BACK
81 /* This callback is for acknowledge time out */
82 static
83 void
84 phLlcNfc_AckTimeoutCb (
85 uint32_t TimerId
86 );
87 #endif /* #ifdef PIGGY_BACK */
88
89 /* This callback is for connection time out */
90 static
91 void
92 phLlcNfc_ConnectionTimeoutCb (
93 uint32_t TimerId,
94 void *pContext
95 );
96 #endif /* #ifdef LLC_TIMER_ENABLE */
97
98 /******************** End of Local functions ************************/
99
100 /********************** Global variables ****************************/
101 static phLlcNfc_Context_t *gpphLlcNfc_Ctxt = NULL;
102
103 /******************** End of Global Variables ***********************/
104
105 NFCSTATUS
phLlcNfc_TimerInit(phLlcNfc_Context_t * psLlcCtxt)106 phLlcNfc_TimerInit(
107 phLlcNfc_Context_t *psLlcCtxt
108 )
109 {
110 NFCSTATUS result = PHNFCSTVAL(CID_NFC_LLC,
111 NFCSTATUS_INVALID_PARAMETER);
112 uint8_t index = 0;
113 if (NULL != psLlcCtxt)
114 {
115 result = NFCSTATUS_SUCCESS;
116 gpphLlcNfc_Ctxt = psLlcCtxt;
117 while (index < PH_LLCNFC_MAX_TIMER_USED)
118 {
119 #ifdef LLC_TIMER_ENABLE
120 gpphLlcNfc_Ctxt->s_timerinfo.timer_id[index] =
121 PH_OSALNFC_INVALID_TIMER_ID;
122 #endif /* #ifdef LLC_TIMER_ENABLE */
123 index++;
124 }
125 }
126 return result;
127 }
128
129 void
phLlcNfc_TimerUnInit(phLlcNfc_Context_t * psLlcCtxt)130 phLlcNfc_TimerUnInit(
131 phLlcNfc_Context_t *psLlcCtxt
132 )
133 {
134 uint8_t index = 0;
135 if ((NULL != gpphLlcNfc_Ctxt) &&
136 (gpphLlcNfc_Ctxt == psLlcCtxt))
137 {
138 while (index <= PH_LLCNFC_ACKTIMER)
139 {
140 if (PH_LLCNFC_GUARDTIMER == index)
141 {
142 phLlcNfc_StopTimers (index,
143 gpphLlcNfc_Ctxt->s_timerinfo.guard_to_count);
144 }
145 else
146 {
147 phLlcNfc_StopTimers (index, 0);
148 }
149 index++;
150 }
151 phLlcNfc_DeleteTimer();
152 }
153 }
154
155 void
phLlcNfc_CreateTimers(void)156 phLlcNfc_CreateTimers(void)
157 {
158 uint8_t index = 0;
159
160 while (index < PH_LLCNFC_MAX_TIMER_USED)
161 {
162 #ifdef LLC_TIMER_ENABLE
163 gpphLlcNfc_Ctxt->s_timerinfo.timer_id[index] =
164 phOsalNfc_Timer_Create();
165 #endif /* #ifdef LLC_TIMER_ENABLE */
166 index++;
167 }
168 return;
169 }
170
171 NFCSTATUS
phLlcNfc_StartTimers(uint8_t TimerType,uint8_t ns_value)172 phLlcNfc_StartTimers (
173 uint8_t TimerType,
174 uint8_t ns_value
175 )
176 {
177 NFCSTATUS result = NFCSTATUS_SUCCESS;
178 #ifdef LLC_TIMER_ENABLE
179
180 uint32_t timerid = 0;
181 uint8_t timerstarted = 0;
182 uint8_t timer_count = 0;
183 uint16_t timer_resolution = 0;
184 ppCallBck_t Callback = NULL;
185 phLlcNfc_Timerinfo_t *ps_timer_info = NULL;
186
187 ps_timer_info = &(gpphLlcNfc_Ctxt->s_timerinfo);
188 PHNFC_UNUSED_VARIABLE(result);
189
190 PH_LLCNFC_PRINT("\n\nLLC : START TIMER CALLED\n\n");
191 /* Depending on the timer type, use the Osal callback */
192 switch(TimerType)
193 {
194 case PH_LLCNFC_CONNECTIONTIMER:
195 {
196 /* Get the connection timer flag */
197 timerstarted = (uint8_t)
198 GET_BITS8(ps_timer_info->timer_flag,
199 PH_LLCNFC_CON_TO_BIT,
200 PH_LLCNFC_TO_NOOFBITS);
201 if (0 == timerstarted)
202 {
203 /* Timer not started, so start the timer */
204 gpphLlcNfc_Ctxt->s_timerinfo.timer_flag = (uint8_t)
205 SET_BITS8 (ps_timer_info->timer_flag,
206 PH_LLCNFC_CON_TO_BIT,
207 PH_LLCNFC_TO_NOOFBITS,
208 (PH_LLCNFC_CON_TO_BIT + 1));
209 }
210
211 timerid = ps_timer_info->timer_id[PH_LLCNFC_CONNECTION_TO_INDEX];
212 Callback = (ppCallBck_t)&phLlcNfc_ConnectionTimeoutCb;
213 timer_resolution = ps_timer_info->con_to_value = (uint16_t)
214 PH_LLCNFC_CONNECTION_TO_VALUE;
215 break;
216 }
217
218 case PH_LLCNFC_GUARDTIMER:
219 {
220 if (ps_timer_info->guard_to_count < PH_LLCNFC_MAX_GUARD_TIMER)
221 {
222 timer_count = ps_timer_info->guard_to_count;
223 timer_resolution = (uint16_t)PH_LLCNFC_RESOLUTION;
224
225 PH_LLCNFC_DEBUG("RESOLUTION VALUE : 0x%02X\n", PH_LLCNFC_RESOLUTION);
226 PH_LLCNFC_DEBUG("TIME-OUT VALUE : 0x%02X\n", PH_LLCNFC_GUARD_TO_VALUE);
227
228 /* Get the guard timer flag */
229 timerstarted = (uint8_t)
230 GET_BITS8 (ps_timer_info->timer_flag,
231 PH_LLCNFC_GUARD_TO_BIT,
232 PH_LLCNFC_TO_NOOFBITS);
233
234 PH_LLCNFC_DEBUG("GUARD TIMER NS INDEX : 0x%02X\n", ns_value);
235 PH_LLCNFC_DEBUG("GUARD TIMER COUNT : 0x%02X\n", timer_count);
236 PH_LLCNFC_DEBUG("GUARD TIMER STARTED : 0x%02X\n", timerstarted);
237
238 if (0 == timerstarted)
239 {
240 /* Timer not started, so start the timer */
241 ps_timer_info->timer_flag = (uint8_t)
242 SET_BITS8 (ps_timer_info->timer_flag,
243 PH_LLCNFC_GUARD_TO_BIT,
244 PH_LLCNFC_TO_NOOFBITS,
245 PH_LLCNFC_GUARD_TO_BIT);
246 }
247
248 timerid = ps_timer_info->timer_id[PH_LLCNFC_GUARDTIMER];
249 Callback = (ppCallBck_t)&phLlcNfc_GuardTimeoutCb;
250
251 /* Guard time out value */
252 ps_timer_info->guard_to_value[timer_count] = (uint16_t)
253 PH_LLCNFC_GUARD_TO_VALUE;
254
255 ps_timer_info->timer_ns_value[timer_count] = ns_value;
256 ps_timer_info->frame_type[timer_count] = (uint8_t)invalid_frame;
257 ps_timer_info->iframe_send_count[timer_count] = 0;
258
259 if ((timer_count > 0) &&
260 (ps_timer_info->guard_to_value[(timer_count - 1)] >=
261 PH_LLCNFC_GUARD_TO_VALUE))
262 {
263 /* If the timer has been started already and the
264 value is same as the previous means that timer has still
265 not expired, so the time out value is increased by
266 a resolution */
267 ps_timer_info->guard_to_value[timer_count] = (uint16_t)
268 (ps_timer_info->guard_to_value[(timer_count - 1)] +
269 PH_LLCNFC_RESOLUTION);
270 }
271
272 PH_LLCNFC_DEBUG("GUARD TIMER VALUE : 0x%04X\n", ps_timer_info->guard_to_value[timer_count]);
273
274
275 ps_timer_info->guard_to_count = (uint8_t)(
276 ps_timer_info->guard_to_count + 1);
277 }
278 else
279 {
280 /* TIMER should not start, because the time out count has readched the limit */
281 timerstarted = TRUE;
282 }
283 break;
284 }
285
286 #ifdef PIGGY_BACK
287
288 case PH_LLCNFC_ACKTIMER:
289 {
290 /* Get the ack timer flag */
291 timerstarted = (uint8_t)GET_BITS8 (
292 ps_timer_info->timer_flag,
293 PH_LLCNFC_ACK_TO_BIT,
294 PH_LLCNFC_TO_NOOFBITS);
295
296 if (FALSE == timerstarted)
297 {
298 /* Timer not started, so start the timer */
299 ps_timer_info->timer_flag = (uint8_t)
300 SET_BITS8 (ps_timer_info->timer_flag,
301 PH_LLCNFC_ACK_TO_BIT,
302 PH_LLCNFC_TO_NOOFBITS,
303 (PH_LLCNFC_ACK_TO_BIT - 1));
304 }
305
306
307 timer_resolution = ps_timer_info->ack_to_value = (uint16_t)
308 PH_LLCNFC_ACK_TO_VALUE;
309 timerid = ps_timer_info->timer_id[PH_LLCNFC_ACKTIMER];
310 Callback = (ppCallBck_t)&phLlcNfc_AckTimeoutCb;
311 break;
312 }
313
314 #endif /* #ifdef PIGGY_BACK */
315
316 default:
317 {
318 result = PHNFCSTVAL(CID_NFC_LLC,
319 NFCSTATUS_INVALID_PARAMETER);
320 break;
321 }
322 }
323 if ((NFCSTATUS_SUCCESS == result) &&
324 (FALSE == timerstarted))
325 {
326 PH_LLCNFC_DEBUG("OSAL START TIMER CALLED TIMER ID : 0x%02X\n", timerid);
327 phOsalNfc_Timer_Start (timerid, timer_resolution, Callback, NULL);
328 }
329
330 PH_LLCNFC_PRINT("\n\nLLC : START TIMER END\n\n");
331
332 #else /* #ifdef LLC_TIMER_ENABLE */
333
334 PHNFC_UNUSED_VARIABLE(result);
335 PHNFC_UNUSED_VARIABLE(TimerType);
336 PHNFC_UNUSED_VARIABLE(ns_value);
337
338 #endif /* #ifdef LLC_TIMER_ENABLE */
339 return result;
340 }
341
342 void
phLlcNfc_StopTimers(uint8_t TimerType,uint8_t no_of_guard_to_del)343 phLlcNfc_StopTimers (
344 uint8_t TimerType,
345 uint8_t no_of_guard_to_del
346 )
347 {
348 NFCSTATUS result = NFCSTATUS_SUCCESS;
349 #ifdef LLC_TIMER_ENABLE
350
351 uint32_t timerid = 0,
352 timerflag = FALSE;
353 uint8_t timer_count = 0;
354 phLlcNfc_Timerinfo_t *ps_timer_info = NULL;
355
356
357 ps_timer_info = &(gpphLlcNfc_Ctxt->s_timerinfo);
358 timerflag = ps_timer_info->timer_flag;
359
360 PHNFC_UNUSED_VARIABLE (result);
361 PH_LLCNFC_PRINT("\n\nLLC : STOP TIMER CALLED\n\n");
362 switch(TimerType)
363 {
364 case PH_LLCNFC_CONNECTIONTIMER:
365 {
366 ps_timer_info->timer_flag = (uint8_t)
367 SET_BITS8(ps_timer_info->timer_flag,
368 PH_LLCNFC_CON_TO_BIT,
369 PH_LLCNFC_TO_NOOFBITS, 0);
370 timerid = ps_timer_info->timer_id
371 [PH_LLCNFC_CONNECTION_TO_INDEX];
372 break;
373 }
374
375 case PH_LLCNFC_GUARDTIMER:
376 {
377 uint8_t start_index = 0;
378
379 timer_count = ps_timer_info->guard_to_count;
380
381 PH_LLCNFC_DEBUG("GUARD TIMER COUNT BEFORE DELETE: 0x%02X\n", timer_count);
382 PH_LLCNFC_DEBUG("GUARD TIMER TO DELETE: 0x%02X\n", no_of_guard_to_del);
383
384 if (timer_count > no_of_guard_to_del)
385 {
386 /* The number of guard timer count is more than the
387 guard timer to delete */
388 while (start_index < (timer_count - no_of_guard_to_del))
389 {
390 /* Copy the previous stored timer values to the present */
391 ps_timer_info->guard_to_value[start_index] = (uint16_t)
392 (ps_timer_info->guard_to_value[
393 (no_of_guard_to_del + start_index)]);
394
395 ps_timer_info->iframe_send_count[start_index] = (uint8_t)
396 (ps_timer_info->iframe_send_count[
397 (no_of_guard_to_del + start_index)]);
398
399 PH_LLCNFC_DEBUG("GUARD TIMER NS INDEX DELETED : 0x%02X\n", ps_timer_info->timer_ns_value[start_index]);
400
401 ps_timer_info->timer_ns_value[start_index] = (uint8_t)
402 (ps_timer_info->timer_ns_value[
403 (no_of_guard_to_del + start_index)]);
404
405 ps_timer_info->frame_type[start_index] = (uint8_t)
406 (ps_timer_info->frame_type[
407 (no_of_guard_to_del + start_index)]);
408
409 start_index = (uint8_t)(start_index + 1);
410 }
411 }
412 else
413 {
414 while (start_index < no_of_guard_to_del)
415 {
416 ps_timer_info->guard_to_value[start_index] = 0;
417
418 ps_timer_info->iframe_send_count[start_index] = 0;
419
420 PH_LLCNFC_DEBUG("GUARD TIMER NS INDEX DELETED ELSE : 0x%02X\n", ps_timer_info->timer_ns_value[start_index]);
421
422 ps_timer_info->timer_ns_value[start_index] = 0;
423
424 ps_timer_info->frame_type[start_index] = 0;
425
426 start_index = (uint8_t)(start_index + 1);
427 }
428 }
429
430 if (timer_count >= no_of_guard_to_del)
431 {
432 timer_count = (uint8_t)(timer_count - no_of_guard_to_del);
433 }
434 else
435 {
436 if (0 != no_of_guard_to_del)
437 {
438 timer_count = 0;
439 }
440 }
441
442 timerid = ps_timer_info->timer_id[PH_LLCNFC_GUARDTIMER];
443 ps_timer_info->guard_to_count = timer_count;
444 PH_LLCNFC_DEBUG("GUARD TIMER COUNT AFTER DELETE: 0x%02X\n", timer_count);
445
446 if (0 == ps_timer_info->guard_to_count)
447 {
448 /* This means that there are no frames to run guard
449 timer, so set the timer flag to 0 */
450 ps_timer_info->timer_flag = (uint8_t)
451 SET_BITS8 (ps_timer_info->timer_flag,
452 PH_LLCNFC_GUARD_TO_BIT,
453 PH_LLCNFC_TO_NOOFBITS, 0);
454 }
455 else
456 {
457 timerflag = 0;
458 }
459 break;
460 }
461
462 #ifdef PIGGY_BACK
463 case PH_LLCNFC_ACKTIMER:
464 {
465 timerflag = (timerflag & PH_LLCNFC_ACK_TO_BIT_VAL);
466
467 ps_timer_info->timer_flag = (uint8_t)
468 SET_BITS8 (ps_timer_info->timer_flag,
469 PH_LLCNFC_ACK_TO_BIT,
470 PH_LLCNFC_TO_NOOFBITS, 0);
471 timerid = ps_timer_info->timer_id[PH_LLCNFC_ACKTIMER];
472 ps_timer_info->ack_to_value = 0;
473 break;
474 }
475 #endif /* #ifdef PIGGY_BACK */
476
477 default:
478 {
479 result = PHNFCSTVAL(CID_NFC_LLC,
480 NFCSTATUS_INVALID_PARAMETER);
481 break;
482 }
483 }
484
485 if ((NFCSTATUS_SUCCESS == result) && (timerflag > 0))
486 {
487 PH_LLCNFC_DEBUG("OSAL STOP TIMER CALLED TIMER ID : 0x%02X\n", timerid);
488 phOsalNfc_Timer_Stop (timerid);
489 }
490
491 PH_LLCNFC_PRINT("\n\nLLC : STOP TIMER END\n\n");
492
493 #else /* #ifdef LLC_TIMER_ENABLE */
494
495 PHNFC_UNUSED_VARIABLE (result);
496 PHNFC_UNUSED_VARIABLE (TimerType);
497 PHNFC_UNUSED_VARIABLE (no_of_guard_to_del);
498
499 #endif /* #ifdef LLC_TIMER_ENABLE */
500 }
501
502 void
phLlcNfc_StopAllTimers(void)503 phLlcNfc_StopAllTimers (void)
504 {
505
506 #ifdef LLC_TIMER_ENABLE
507
508 phLlcNfc_Timerinfo_t *ps_timer_info = NULL;
509 uint8_t timer_started = 0;
510 uint32_t timerid = 0;
511 uint8_t timer_index = 0;
512
513
514 ps_timer_info = &(gpphLlcNfc_Ctxt->s_timerinfo);
515
516 PH_LLCNFC_PRINT("\n\nLLC : STOP ALL TIMERS CALLED \n\n");
517
518 timerid = ps_timer_info->timer_id[timer_index];
519 timer_started = (uint8_t)
520 GET_BITS8(ps_timer_info->timer_flag,
521 PH_LLCNFC_CON_TO_BIT,
522 PH_LLCNFC_TO_NOOFBITS);
523
524 PH_LLCNFC_DEBUG("CONNECTION TIMER ID: 0x%02X\n", timerid);
525
526 if (0 != timer_started)
527 {
528 /* Connection timer is started, so now stop it */
529 ps_timer_info->timer_flag = (uint8_t)
530 SET_BITS8 (ps_timer_info->timer_flag,
531 PH_LLCNFC_CON_TO_BIT,
532 PH_LLCNFC_TO_NOOFBITS, 0);
533 #if 0
534
535 ps_timer_info->con_to_value = 0;
536
537 #endif /* #if 0 */
538
539 phOsalNfc_Timer_Stop (timerid);
540 }
541
542 timer_index = (uint8_t)(timer_index + 1);
543 timerid = ps_timer_info->timer_id[timer_index];
544 timer_started = (uint8_t)GET_BITS8 (ps_timer_info->timer_flag,
545 PH_LLCNFC_GUARD_TO_BIT,
546 PH_LLCNFC_TO_NOOFBITS);
547
548 if (0 != timer_started)
549 {
550 /* Guard timer is already started */
551 ps_timer_info->timer_flag = (uint8_t)
552 SET_BITS8 (ps_timer_info->timer_flag,
553 PH_LLCNFC_GUARD_TO_BIT,
554 PH_LLCNFC_TO_NOOFBITS, 0);
555
556 timer_index = 0;
557 ps_timer_info->guard_to_count = 0;
558
559 #if 0
560
561 /* Reset all the guard timer related variables */
562 while (timer_index < ps_timer_info->guard_to_count)
563 {
564 ps_timer_info->guard_to_value[timer_index] = 0;
565 ps_timer_info->iframe_send_count[timer_index] = 0;
566
567 timer_index = (uint8_t)(timer_index + 1);
568 }
569
570 #endif /* #if 0 */
571
572 PH_LLCNFC_DEBUG("GUARD TIMER ID: 0x%02X\n", timerid);
573
574 /* Stop the timer */
575 phOsalNfc_Timer_Stop (timerid);
576
577 PH_LLCNFC_PRINT("\n\nLLC : STOP ALL TIMERS END \n\n");
578 }
579
580 #endif /* #ifdef LLC_TIMER_ENABLE */
581 }
582
583 void
phLlcNfc_DeleteTimer(void)584 phLlcNfc_DeleteTimer (void)
585 {
586 uint8_t index = 0;
587 while (index < PH_LLCNFC_MAX_TIMER_USED)
588 {
589 #ifdef LLC_TIMER_ENABLE
590 phOsalNfc_Timer_Delete(
591 gpphLlcNfc_Ctxt->s_timerinfo.timer_id[index]);
592 gpphLlcNfc_Ctxt->s_timerinfo.timer_id[index] =
593 PH_OSALNFC_INVALID_TIMER_ID;
594 #endif /* #ifdef LLC_TIMER_ENABLE */
595 index++;
596 }
597 }
598
599 #ifdef LLC_TIMER_ENABLE
600
601 #define LLC_GUARD_TIMER_RETRIES (0x03U)
602
603 static
604 void
phLlcNfc_GuardTimeoutCb(uint32_t TimerId,void * pContext)605 phLlcNfc_GuardTimeoutCb (
606 uint32_t TimerId,
607 void *pContext
608 )
609 {
610 NFCSTATUS result = NFCSTATUS_SUCCESS;
611 phLlcNfc_Timerinfo_t *ps_timer_info = NULL;
612 phLlcNfc_Frame_t *ps_frame_info = NULL;
613 phLlcNfc_LlcPacket_t s_packet_info;
614 uint8_t index = 0;
615 /* zero_to_index = Time out index has become 0 */
616 uint8_t zero_to_index = 0;
617
618 #if defined (GUARD_TO_ERROR)
619 phNfc_sCompletionInfo_t notifyinfo = {0,0,0};
620 #endif /* #if defined (GUARD_TO_ERROR) */
621
622 PH_LLCNFC_PRINT("\n\nLLC : GUARD TIMEOUT CB CALLED \n\n");
623
624 if ((NULL != gpphLlcNfc_Ctxt) && (TimerId ==
625 gpphLlcNfc_Ctxt->s_timerinfo.timer_id[PH_LLCNFC_GUARDTIMER]) &&
626 (PH_LLCNFC_GUARD_TO_BIT_VAL ==
627 (gpphLlcNfc_Ctxt->s_timerinfo.timer_flag &
628 PH_LLCNFC_GUARD_TO_BIT_VAL)))
629 {
630 uint8_t timer_expired = FALSE;
631
632 ps_frame_info = &(gpphLlcNfc_Ctxt->s_frameinfo);
633 ps_timer_info = &(gpphLlcNfc_Ctxt->s_timerinfo);
634
635 #if !defined (CYCLIC_TIMER)
636 phOsalNfc_Timer_Stop(
637 ps_timer_info->timer_id[PH_LLCNFC_GUARDTIMER]);
638 #endif
639
640 PH_LLCNFC_DEBUG("NO OF TIMEOUT COUNT : 0x%02X\n", ps_timer_info->guard_to_count);
641 /* Loop is completely depending on the number of different LLC
642 send called */
643 while (index < ps_timer_info->guard_to_count)
644 {
645 /* This loop runs for all the timer present in the data structure.
646 This means if there are 2 I frame has been sent and
647 response is not received for the I frames sent then the
648 each time this timer expires, the time out value is decremented
649 by the PH_LLCNFC_RESOLUTION value */
650 if (0 != ps_timer_info->guard_to_value[index])
651 {
652 /* If timer value is not zero then enter,
653 this means that the value is not zero */
654 if (ps_timer_info->guard_to_value[index] > 0)
655 {
656 if (ps_timer_info->guard_to_value[index] >=
657 PH_LLCNFC_RESOLUTION)
658 {
659 ps_timer_info->guard_to_value[index] = (uint16_t)
660 (ps_timer_info->guard_to_value[index] -
661 PH_LLCNFC_RESOLUTION);
662 }
663 else
664 {
665 ps_timer_info->guard_to_value[index] = 0;
666 }
667 }
668
669 if (0 == ps_timer_info->guard_to_value[index])
670 {
671 /* Timer value has expired, so resend has to be done
672 Timer value is 0 */
673 ps_timer_info->frame_type[index] = (uint8_t)resend_i_frame;
674 if (FALSE == timer_expired)
675 {
676 /* As the statement is in the loop, so there are possibilities
677 of more than 1 timer value can be 0, so if previous timer
678 value has already been 0, then again dont change the
679 index */
680 zero_to_index = index;
681 timer_expired = TRUE;
682 }
683 }
684 }
685 index = (uint8_t)(index + 1);
686 }
687
688 #if !defined (CYCLIC_TIMER)
689 /* Start the timer again */
690 phOsalNfc_Timer_Start(
691 ps_timer_info->timer_id[PH_LLCNFC_GUARDTIMER],
692 PH_LLCNFC_RESOLUTION, phLlcNfc_GuardTimeoutCb, NULL);
693 #endif
694 PH_LLCNFC_DEBUG("TIMER EXPIRED : 0x%02X\n", timer_expired);
695
696 if (TRUE == timer_expired)
697 {
698 PH_LLCNFC_DEBUG("TIMER EXPIRED INDEX: 0x%02X\n", zero_to_index);
699 PH_LLCNFC_DEBUG("TIMER EXPIRED NS INDEX: 0x%02X\n", ps_timer_info->timer_ns_value[zero_to_index]);
700 PH_LLCNFC_DEBUG("TIMER EXPIRED RETRIES : 0x%02X\n", ps_timer_info->iframe_send_count[zero_to_index]);
701
702 PH_LLCNFC_DEBUG("TIMER EXPIRED GUARD TIME-OUT COUNT: 0x%02X\n", ps_timer_info->guard_to_value[zero_to_index]);
703
704 if ((0 == ps_timer_info->guard_to_value[zero_to_index]) &&
705 (ps_timer_info->iframe_send_count[zero_to_index] <
706 LLC_GUARD_TIMER_RETRIES))
707 {
708 if (ps_frame_info->s_send_store.winsize_cnt > 0)
709 {
710 uint8_t start_index = 0;
711 uint8_t timer_count = 0;
712 uint8_t while_exit = FALSE;
713
714 timer_count = ps_timer_info->guard_to_count;
715
716 /* Check before changing the index to resend, if index
717 already exist then dont set the index */
718 while ((FALSE == while_exit) && (start_index < timer_count))
719 {
720 if (resend_i_frame ==
721 ps_timer_info->frame_type[start_index])
722 {
723 while_exit = TRUE;
724 }
725 else
726 {
727 start_index = (uint8_t)(start_index + 1);
728 }
729 }
730
731 if (FALSE == while_exit)
732 {
733 /* This " ps_timer_info->index_to_send " member is
734 useful, when 2 time out values are 0, then
735 only first timed out value has to be resent and
736 other has to wait until the the first timed out
737 I frame is resent
738 This statement is executed only if, none of the timer
739 has expires previously, this is the first timer in the
740 list that has time out value has 0
741 */
742 ps_timer_info->index_to_send = zero_to_index;
743 }
744 else
745 {
746 /* This statement is executed only if, any one of the time
747 out value was 0 previously, so first resend has to be done
748 for the previous I frame, so the index is set to the previous
749 I frame
750 */
751 ps_timer_info->index_to_send = start_index;
752 }
753
754 /* Now resend the frame stored */
755 result = phLlcNfc_H_SendTimedOutIFrame (gpphLlcNfc_Ctxt,
756 &(ps_frame_info->s_send_store),
757 0);
758 }
759 }
760 else
761 {
762 if ((LLC_GUARD_TIMER_RETRIES ==
763 ps_timer_info->iframe_send_count[zero_to_index]) &&
764 (NULL != gpphLlcNfc_Ctxt->cb_for_if.notify))
765 {
766 phLlcNfc_StopAllTimers ();
767 #if defined (GUARD_TO_ERROR)
768
769 notifyinfo.status = PHNFCSTVAL(CID_NFC_LLC,
770 NFCSTATUS_BOARD_COMMUNICATION_ERROR);
771 #if 0
772 phOsalNfc_RaiseException(phOsalNfc_e_UnrecovFirmwareErr,1);
773 #endif /* #if 0 */
774 /* Resend done, no answer from the device */
775 gpphLlcNfc_Ctxt->cb_for_if.notify (
776 gpphLlcNfc_Ctxt->cb_for_if.pif_ctxt,
777 gpphLlcNfc_Ctxt->phwinfo,
778 NFC_NOTIFY_DEVICE_ERROR,
779 ¬ifyinfo);
780
781 #endif /* #if defined (GUARD_TO_ERROR) */
782
783 #if (!defined (GUARD_TO_ERROR) && defined (GUARD_TO_URSET))
784
785 PH_LLCNFC_PRINT("U-RSET IS SENT \n");
786
787 result = phLlcNfc_H_CreateUFramePayload(gpphLlcNfc_Ctxt,
788 &(s_packet_info),
789 &(s_packet_info.llcbuf_len),
790 phLlcNfc_e_rset);
791
792 result = phLlcNfc_Interface_Write(gpphLlcNfc_Ctxt,
793 (uint8_t*)&(s_packet_info.s_llcbuf),
794 (uint32_t)s_packet_info.llcbuf_len);
795
796 ps_frame_info->write_status = result;
797 if (NFCSTATUS_PENDING == result)
798 {
799 /* Start the timer */
800 result = phLlcNfc_StartTimers (PH_LLCNFC_CONNECTIONTIMER, 0);
801 if (NFCSTATUS_SUCCESS == result)
802 {
803 ps_frame_info->retry_cnt = 0;
804 gpphLlcNfc_Ctxt->s_frameinfo.sent_frame_type =
805 u_rset_frame;
806 result = NFCSTATUS_PENDING;
807 }
808 }
809 else
810 {
811 if (NFCSTATUS_BUSY == PHNFCSTATUS (result))
812 {
813 ps_frame_info->write_wait_call = u_rset_frame;
814 }
815 }
816
817 #endif /* #if defined (GUARD_TO_ERROR) */
818 }
819 }
820 }
821 }
822 PH_LLCNFC_PRINT("\n\nLLC : GUARD TIMEOUT CB END\n\n");
823 }
824
825 #ifdef PIGGY_BACK
826
827 static
828 void
phLlcNfc_AckTimeoutCb(uint32_t TimerId)829 phLlcNfc_AckTimeoutCb (
830 uint32_t TimerId
831 )
832 {
833 NFCSTATUS result = NFCSTATUS_SUCCESS;
834 phLlcNfc_Frame_t *ps_frame_info = NULL;
835 phLlcNfc_Timerinfo_t *ps_timer_info = NULL;
836 phLlcNfc_LlcPacket_t s_packet_info;
837
838 PH_LLCNFC_PRINT("\n\nLLC : ACK TIMEOUT CB CALLED\n\n");
839
840 if ((NULL != gpphLlcNfc_Ctxt) && (TimerId ==
841 gpphLlcNfc_Ctxt->s_timerinfo.timer_id[PH_LLCNFC_ACKTIMER])
842 && (PH_LLCNFC_ACK_TO_BIT_VAL ==
843 (gpphLlcNfc_Ctxt->s_timerinfo.timer_flag &
844 PH_LLCNFC_ACK_TO_BIT_VAL)))
845 {
846 ps_frame_info = &(gpphLlcNfc_Ctxt->s_frameinfo);
847 ps_timer_info = &(gpphLlcNfc_Ctxt->s_timerinfo);
848
849 phLlcNfc_StopTimers (PH_LLCNFC_ACKTIMER, 0);
850
851 if (NFCSTATUS_BUSY == PHNFCSTATUS (ps_frame_info->write_status))
852 {
853 /* Any how write cannot be done and some frame is ready to be sent
854 so this frame will act as the ACK */
855 result = phLlcNfc_H_WriteWaitCall (gpphLlcNfc_Ctxt);
856 }
857 else
858 {
859 /* Create S frame */
860 (void)phLlcNfc_H_CreateSFramePayload (ps_frame_info, &(s_packet_info), phLlcNfc_e_rr);
861
862 result = phLlcNfc_Interface_Write(gpphLlcNfc_Ctxt,
863 (uint8_t *)&(s_packet_info.s_llcbuf),
864 (uint32_t)(s_packet_info.llcbuf_len));
865
866 if (NFCSTATUS_PENDING == result)
867 {
868 if (0 == ps_frame_info->send_error_count)
869 {
870 ps_frame_info->write_wait_call = invalid_frame;
871 }
872 ps_frame_info->sent_frame_type = s_frame;
873 }
874 else
875 {
876 if (invalid_frame == ps_frame_info->write_wait_call)
877 {
878 ps_frame_info->write_wait_call = s_frame;
879 }
880 }
881 }
882 }
883
884 /* ACK is sent, so reset the response received count */
885 gpphLlcNfc_Ctxt->s_frameinfo.resp_recvd_count = 0;
886
887 PH_LLCNFC_PRINT("\n\nLLC : ACK TIMEOUT CB END\n\n");
888 }
889
890 #endif /* #ifdef PIGGY_BACK */
891
892 static
893 void
phLlcNfc_ConnectionTimeoutCb(uint32_t TimerId,void * pContext)894 phLlcNfc_ConnectionTimeoutCb (
895 uint32_t TimerId,
896 void *pContext
897 )
898 {
899 NFCSTATUS result = NFCSTATUS_SUCCESS;
900 phNfc_sCompletionInfo_t notifyinfo = {0,0,0};
901 pphNfcIF_Notification_CB_t notifyul = NULL;
902 void *p_upperctxt = NULL;
903 phLlcNfc_Frame_t *ps_frame_info = NULL;
904 phLlcNfc_Timerinfo_t *ps_timer_info = NULL;
905 phLlcNfc_LlcPacket_t s_packet_info;
906
907 PH_LLCNFC_PRINT("\n\nLLC : CONNECTION TIMEOUT CB CALLED\n\n");
908 if ((NULL != gpphLlcNfc_Ctxt) && (TimerId ==
909 gpphLlcNfc_Ctxt->s_timerinfo.timer_id[PH_LLCNFC_CONNECTIONTIMER])
910 && (PH_LLCNFC_CON_TO_BIT_VAL ==
911 (gpphLlcNfc_Ctxt->s_timerinfo.timer_flag &
912 PH_LLCNFC_CON_TO_BIT_VAL)))
913 {
914 ps_frame_info = &(gpphLlcNfc_Ctxt->s_frameinfo);
915 ps_timer_info = &(gpphLlcNfc_Ctxt->s_timerinfo);
916 if (ps_timer_info->con_to_value > 0)
917 {
918 #if !defined (CYCLIC_TIMER)
919 phOsalNfc_Timer_Stop(
920 ps_timer_info->timer_id[PH_LLCNFC_CONNECTIONTIMER]);
921 /* phLlcNfc_StopTimers(PH_LLCNFC_CONNECTIONTIMER, 0); */
922 #endif
923 ps_timer_info->con_to_value = 0;
924
925 if (0 == ps_timer_info->con_to_value)
926 {
927 PH_LLCNFC_DEBUG("TIMER EXPIRED RETRY COUNT : %02X\n", ps_frame_info->retry_cnt);
928 phLlcNfc_StopTimers (PH_LLCNFC_CONNECTIONTIMER, 0);
929
930 if (ps_frame_info->retry_cnt < PH_LLCNFC_MAX_RETRY_COUNT)
931 {
932 /* Create a U frame */
933 result = phLlcNfc_H_CreateUFramePayload(gpphLlcNfc_Ctxt,
934 &(s_packet_info),
935 &(s_packet_info.llcbuf_len),
936 phLlcNfc_e_rset);
937
938 if (NFCSTATUS_SUCCESS == result)
939 {
940 /* Call DAL write */
941 result = phLlcNfc_Interface_Write (gpphLlcNfc_Ctxt,
942 (uint8_t*)&(s_packet_info.s_llcbuf),
943 (uint32_t)(s_packet_info.llcbuf_len));
944 }
945 if (NFCSTATUS_PENDING == result)
946 {
947 /* Start the timer */
948 result = phLlcNfc_StartTimers(PH_LLCNFC_CONNECTIONTIMER, 0);
949 if (NFCSTATUS_SUCCESS == result)
950 {
951 ps_frame_info->retry_cnt++;
952 result = NFCSTATUS_PENDING;
953 }
954 }
955 else
956 {
957 if (NFCSTATUS_BUSY == PHNFCSTATUS(result))
958 {
959 result = NFCSTATUS_PENDING;
960 }
961 }
962 }
963 else
964 {
965 PH_LLCNFC_PRINT("RETRY COUNT LIMIT REACHED \n");
966 if ((ps_frame_info->retry_cnt == PH_LLCNFC_MAX_RETRY_COUNT)
967 && (NULL != gpphLlcNfc_Ctxt->cb_for_if.notify))
968 {
969 void *p_hw_info = NULL;
970 uint8_t type = 0;
971
972 p_hw_info = gpphLlcNfc_Ctxt->phwinfo;
973 notifyinfo.status = PHNFCSTVAL(CID_NFC_LLC,
974 NFCSTATUS_BOARD_COMMUNICATION_ERROR);
975
976 notifyul = gpphLlcNfc_Ctxt->cb_for_if.notify;
977 p_upperctxt = gpphLlcNfc_Ctxt->cb_for_if.pif_ctxt;
978 type = NFC_NOTIFY_ERROR;
979 if (init_u_rset_frame == ps_frame_info->sent_frame_type)
980 {
981 type = NFC_NOTIFY_INIT_FAILED;
982 /* Release if, the initialisation is not complete */
983 result = phLlcNfc_Release(gpphLlcNfc_Ctxt, p_hw_info);
984 gpphLlcNfc_Ctxt = NULL;
985 }
986 else
987 {
988 type = NFC_NOTIFY_DEVICE_ERROR;
989 notifyinfo.status = PHNFCSTVAL(CID_NFC_LLC,
990 NFCSTATUS_BOARD_COMMUNICATION_ERROR);
991 #if 0
992 phOsalNfc_RaiseException(phOsalNfc_e_UnrecovFirmwareErr,1);
993 #endif /* #if 0 */
994 }
995 /* Notify the upper layer */
996 notifyul(p_upperctxt, p_hw_info, type, ¬ifyinfo);
997 }
998 }
999 }
1000 #if !defined (CYCLIC_TIMER)
1001 else
1002 {
1003 /* Start the timer again */
1004 phOsalNfc_Timer_Start(
1005 ps_timer_info->timer_id[PH_LLCNFC_CONNECTIONTIMER],
1006 ps_timer_info->con_to_value, phLlcNfc_ConnectionTimeoutCb, NULL);
1007 }
1008 #endif
1009 }
1010 }
1011 PH_LLCNFC_PRINT("\n\nLLC : CONNECTION TIMEOUT CB END\n\n");
1012 }
1013 #endif /* #ifdef LLC_TIMER_ENABLE */
1014
1015 #ifdef LLC_URSET_NO_DELAY
1016
1017 /* NO definition required */
1018
1019 #else /* #ifdef LLC_URSET_NO_DELAY */
1020
1021 void
phLlcNfc_URSET_Delay_Notify(uint32_t delay_id,void * pContext)1022 phLlcNfc_URSET_Delay_Notify (
1023 uint32_t delay_id,
1024 void *pContext)
1025 {
1026 phLlcNfc_Frame_t *ps_frame_info = NULL;
1027 phNfc_sCompletionInfo_t notifyinfo = {0,0,0};
1028
1029 if (NULL != gpphLlcNfc_Ctxt)
1030 {
1031 ps_frame_info = &(gpphLlcNfc_Ctxt->s_frameinfo);
1032
1033 phOsalNfc_Timer_Stop (delay_id);
1034 phOsalNfc_Timer_Delete (delay_id);
1035 if (ps_frame_info->s_send_store.winsize_cnt > 0)
1036 {
1037 #if 0
1038
1039 /* Resend I frame */
1040 (void)phLlcNfc_H_SendTimedOutIFrame (gpphLlcNfc_Ctxt,
1041 &(ps_frame_info->s_send_store), 0);
1042
1043 #else
1044
1045 (void)phLlcNfc_H_SendUserIFrame (gpphLlcNfc_Ctxt,
1046 &(ps_frame_info->s_send_store));
1047
1048 #endif /* #if 0 */
1049 gpphLlcNfc_Ctxt->state = phLlcNfc_Resend_State;
1050 }
1051 else
1052 {
1053 if ((init_u_rset_frame == ps_frame_info->sent_frame_type) &&
1054 (NULL != gpphLlcNfc_Ctxt->cb_for_if.notify))
1055 {
1056 ps_frame_info->sent_frame_type = write_resp_received;
1057 notifyinfo.status = NFCSTATUS_SUCCESS;
1058 /* Send the notification to the upper layer */
1059 gpphLlcNfc_Ctxt->cb_for_if.notify (
1060 gpphLlcNfc_Ctxt->cb_for_if.pif_ctxt,
1061 gpphLlcNfc_Ctxt->phwinfo,
1062 NFC_NOTIFY_INIT_COMPLETED,
1063 ¬ifyinfo);
1064 }
1065 }
1066 }
1067 }
1068
1069 #endif /* #ifdef LLC_URSET_NO_DELAY */
1070
1071