• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * osapi.c
3  *
4  * Copyright(c) 1998 - 2010 Texas Instruments. All rights reserved.
5  * All rights reserved.
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
10  *
11  *  * Redistributions of source code must retain the above copyright
12  *    notice, this list of conditions and the following disclaimer.
13  *  * Redistributions in binary form must reproduce the above copyright
14  *    notice, this list of conditions and the following disclaimer in
15  *    the documentation and/or other materials provided with the
16  *    distribution.
17  *  * Neither the name Texas Instruments nor the names of its
18  *    contributors may be used to endorse or promote products derived
19  *    from this software without specific prior written permission.
20  *
21  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
22  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
23  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
24  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
25  * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
26  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
27  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
28  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
29  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
30  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
31  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
32  */
33 
34 
35 /*
36  * src/osapi.c
37  *
38  */
39 #include "tidef.h"
40 #include "arch_ti.h"
41 
42 #include <linux/stddef.h>
43 #include <linux/string.h>
44 #include <linux/time.h>
45 #include <linux/timer.h>
46 #include <linux/module.h>
47 #include <linux/kernel.h>
48 #include <linux/netdevice.h>
49 #include <linux/completion.h>
50 #include <linux/etherdevice.h>
51 #include <linux/vmalloc.h>
52 #include <linux/string.h>
53 #include <linux/delay.h>
54 #include <linux/time.h>
55 #include <linux/list.h>
56 #include <stdarg.h>
57 #include <asm/io.h>
58 #include "RxBuf_linux.h"
59 
60 /*#include "debug_module.h"*/
61 #include "host_platform.h"
62 #include "WlanDrvIf.h"
63 #include "bmtrace_api.h"
64 #include "TI_IPC_Api.h"
65 #include "802_11Defs.h"
66 #include "osApi.h"
67 #include "txMgmtQueue_Api.h"
68 #include "EvHandler.h"
69 
70 #ifdef ESTA_TIMER_DEBUG
71 #define esta_timer_log(fmt,args...)  printk(fmt, ## args)
72 #else
73 #define esta_timer_log(fmt,args...)
74 #endif
75 
76 #define FRAG_SIZE        200
77 
78 typedef struct timer_list TOsTimer;
79 
80 TI_BOOL bRedirectOutputToLogger = TI_FALSE;
81 TI_BOOL use_debug_module = TI_FALSE;
82 
83 /****************************************************************************************
84  *                        																*
85  *						OS Report API													*
86  *																						*
87  ****************************************************************************************/
SendLoggerData(TI_HANDLE OsContext,TI_UINT8 * pMsg,TI_UINT16 len)88 static void SendLoggerData (TI_HANDLE OsContext, TI_UINT8 *pMsg, TI_UINT16 len)
89 {
90 	TWlanDrvIfObj *drv = (TWlanDrvIfObj *)OsContext;
91 
92 	if (len > 0)
93 	{
94 		EvHandlerSendEvent(drv->tCommon.hEvHandler, IPC_EVENT_LOGGER, pMsg, len);
95 	}
96 }
97 
os_setDebugOutputToLogger(TI_BOOL value)98 void os_setDebugOutputToLogger(TI_BOOL value)
99 {
100 	bRedirectOutputToLogger = value;
101 }
102 /****************************************************************************************
103  *                        os_setDebugMode()
104  ****************************************************************************************
105 DESCRIPTION:  	Set the Debug Mode
106 
107 INPUT:
108 
109 RETURN:			None
110 
111 NOTES:
112 *****************************************************************************************/
os_setDebugMode(TI_BOOL enable)113 void os_setDebugMode(TI_BOOL enable)
114 {
115 	use_debug_module = enable;
116 }
117 
118 
119 /****************************************************************************************
120  *                        os_printf()
121  ****************************************************************************************
122 DESCRIPTION:  	Print formatted output.
123 
124 INPUT:          format -  Specifies the string, to be printed
125 
126 RETURN:			None
127 
128 NOTES:
129 *****************************************************************************************/
os_printf(const char * format,...)130 void os_printf(const char *format ,...)
131 {
132 	static int from_new_line = 1;		/* Used to save the last message EOL */
133 	va_list ap;
134 	static char msg[MAX_MESSAGE_SIZE];
135 	char *p_msg = msg;					/* Pointer to the message */
136 	TI_UINT16 message_len;
137 	TI_UINT32 sec = 0;
138 	TI_UINT32 uSec = 0;
139 	os_memoryZero(NULL,msg, MAX_MESSAGE_SIZE);
140 
141 	/* Format the message and keep the message length */
142 	va_start(ap,format);
143 	message_len = vsnprintf(&msg[0], sizeof(msg) -1 , format, ap);
144 	if( from_new_line )
145         {
146             if (msg[1] == '$')
147             {
148                 p_msg += 4;
149             }
150 
151             sec = os_timeStampUs(NULL);
152             uSec = sec % MICROSECOND_IN_SECONDS;
153             sec /= MICROSECOND_IN_SECONDS;
154 
155             printk(KERN_INFO DRIVER_NAME ": %d.%06d: %s",sec,uSec,p_msg);
156         }
157         else
158         {
159 		printk(&msg[0]);
160         }
161 
162 	from_new_line = ( msg[message_len - 1] == '\n' );
163 
164 	va_end(ap);
165 }
166 
167 /****************************************************************************************
168  *                        																*
169  *							OS TIMER API												*
170  *																						*
171  ****************************************************************************************/
172 
173 /****************************************************************************************
174  *                        os_timerCreate()
175  ****************************************************************************************
176 DESCRIPTION:    This function creates and initializes an OS timer object associated with a
177 				caller's pRoutine function.
178 
179 ARGUMENTS:		OsContext   - The OS handle
180                 pRoutine    - The user callback function
181                 hFuncHandle - The user callback handle
182 
183 RETURN:			A handle of the created OS timer.
184 
185 NOTES:         	1) The user's callback is called directly from OS timer context when expired.
186                 2) In some OSs, it may be needed to use an intermediate callback in the
187                    osapi layer (use os_timerHandlr for that).
188 
189 *****************************************************************************************/
os_timerCreate(TI_HANDLE OsContext,fTimerFunction pRoutine,TI_HANDLE hFuncHandle)190 TI_HANDLE os_timerCreate (TI_HANDLE OsContext, fTimerFunction pRoutine, TI_HANDLE hFuncHandle)
191 {
192 	TOsTimer *pOsTimer = os_memoryAlloc (OsContext, sizeof(TOsTimer));
193 
194     if(pOsTimer)
195     {
196         init_timer (pOsTimer);
197         pOsTimer->function = (void *)pRoutine;
198         pOsTimer->data     = (int)hFuncHandle;
199     }
200 
201     return (TI_HANDLE)pOsTimer;
202 }
203 
204 
205 /****************************************************************************************
206  *                        os_timerDestroy()
207  ****************************************************************************************
208 DESCRIPTION:    This function destroys the OS timer object.
209 
210 ARGUMENTS:
211 
212 RETURN:
213 
214 NOTES:
215 *****************************************************************************************/
os_timerDestroy(TI_HANDLE OsContext,TI_HANDLE TimerHandle)216 void os_timerDestroy (TI_HANDLE OsContext, TI_HANDLE TimerHandle)
217 {
218 	os_timerStop (OsContext, TimerHandle);
219 	os_memoryFree (OsContext, TimerHandle, sizeof(TOsTimer));
220 }
221 
222 
223 /****************************************************************************************
224  *                        os_timerStart()
225  ****************************************************************************************
226 DESCRIPTION:    This function start the timer object.
227 
228 ARGUMENTS:
229 
230 RETURN:
231 
232 NOTES:
233 *****************************************************************************************/
os_timerStart(TI_HANDLE OsContext,TI_HANDLE TimerHandle,TI_UINT32 DelayMs)234 void os_timerStart (TI_HANDLE OsContext, TI_HANDLE TimerHandle, TI_UINT32 DelayMs)
235 {
236 	TI_UINT32 jiffie_cnt = msecs_to_jiffies (DelayMs);
237 
238 	mod_timer ((TOsTimer *)TimerHandle, jiffies + jiffie_cnt);
239 }
240 
241 
242 /****************************************************************************************
243  *                        os_stopTimer()
244  ****************************************************************************************
245 DESCRIPTION:    This function stop the timer object.
246 
247 ARGUMENTS:
248 
249 RETURN:
250 
251 NOTES:
252 *****************************************************************************************/
os_timerStop(TI_HANDLE OsContext,TI_HANDLE TimerHandle)253 void os_timerStop (TI_HANDLE OsContext, TI_HANDLE TimerHandle)
254 {
255 	del_timer_sync((TOsTimer *)TimerHandle);
256 }
257 
258 
259 /****************************************************************************************
260  *                        os_periodicIntrTimerStart()
261  ****************************************************************************************
262 DESCRIPTION:    This function starts the periodic interrupt mechanism. This mode is used
263 				when interrupts that usually received from the Fw is now masked, and we are
264 				checking for any need of Fw handling in time periods.
265 
266 ARGUMENTS:
267 
268 RETURN:
269 
270 NOTES:         	Power level of the CHIP should be always awake in this mode (no ELP)
271 *****************************************************************************************/
272 #ifdef PRIODIC_INTERRUPT
os_periodicIntrTimerStart(TI_HANDLE OsContext)273 void os_periodicIntrTimerStart (TI_HANDLE OsContext)
274 {
275 	TWlanDrvIfObj *drv = (TWlanDrvIfObj *)OsContext;
276 
277 	mod_timer (drv->hPollTimer, jiffies + TIWLAN_IRQ_POLL_INTERVAL);
278 }
279 #endif
280 
281 
282 /****************************************************************************************
283  *                        os_timeStampMs()
284  ****************************************************************************************
285 DESCRIPTION:	This function returns the number of milliseconds that have elapsed since
286 				the system was booted.
287 
288 ARGUMENTS:		OsContext - our adapter context.
289 
290 RETURN:
291 
292 NOTES:
293 *****************************************************************************************/
os_timeStampMs(TI_HANDLE OsContext)294 TI_UINT32 os_timeStampMs (TI_HANDLE OsContext)
295 {
296 	struct timeval tv;
297 	do_gettimeofday(&tv);
298 	return tv.tv_sec*1000 + tv.tv_usec/1000;
299 }
300 
301 
302 /****************************************************************************************
303  *                        os_timeStampUs()
304  ****************************************************************************************
305 DESCRIPTION:	This function returns the number of microseconds that have elapsed since
306 				the system was booted.
307 
308 ARGUMENTS:		OsContext - our adapter context.
309 				Note that sometimes this function will be called with NULL(!!!) as argument!
310 
311 RETURN:
312 
313 NOTES:
314 *****************************************************************************************/
os_timeStampUs(TI_HANDLE OsContext)315 TI_UINT32 os_timeStampUs (TI_HANDLE OsContext)
316 {
317 	struct timeval tv;
318 	do_gettimeofday(&tv);
319 	return tv.tv_sec*1000000 + tv.tv_usec;
320 }
321 
322 
323 /****************************************************************************************
324  *                        os_StalluSec()
325  ****************************************************************************************
326 DESCRIPTION:	This function make delay in microseconds.
327 
328 ARGUMENTS:		OsContext - our adapter context.
329 				uSec - delay time in microseconds
330 
331 RETURN:
332 
333 NOTES:
334 *****************************************************************************************/
os_StalluSec(TI_HANDLE OsContext,TI_UINT32 uSec)335 void os_StalluSec (TI_HANDLE OsContext, TI_UINT32 uSec)
336 {
337 	udelay (uSec);
338 }
339 
340 
341 /****************************************************************************************
342  *                        																*
343  *							Protection services	API										*
344  *																						*
345  ****************************************************************************************
346  * OS protection is implemented as spin_lock_irqsave and spin_unlock_irqrestore  								*
347  ****************************************************************************************/
348 
349 
350 /****************************************************************************************
351  *                        os_protectCreate()
352  ****************************************************************************************
353 DESCRIPTION:
354 
355 ARGUMENTS:		OsContext - our adapter context.
356 
357 RETURN:			A handle of the created mutex/spinlock.
358 				TI_HANDLE_INVALID if there is insufficient memory available or problems
359 				initializing the mutex
360 
361 NOTES:
362 *****************************************************************************************/
os_protectCreate(TI_HANDLE OsContext)363 TI_HANDLE os_protectCreate (TI_HANDLE OsContext)
364 {
365 	return NULL;
366 }
367 
368 
369 /****************************************************************************************
370  *                        os_protectDestroy()
371  ****************************************************************************************
372 DESCRIPTION:
373 
374 ARGUMENTS:		OsContext - our adapter context.
375 
376 RETURN:			None - This had better work since there is not a return value to the user
377 
378 NOTES:
379 *****************************************************************************************/
os_protectDestroy(TI_HANDLE OsContext,TI_HANDLE ProtectCtx)380 void os_protectDestroy (TI_HANDLE OsContext, TI_HANDLE ProtectCtx)
381 {
382 }
383 
384 
385 /****************************************************************************************
386  *                        os_protectLock()
387  ****************************************************************************************
388 DESCRIPTION:
389 
390 ARGUMENTS:		OsContext - our adapter context.
391 
392 RETURN:			None - This had better work since there is not a return value to the user
393 
394 NOTES:
395 *****************************************************************************************/
os_protectLock(TI_HANDLE OsContext,TI_HANDLE ProtectContext)396 void os_protectLock (TI_HANDLE OsContext, TI_HANDLE ProtectContext)
397 {
398 	TWlanDrvIfObj *drv = (TWlanDrvIfObj *)OsContext;
399 
400 	spin_lock_irqsave (&drv->lock, drv->flags);
401 }
402 
403 
404 /****************************************************************************************
405  *                        os_protectUnlock()
406  ****************************************************************************************
407 DESCRIPTION:
408 
409 ARGUMENTS:		OsContext - our adapter context.
410 
411 RETURN:			None - This had better work since there is not a return value to the user
412 
413 NOTES:
414 *****************************************************************************************/
os_protectUnlock(TI_HANDLE OsContext,TI_HANDLE ProtectContext)415 void os_protectUnlock (TI_HANDLE OsContext, TI_HANDLE ProtectContext)
416 {
417     TWlanDrvIfObj *drv = (TWlanDrvIfObj *)OsContext;
418 
419     spin_unlock_irqrestore (&drv->lock, drv->flags);
420 }
421 /****************************************************************************************
422  *                        os_receivePacket()
423  ****************************************************************************************
424 DESCRIPTION:
425 
426 ARGUMENTS:
427 
428 RETURN:
429 
430 NOTES:
431 *****************************************************************************************/
os_receivePacket(TI_HANDLE OsContext,void * pRxDesc,void * pPacket,TI_UINT16 Length)432 TI_BOOL os_receivePacket(TI_HANDLE OsContext, void *pRxDesc ,void *pPacket, TI_UINT16 Length)
433 {
434    TWlanDrvIfObj  *drv     = (TWlanDrvIfObj *)OsContext;
435    unsigned char  *pdata   = (unsigned char *)((TI_UINT32)pPacket & ~(TI_UINT32)0x3);
436    rx_head_t      *rx_head = (rx_head_t *)(pdata -  WSPI_PAD_BYTES - RX_HEAD_LEN_ALIGNED);
437    struct sk_buff *skb     = rx_head->skb;
438 
439 #ifdef TI_DBG
440    if ((TI_UINT32)pPacket & 0x3)
441    {
442      if ((TI_UINT32)pPacket - (TI_UINT32)skb->data != 2)
443 	 {
444 	   printk("os_receivePacket() address error skb=0x%x skb->data=0x%x pPacket=0x%x !!!\n",(int)skb, (int)skb->data, (int)pPacket);
445 	 }
446    }
447    else
448    {
449 	 if ((TI_UINT32)skb->data != (TI_UINT32)pPacket)
450 	 {
451 	   printk("os_receivePacket() address error skb=0x%x skb->data=0x%x pPacket=0x%x !!!\n",(int)skb, (int)skb->data, (int)pPacket);
452 	 }
453    }
454    if (Length != RX_ETH_PKT_LEN(pPacket))
455    {
456 	 printk("os_receivePacket() Length=%d !=  RX_ETH_PKT_LEN(pPacket)=%d!!!\n",(int)Length, RX_ETH_PKT_LEN(pPacket));
457    }
458 
459 #endif
460 /*
461    printk("-->> os_receivePacket() pPacket=0x%x Length=%d skb=0x%x skb->data=0x%x skb->head=0x%x skb->len=%d\n",
462 		  (int)pPacket, (int)Length, (int)skb, (int)skb->data, (int)skb->head, (int)skb->len);
463 */
464    /* Use skb_reserve, it updates both skb->data and skb->tail. */
465    skb->data = RX_ETH_PKT_DATA(pPacket);
466    skb->tail = skb->data;
467    skb_put(skb, RX_ETH_PKT_LEN(pPacket));
468 /*
469    printk("-->> os_receivePacket() skb=0x%x skb->data=0x%x skb->head=0x%x skb->len=%d\n",
470 		  (int)skb, (int)skb->data, (int)skb->head, (int)skb->len);
471 */
472    ti_nodprintf(TIWLAN_LOG_INFO, "os_receivePacket - Received EAPOL len-%d\n", WBUF_LEN(pWbuf));
473 
474    skb->dev       = drv->netdev;
475    skb->protocol  = eth_type_trans(skb, drv->netdev);
476    skb->ip_summed = CHECKSUM_NONE;
477 
478    drv->stats.rx_packets++;
479    drv->stats.rx_bytes += skb->len;
480 
481    /* Send the skb to the TCP stack.
482     * it responsibly of the Linux kernel to free the skb
483     */
484    {
485        CL_TRACE_START_L1();
486 
487        os_wake_lock_timeout_enable(drv);
488 
489        netif_rx_ni(skb);
490 
491        /* Note: Don't change this trace (needed to exclude OS processing from Rx CPU utilization) */
492        CL_TRACE_END_L1("tiwlan_drv.ko", "OS", "RX", "");
493    }
494 
495    return TI_TRUE;
496 }
497 
498 /*-----------------------------------------------------------------------------
499 
500 Routine Name:  os_timerHandlr
501 
502 Routine Description:
503 
504     Just a place holder for timer expiration handling in other OSs.
505     In Linux, user callback is called directly on OS timer expiry.
506 
507 Arguments:     parm - timer object handle
508 
509 Return Value:  None.
510 
511 Notes:
512 
513 -----------------------------------------------------------------------------*/
os_timerHandlr(unsigned long parm)514 void os_timerHandlr(unsigned long parm)
515 {
516     /* Not needed in Linux (user callback is called directly on OS timer expiry). */
517 }
518 
519 
520 /*-----------------------------------------------------------------------------
521 Routine Name:  os_connectionStatus
522 
523 Routine Description:
524 
525 The eSTA-DK will call this API so the OS stack is aware that the
526 WLAN layer is ready to function.
527 
528 Arguments:
529 cStatus = 1; WLAN in ready for network packets
530 cStatus = 0; WLAN in not ready for network packets
531 
532 Return Value:  None
533 -----------------------------------------------------------------------------*/
os_IndicateEvent(TI_HANDLE OsContext,IPC_EV_DATA * pData)534 TI_INT32 os_IndicateEvent (TI_HANDLE OsContext, IPC_EV_DATA* pData)
535 {
536 	IPC_EVENT_PARAMS *pInParam =  &pData->EvParams;
537 	TWlanDrvIfObj    *drv = (TWlanDrvIfObj *)OsContext;
538 	/*TI_UINT8 AuthBuf[sizeof(TI_UINT32) + sizeof(OS_802_11_AUTHENTICATION_REQUEST)];*/
539 
540 	ti_nodprintf(TIWLAN_LOG_INFO, "\n  os_ConnectionStatus Event 0x%08x \n", CsStatus->Event);
541 
542 	switch(pInParam->uEventType)
543 	{
544 		case IPC_EVENT_ASSOCIATED:
545 			if (drv->netdev != NULL)
546             	netif_carrier_on(drv->netdev);
547          	break;
548 
549        case IPC_EVENT_DISASSOCIATED:
550          	if (drv->netdev != NULL)
551         		netif_carrier_off(drv->netdev);
552       		break;
553 
554       case IPC_EVENT_LINK_SPEED:
555          	drv->tCommon.uLinkSpeed = (*(TI_UINT32*)pData->uBuffer * 10000) / 2;
556          	ti_nodprintf(TIWLAN_LOG_INFO, "\n  Link Speed = 0x%08x \n",drv->tCommon.uLinkSpeed);
557       		break;
558    }
559 
560    return TI_OK;
561 }
562 
563 
564 
565 /******************************************************************************/
566 
os_disableIrq(TI_HANDLE OsContext)567 void os_disableIrq (TI_HANDLE OsContext)
568 {
569 	TWlanDrvIfObj *drv = (TWlanDrvIfObj *)OsContext;
570 	disable_irq (drv->irq);
571 }
572 
os_enableIrq(TI_HANDLE OsContext)573 void os_enableIrq (TI_HANDLE OsContext)
574 {
575 	TWlanDrvIfObj *drv = (TWlanDrvIfObj *)OsContext;
576 	enable_irq (drv->irq);
577 }
578 
579 /*-----------------------------------------------------------------------------
580 Routine Name:  os_InterruptServiced
581 
582 Routine Description: Called when IRQ line is not asserted any more
583 					(i.e. we can enable IRQ in Level sensitive platform)
584 
585 Arguments:	OsContext - handle to OS context
586 
587 Return Value:  none
588 -----------------------------------------------------------------------------*/
os_InterruptServiced(TI_HANDLE OsContext)589 void os_InterruptServiced (TI_HANDLE OsContext)
590 {
591 	/* To be implemented with Level IRQ */
592 }
593 
594 /*-----------------------------------------------------------------------------
595 Routine Name:  os_wake_lock_timeout
596 
597 Routine Description: Called to prevent system from suspend for 1 sec
598 
599 Arguments:     OsContext - handle to OS context
600 
601 Return Value:  packet counter
602 -----------------------------------------------------------------------------*/
os_wake_lock_timeout(TI_HANDLE OsContext)603 int os_wake_lock_timeout (TI_HANDLE OsContext)
604 {
605 	TWlanDrvIfObj *drv = (TWlanDrvIfObj *)OsContext;
606 	int ret = 0;
607 	unsigned long flags;
608 
609 	if (drv) {
610 		spin_lock_irqsave(&drv->lock, flags);
611 		ret = drv->wl_packet;
612 		if (drv->wl_packet) {
613 			drv->wl_packet = 0;
614 #ifdef CONFIG_HAS_WAKELOCK
615 			wake_lock_timeout(&drv->wl_rxwake, HZ);
616 #endif
617 		}
618 		spin_unlock_irqrestore(&drv->lock, flags);
619 	}
620 	/* printk("%s: %d\n", __func__, ret); */
621 	return ret;
622 }
623 
624 /*-----------------------------------------------------------------------------
625 Routine Name:  os_wake_lock_timeout_enable
626 
627 Routine Description: Called to set flag for suspend prevention for some time
628 
629 Arguments:     OsContext - handle to OS context
630 
631 Return Value:  packet counter
632 -----------------------------------------------------------------------------*/
os_wake_lock_timeout_enable(TI_HANDLE OsContext)633 int os_wake_lock_timeout_enable (TI_HANDLE OsContext)
634 {
635 	TWlanDrvIfObj *drv = (TWlanDrvIfObj *)OsContext;
636 	unsigned long flags;
637 	int ret = 0;
638 
639 	if (drv) {
640 		spin_lock_irqsave(&drv->lock, flags);
641 		ret = drv->wl_packet = 1;
642 		spin_unlock_irqrestore(&drv->lock, flags);
643 	}
644 	return ret;
645 }
646 
647 /*-----------------------------------------------------------------------------
648 Routine Name:  os_wake_lock
649 
650 Routine Description: Called to prevent system from suspend
651 
652 Arguments:     OsContext - handle to OS context
653 
654 Return Value:  wake_lock counter
655 -----------------------------------------------------------------------------*/
os_wake_lock(TI_HANDLE OsContext)656 int os_wake_lock (TI_HANDLE OsContext)
657 {
658 	TWlanDrvIfObj *drv = (TWlanDrvIfObj *)OsContext;
659 	int ret = 0;
660 	unsigned long flags;
661 
662 	if (drv) {
663 		spin_lock_irqsave(&drv->lock, flags);
664 #ifdef CONFIG_HAS_WAKELOCK
665 		if (!drv->wl_count)
666 			wake_lock(&drv->wl_wifi);
667 #endif
668 		drv->wl_count++;
669 		ret = drv->wl_count;
670 		spin_unlock_irqrestore(&drv->lock, flags);
671 	}
672 	/* printk("%s: %d\n", __func__, ret); */
673 	return ret;
674 }
675 
676 /*-----------------------------------------------------------------------------
677 Routine Name:  os_wake_unlock
678 
679 Routine Description: Called to allow system to suspend
680 
681 Arguments:     OsContext - handle to OS context
682 
683 Return Value:  wake_lock counter
684 -----------------------------------------------------------------------------*/
os_wake_unlock(TI_HANDLE OsContext)685 int os_wake_unlock (TI_HANDLE OsContext)
686 {
687 	TWlanDrvIfObj *drv = (TWlanDrvIfObj *)OsContext;
688 	int ret = 0;
689 	unsigned long flags;
690 
691 	if (drv) {
692 		spin_lock_irqsave(&drv->lock, flags);
693 		if (drv->wl_count) {
694 			drv->wl_count--;
695 #ifdef CONFIG_HAS_WAKELOCK
696 			if (!drv->wl_count)
697 				wake_unlock(&drv->wl_wifi);
698 #endif
699 			ret = drv->wl_count;
700 		}
701 		spin_unlock_irqrestore(&drv->lock, flags);
702 	}
703 	/* printk("%s: %d\n", __func__, ret); */
704 	return ret;
705 }
706 
707 /*-----------------------------------------------------------------------------
708 Routine Name:  os_RequestSchedule
709 
710 Routine Description:
711 
712 Arguments:
713 
714 Return Value:  TI_OK
715 -----------------------------------------------------------------------------*/
os_RequestSchedule(TI_HANDLE OsContext)716 int os_RequestSchedule (TI_HANDLE OsContext)
717 {
718 	TWlanDrvIfObj *drv = (TWlanDrvIfObj *)OsContext;
719 
720 	/* Note: The performance trace below doesn't inclose the schedule
721 	 *   itself because the rescheduling can occur immediately and call
722 	 *   os_RequestSchedule again which will confuse the trace tools */
723 	CL_TRACE_START_L3();
724 	CL_TRACE_END_L3("tiwlan_drv.ko", "OS", "TASK", "");
725 
726 	if( !queue_work(drv->tiwlan_wq, &drv->tWork) ) {
727 		/* printk("%s: Fail\n",__func__); */
728 		return TI_NOK;
729 	}
730 
731 	return TI_OK;
732 }
733 
734 
735 /*-----------------------------------------------------------------------------
736 Routine Name: os_SignalObjectCreate
737 
738 Routine Description:
739 
740 Arguments:
741 
742 Return Value: TI_OK
743 -----------------------------------------------------------------------------*/
os_SignalObjectCreate(TI_HANDLE OsContext)744 void *os_SignalObjectCreate (TI_HANDLE OsContext)
745 {
746 	struct completion *myPtr;
747 	myPtr = os_memoryAlloc(OsContext, sizeof(struct completion));
748 	if (myPtr)
749 		init_completion (myPtr);
750 	return (myPtr);
751 }
752 
753 
754 /*-----------------------------------------------------------------------------
755 Routine Name: os_SignalObjectWait
756 
757 Routine Description:
758 
759 Arguments:
760 
761 Return Value: TI_OK
762 -----------------------------------------------------------------------------*/
os_SignalObjectWait(TI_HANDLE OsContext,void * signalObject)763 int os_SignalObjectWait (TI_HANDLE OsContext, void *signalObject)
764 {
765 	if (!signalObject)
766 		return TI_NOK;
767 	if (!wait_for_completion_timeout((struct completion *)signalObject,
768 					msecs_to_jiffies(10000))) {
769 		printk("tiwlan: 10 sec %s timeout\n", __func__);
770 	}
771 	return TI_OK;
772 }
773 
774 
775 /*-----------------------------------------------------------------------------
776 Routine Name: os_SignalObjectSet
777 
778 Routine Description:
779 
780 Arguments:
781 
782 Return Value: TI_OK
783 -----------------------------------------------------------------------------*/
os_SignalObjectSet(TI_HANDLE OsContext,void * signalObject)784 int os_SignalObjectSet (TI_HANDLE OsContext, void *signalObject)
785 {
786 	if (!signalObject)
787 		return TI_NOK;
788 	complete ((struct completion *)signalObject);
789 	return TI_OK;
790 }
791 
792 
793 /*-----------------------------------------------------------------------------
794 Routine Name: os_SignalObjectFree
795 
796 Routine Description:
797 
798 Arguments:
799 
800 Return Value: TI_OK
801 -----------------------------------------------------------------------------*/
os_SignalObjectFree(TI_HANDLE OsContext,void * signalObject)802 int os_SignalObjectFree (TI_HANDLE OsContext, void *signalObject)
803 {
804 	if (!signalObject)
805 		return TI_NOK;
806 	os_memoryFree(OsContext, signalObject, sizeof(struct completion));
807 	return TI_OK;
808 }
809 
810 
811 /**
812  * \fn     os_Trace
813  * \brief  Prepare and send trace message to the logger.
814  *
815  * \param  OsContext    - The OS handle
816  * \param  uLevel   	- Severity level of the trace message
817  * \param  uFileId  	- Source file ID of the trace message
818  * \param  uLineNum 	- Line number of the trace message
819  * \param  uParamsNum   - Number of parameters in the trace message
820  * \param  ...          - The trace message parameters
821  *
822  * \return void
823  */
os_Trace(TI_HANDLE OsContext,TI_UINT32 uLevel,TI_UINT32 uFileId,TI_UINT32 uLineNum,TI_UINT32 uParamsNum,...)824 void os_Trace (TI_HANDLE OsContext, TI_UINT32 uLevel, TI_UINT32 uFileId, TI_UINT32 uLineNum, TI_UINT32 uParamsNum, ...)
825 {
826 	TI_UINT32	index;
827 	TI_UINT32	uParam;
828 	TI_UINT32	uMaxParamValue = 0;
829 	TI_UINT32	uMsgLen	= TRACE_MSG_MIN_LENGTH;
830 	TI_UINT8    aMsg[TRACE_MSG_MAX_LENGTH] = {0};
831 	TTraceMsg   *pMsgHdr  = (TTraceMsg *)&aMsg[0];
832 	TI_UINT8    *pMsgData = &aMsg[0] + sizeof(TTraceMsg);
833 	va_list	    list;
834 
835 	if (!bRedirectOutputToLogger)
836 	{
837 		return;
838 	}
839 
840 	if (uParamsNum > TRACE_MSG_MAX_PARAMS)
841 	{
842 		uParamsNum = TRACE_MSG_MAX_PARAMS;
843 	}
844 
845 	/* sync on the parameters */
846 	va_start(list, uParamsNum);
847 
848 	/* find the longest parameter */
849 	for (index = 0; index < uParamsNum; index++)
850 	{
851 		/* get parameter from the stack */
852 		uParam = va_arg (list, TI_UINT32);
853 
854 		/* save the longest parameter at variable 'uMaxParamValue' */
855 		if (uParam > uMaxParamValue)
856         {
857 			uMaxParamValue = uParam;
858         }
859 
860 		/* 32 bit parameter is the longest possible - get out of the loop */
861 		if (uMaxParamValue > UINT16_MAX_VAL)
862         {
863 			break;
864         }
865 	}
866 
867 	/* Set msg length and format according to the biggest parameter value (8/16/32 bits) */
868 	if (uMaxParamValue > UINT16_MAX_VAL)
869 	{
870 		pMsgHdr->uFormat = TRACE_FORMAT_32_BITS_PARAMS;
871 		uMsgLen += uParamsNum * sizeof(TI_UINT32);
872 	}
873 	else if (uMaxParamValue > UINT8_MAX_VAL)
874 	{
875 		pMsgHdr->uFormat = TRACE_FORMAT_16_BITS_PARAMS;
876 		uMsgLen += uParamsNum * sizeof(TI_UINT16);
877 	}
878 	else
879 	{
880 		pMsgHdr->uFormat = TRACE_FORMAT_8_BITS_PARAMS;
881 		uMsgLen += uParamsNum;
882 	}
883 
884 	/* Fill all other header information */
885 	pMsgHdr->uLevel     = (TI_UINT8)uLevel;
886 	pMsgHdr->uParamsNum = (TI_UINT8)uParamsNum;
887 	pMsgHdr->uFileId    = (TI_UINT16)uFileId;
888 	pMsgHdr->uLineNum   = (TI_UINT16)uLineNum;
889 
890 	/* re-sync on the parameters */
891 	va_start(list, uParamsNum);
892 
893 	/* add the parameters */
894 	for (index = 0; index < uParamsNum; index++)
895 	{
896 		/* get parameter from the stack */
897 		uParam = va_arg(list, TI_UINT32);
898 
899 		/* insert the parameter and increment msg pointer */
900 		switch(pMsgHdr->uFormat)
901 		{
902 		case TRACE_FORMAT_8_BITS_PARAMS:
903 			INSERT_BYTE(pMsgData, uParam);
904 			break;
905 
906 		case TRACE_FORMAT_16_BITS_PARAMS:
907 			INSERT_2_BYTES(pMsgData, uParam);
908 			break;
909 
910 		case TRACE_FORMAT_32_BITS_PARAMS:
911 			INSERT_4_BYTES(pMsgData, uParam);
912 			break;
913 
914         default:
915             va_end(list);
916             return;
917 		}
918 	}
919 
920 	va_end(list);
921 
922 	/* Send the trace message to the logger */
923 	SendLoggerData(OsContext, aMsg, (TI_UINT16)uMsgLen);
924 }
925 
926 /*--------------------------------------------------------------------------------------*/
927 
928 /**
929  * \fn     os_SetDrvThreadPriority
930  * \brief  Called upon init to set WLAN driver thread priority.
931  *         Currently not supported in Linux.
932  *
933  * \param  OsContext              - The OS handle
934  * \param  uWlanDrvThreadPriority - The WLAN driver thread priority
935  * \return
936  */
os_SetDrvThreadPriority(TI_HANDLE OsContext,TI_UINT32 uWlanDrvThreadPriority)937 void os_SetDrvThreadPriority (TI_HANDLE OsContext, TI_UINT32 uWlanDrvThreadPriority)
938 {
939 }
940