/*
 *************************************************************************
 * Ralink Tech Inc.
 * 5F., No.36, Taiyuan St., Jhubei City,
 * Hsinchu County 302,
 * Taiwan, R.O.C.
 *
 * (c) Copyright 2002-2007, Ralink Technology, Inc.
 *
 * This program is free software; you can redistribute it and/or modify  *
 * it under the terms of the GNU General Public License as published by  *
 * the Free Software Foundation; either version 2 of the License, or     *
 * (at your option) any later version.                                   *
 *                                                                       *
 * This program is distributed in the hope that it will be useful,       *
 * but WITHOUT ANY WARRANTY; without even the implied warranty of        *
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
 * GNU General Public License for more details.                          *
 *                                                                       *
 * You should have received a copy of the GNU General Public License     *
 * along with this program; if not, write to the                         *
 * Free Software Foundation, Inc.,                                       *
 * 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.             *
 *                                                                       *
 *************************************************************************
 */

#include <linux/firmware.h>
#include <linux/sched.h>
#include <linux/slab.h>
#include "rt_config.h"

unsigned long RTDebugLevel = RT_DEBUG_ERROR;

/* for wireless system event message */
char const *pWirelessSysEventText[IW_SYS_EVENT_TYPE_NUM] = {
	/* system status event */
	"had associated successfully",	/* IW_ASSOC_EVENT_FLAG */
	"had disassociated",	/* IW_DISASSOC_EVENT_FLAG */
	"had deauthenticated",	/* IW_DEAUTH_EVENT_FLAG */
	"had been aged-out and disassociated",	/* IW_AGEOUT_EVENT_FLAG */
	"occurred CounterMeasures attack",	/* IW_COUNTER_MEASURES_EVENT_FLAG */
	"occurred replay counter different in Key Handshaking",	/* IW_REPLAY_COUNTER_DIFF_EVENT_FLAG */
	"occurred RSNIE different in Key Handshaking",	/* IW_RSNIE_DIFF_EVENT_FLAG */
	"occurred MIC different in Key Handshaking",	/* IW_MIC_DIFF_EVENT_FLAG */
	"occurred ICV error in RX",	/* IW_ICV_ERROR_EVENT_FLAG */
	"occurred MIC error in RX",	/* IW_MIC_ERROR_EVENT_FLAG */
	"Group Key Handshaking timeout",	/* IW_GROUP_HS_TIMEOUT_EVENT_FLAG */
	"Pairwise Key Handshaking timeout",	/* IW_PAIRWISE_HS_TIMEOUT_EVENT_FLAG */
	"RSN IE sanity check failure",	/* IW_RSNIE_SANITY_FAIL_EVENT_FLAG */
	"set key done in WPA/WPAPSK",	/* IW_SET_KEY_DONE_WPA1_EVENT_FLAG */
	"set key done in WPA2/WPA2PSK",	/* IW_SET_KEY_DONE_WPA2_EVENT_FLAG */
	"connects with our wireless client",	/* IW_STA_LINKUP_EVENT_FLAG */
	"disconnects with our wireless client",	/* IW_STA_LINKDOWN_EVENT_FLAG */
	"scan completed"	/* IW_SCAN_COMPLETED_EVENT_FLAG */
	    "scan terminate! Busy! Enqueue fail!"	/* IW_SCAN_ENQUEUE_FAIL_EVENT_FLAG */
};

/* for wireless IDS_spoof_attack event message */
char const *pWirelessSpoofEventText[IW_SPOOF_EVENT_TYPE_NUM] = {
	"detected conflict SSID",	/* IW_CONFLICT_SSID_EVENT_FLAG */
	"detected spoofed association response",	/* IW_SPOOF_ASSOC_RESP_EVENT_FLAG */
	"detected spoofed reassociation responses",	/* IW_SPOOF_REASSOC_RESP_EVENT_FLAG */
	"detected spoofed probe response",	/* IW_SPOOF_PROBE_RESP_EVENT_FLAG */
	"detected spoofed beacon",	/* IW_SPOOF_BEACON_EVENT_FLAG */
	"detected spoofed disassociation",	/* IW_SPOOF_DISASSOC_EVENT_FLAG */
	"detected spoofed authentication",	/* IW_SPOOF_AUTH_EVENT_FLAG */
	"detected spoofed deauthentication",	/* IW_SPOOF_DEAUTH_EVENT_FLAG */
	"detected spoofed unknown management frame",	/* IW_SPOOF_UNKNOWN_MGMT_EVENT_FLAG */
	"detected replay attack"	/* IW_REPLAY_ATTACK_EVENT_FLAG */
};

/* for wireless IDS_flooding_attack event message */
char const *pWirelessFloodEventText[IW_FLOOD_EVENT_TYPE_NUM] = {
	"detected authentication flooding",	/* IW_FLOOD_AUTH_EVENT_FLAG */
	"detected association request flooding",	/* IW_FLOOD_ASSOC_REQ_EVENT_FLAG */
	"detected reassociation request flooding",	/* IW_FLOOD_REASSOC_REQ_EVENT_FLAG */
	"detected probe request flooding",	/* IW_FLOOD_PROBE_REQ_EVENT_FLAG */
	"detected disassociation flooding",	/* IW_FLOOD_DISASSOC_EVENT_FLAG */
	"detected deauthentication flooding",	/* IW_FLOOD_DEAUTH_EVENT_FLAG */
	"detected 802.1x eap-request flooding"	/* IW_FLOOD_EAP_REQ_EVENT_FLAG */
};

/* timeout -- ms */
void RTMP_SetPeriodicTimer(struct timer_list *pTimer,
			   IN unsigned long timeout)
{
	timeout = ((timeout * OS_HZ) / 1000);
	pTimer->expires = jiffies + timeout;
	add_timer(pTimer);
}

/* convert NdisMInitializeTimer --> RTMP_OS_Init_Timer */
void RTMP_OS_Init_Timer(struct rt_rtmp_adapter *pAd,
			struct timer_list *pTimer,
			IN TIMER_FUNCTION function, void *data)
{
	init_timer(pTimer);
	pTimer->data = (unsigned long)data;
	pTimer->function = function;
}

void RTMP_OS_Add_Timer(struct timer_list *pTimer,
		       IN unsigned long timeout)
{
	if (timer_pending(pTimer))
		return;

	timeout = ((timeout * OS_HZ) / 1000);
	pTimer->expires = jiffies + timeout;
	add_timer(pTimer);
}

void RTMP_OS_Mod_Timer(struct timer_list *pTimer,
		       IN unsigned long timeout)
{
	timeout = ((timeout * OS_HZ) / 1000);
	mod_timer(pTimer, jiffies + timeout);
}

void RTMP_OS_Del_Timer(struct timer_list *pTimer,
		       OUT BOOLEAN * pCancelled)
{
	if (timer_pending(pTimer)) {
		*pCancelled = del_timer_sync(pTimer);
	} else {
		*pCancelled = TRUE;
	}

}

void RTMP_OS_Release_Packet(struct rt_rtmp_adapter *pAd, struct rt_queue_entry *pEntry)
{
	/*RTMPFreeNdisPacket(pAd, (struct sk_buff *)pEntry); */
}

/* Unify all delay routine by using udelay */
void RTMPusecDelay(unsigned long usec)
{
	unsigned long i;

	for (i = 0; i < (usec / 50); i++)
		udelay(50);

	if (usec % 50)
		udelay(usec % 50);
}

void RTMP_GetCurrentSystemTime(LARGE_INTEGER *time)
{
	time->u.LowPart = jiffies;
}

/* pAd MUST allow to be NULL */
int os_alloc_mem(struct rt_rtmp_adapter *pAd, u8 ** mem, unsigned long size)
{
	*mem = kmalloc(size, GFP_ATOMIC);
	if (*mem)
		return NDIS_STATUS_SUCCESS;
	else
		return NDIS_STATUS_FAILURE;
}

/* pAd MUST allow to be NULL */
int os_free_mem(struct rt_rtmp_adapter *pAd, void *mem)
{

	ASSERT(mem);
	kfree(mem);
	return NDIS_STATUS_SUCCESS;
}

void *RtmpOSNetPktAlloc(struct rt_rtmp_adapter *pAd, IN int size)
{
	struct sk_buff *skb;
	/* Add 2 more bytes for ip header alignment */
	skb = dev_alloc_skb(size + 2);

	return (void *)skb;
}

void *RTMP_AllocateFragPacketBuffer(struct rt_rtmp_adapter *pAd,
					   unsigned long Length)
{
	struct sk_buff *pkt;

	pkt = dev_alloc_skb(Length);

	if (pkt == NULL) {
		DBGPRINT(RT_DEBUG_ERROR,
			 ("can't allocate frag rx %ld size packet\n", Length));
	}

	if (pkt) {
		RTMP_SET_PACKET_SOURCE(OSPKT_TO_RTPKT(pkt), PKTSRC_NDIS);
	}

	return (void *)pkt;
}

void *RTMP_AllocateTxPacketBuffer(struct rt_rtmp_adapter *pAd,
					 unsigned long Length,
					 IN BOOLEAN Cached,
					 void **VirtualAddress)
{
	struct sk_buff *pkt;

	pkt = dev_alloc_skb(Length);

	if (pkt == NULL) {
		DBGPRINT(RT_DEBUG_ERROR,
			 ("can't allocate tx %ld size packet\n", Length));
	}

	if (pkt) {
		RTMP_SET_PACKET_SOURCE(OSPKT_TO_RTPKT(pkt), PKTSRC_NDIS);
		*VirtualAddress = (void *)pkt->data;
	} else {
		*VirtualAddress = (void *)NULL;
	}

	return (void *)pkt;
}

void build_tx_packet(struct rt_rtmp_adapter *pAd,
		     void *pPacket,
		     u8 *pFrame, unsigned long FrameLen)
{

	struct sk_buff *pTxPkt;

	ASSERT(pPacket);
	pTxPkt = RTPKT_TO_OSPKT(pPacket);

	NdisMoveMemory(skb_put(pTxPkt, FrameLen), pFrame, FrameLen);
}

void RTMPFreeAdapter(struct rt_rtmp_adapter *pAd)
{
	struct os_cookie *os_cookie;
	int index;

	os_cookie = (struct os_cookie *)pAd->OS_Cookie;

	if (pAd->BeaconBuf)
		kfree(pAd->BeaconBuf);

	NdisFreeSpinLock(&pAd->MgmtRingLock);

#ifdef RTMP_MAC_PCI
	NdisFreeSpinLock(&pAd->RxRingLock);
#ifdef RT3090
	NdisFreeSpinLock(&pAd->McuCmdLock);
#endif /* RT3090 // */
#endif /* RTMP_MAC_PCI // */

	for (index = 0; index < NUM_OF_TX_RING; index++) {
		NdisFreeSpinLock(&pAd->TxSwQueueLock[index]);
		NdisFreeSpinLock(&pAd->DeQueueLock[index]);
		pAd->DeQueueRunning[index] = FALSE;
	}

	NdisFreeSpinLock(&pAd->irq_lock);

	release_firmware(pAd->firmware);

	vfree(pAd);		/* pci_free_consistent(os_cookie->pci_dev,sizeof(struct rt_rtmp_adapter),pAd,os_cookie->pAd_pa); */
	if (os_cookie)
		kfree(os_cookie);
}

BOOLEAN OS_Need_Clone_Packet(void)
{
	return FALSE;
}

/*
	========================================================================

	Routine Description:
		clone an input NDIS PACKET to another one. The new internally created NDIS PACKET
		must have only one NDIS BUFFER
		return - byte copied. 0 means can't create NDIS PACKET
		NOTE: internally created char should be destroyed by RTMPFreeNdisPacket

	Arguments:
		pAd 	Pointer to our adapter
		pInsAMSDUHdr	EWC A-MSDU format has extra 14-bytes header. if TRUE, insert this 14-byte hdr in front of MSDU.
		*pSrcTotalLen			return total packet length. This lenght is calculated with 802.3 format packet.

	Return Value:
		NDIS_STATUS_SUCCESS
		NDIS_STATUS_FAILURE

	Note:

	========================================================================
*/
int RTMPCloneNdisPacket(struct rt_rtmp_adapter *pAd,
				IN BOOLEAN pInsAMSDUHdr,
				void *pInPacket,
				void **ppOutPacket)
{

	struct sk_buff *pkt;

	ASSERT(pInPacket);
	ASSERT(ppOutPacket);

	/* 1. Allocate a packet */
	pkt = dev_alloc_skb(2048);

	if (pkt == NULL) {
		return NDIS_STATUS_FAILURE;
	}

	skb_put(pkt, GET_OS_PKT_LEN(pInPacket));
	NdisMoveMemory(pkt->data, GET_OS_PKT_DATAPTR(pInPacket),
		       GET_OS_PKT_LEN(pInPacket));
	*ppOutPacket = OSPKT_TO_RTPKT(pkt);

	RTMP_SET_PACKET_SOURCE(OSPKT_TO_RTPKT(pkt), PKTSRC_NDIS);

	printk("###Clone###\n");

	return NDIS_STATUS_SUCCESS;
}

/* the allocated NDIS PACKET must be freed via RTMPFreeNdisPacket() */
int RTMPAllocateNdisPacket(struct rt_rtmp_adapter *pAd,
				   void **ppPacket,
				   u8 *pHeader,
				   u32 HeaderLen,
				   u8 *pData, u32 DataLen)
{
	void *pPacket;
	ASSERT(pData);
	ASSERT(DataLen);

	/* 1. Allocate a packet */
	pPacket =
	    (void **) dev_alloc_skb(HeaderLen + DataLen +
					   RTMP_PKT_TAIL_PADDING);
	if (pPacket == NULL) {
		*ppPacket = NULL;
#ifdef DEBUG
		printk("RTMPAllocateNdisPacket Fail\n");
#endif
		return NDIS_STATUS_FAILURE;
	}
	/* 2. clone the frame content */
	if (HeaderLen > 0)
		NdisMoveMemory(GET_OS_PKT_DATAPTR(pPacket), pHeader, HeaderLen);
	if (DataLen > 0)
		NdisMoveMemory(GET_OS_PKT_DATAPTR(pPacket) + HeaderLen, pData,
			       DataLen);

	/* 3. update length of packet */
	skb_put(GET_OS_PKT_TYPE(pPacket), HeaderLen + DataLen);

	RTMP_SET_PACKET_SOURCE(pPacket, PKTSRC_NDIS);
/*      printk("%s : pPacket = %p, len = %d\n", __func__, pPacket, GET_OS_PKT_LEN(pPacket)); */
	*ppPacket = pPacket;
	return NDIS_STATUS_SUCCESS;
}

/*
  ========================================================================
  Description:
	This routine frees a miniport internally allocated char and its
	corresponding NDIS_BUFFER and allocated memory.
  ========================================================================
*/
void RTMPFreeNdisPacket(struct rt_rtmp_adapter *pAd, void *pPacket)
{
	dev_kfree_skb_any(RTPKT_TO_OSPKT(pPacket));
}

/* IRQL = DISPATCH_LEVEL */
/* NOTE: we do have an assumption here, that Byte0 and Byte1 always reasid at the same */
/*                       scatter gather buffer */
int Sniff2BytesFromNdisBuffer(char *pFirstBuffer,
				      u8 DesiredOffset,
				      u8 *pByte0, u8 *pByte1)
{
	*pByte0 = *(u8 *)(pFirstBuffer + DesiredOffset);
	*pByte1 = *(u8 *)(pFirstBuffer + DesiredOffset + 1);

	return NDIS_STATUS_SUCCESS;
}

void RTMP_QueryPacketInfo(void *pPacket,
			  struct rt_packet_info *pPacketInfo,
			  u8 **pSrcBufVA, u32 * pSrcBufLen)
{
	pPacketInfo->BufferCount = 1;
	pPacketInfo->pFirstBuffer = (char *)GET_OS_PKT_DATAPTR(pPacket);
	pPacketInfo->PhysicalBufferCount = 1;
	pPacketInfo->TotalPacketLength = GET_OS_PKT_LEN(pPacket);

	*pSrcBufVA = GET_OS_PKT_DATAPTR(pPacket);
	*pSrcBufLen = GET_OS_PKT_LEN(pPacket);
}

void RTMP_QueryNextPacketInfo(void **ppPacket,
			      struct rt_packet_info *pPacketInfo,
			      u8 **pSrcBufVA, u32 * pSrcBufLen)
{
	void *pPacket = NULL;

	if (*ppPacket)
		pPacket = GET_OS_PKT_NEXT(*ppPacket);

	if (pPacket) {
		pPacketInfo->BufferCount = 1;
		pPacketInfo->pFirstBuffer =
		    (char *)GET_OS_PKT_DATAPTR(pPacket);
		pPacketInfo->PhysicalBufferCount = 1;
		pPacketInfo->TotalPacketLength = GET_OS_PKT_LEN(pPacket);

		*pSrcBufVA = GET_OS_PKT_DATAPTR(pPacket);
		*pSrcBufLen = GET_OS_PKT_LEN(pPacket);
		*ppPacket = GET_OS_PKT_NEXT(pPacket);
	} else {
		pPacketInfo->BufferCount = 0;
		pPacketInfo->pFirstBuffer = NULL;
		pPacketInfo->PhysicalBufferCount = 0;
		pPacketInfo->TotalPacketLength = 0;

		*pSrcBufVA = NULL;
		*pSrcBufLen = 0;
		*ppPacket = NULL;
	}
}

void *DuplicatePacket(struct rt_rtmp_adapter *pAd,
			     void *pPacket, u8 FromWhichBSSID)
{
	struct sk_buff *skb;
	void *pRetPacket = NULL;
	u16 DataSize;
	u8 *pData;

	DataSize = (u16)GET_OS_PKT_LEN(pPacket);
	pData = (u8 *)GET_OS_PKT_DATAPTR(pPacket);

	skb = skb_clone(RTPKT_TO_OSPKT(pPacket), MEM_ALLOC_FLAG);
	if (skb) {
		skb->dev = get_netdev_from_bssid(pAd, FromWhichBSSID);
		pRetPacket = OSPKT_TO_RTPKT(skb);
	}

	return pRetPacket;

}

void *duplicate_pkt(struct rt_rtmp_adapter *pAd,
			   u8 *pHeader802_3,
			   u32 HdrLen,
			   u8 *pData,
			   unsigned long DataSize, u8 FromWhichBSSID)
{
	struct sk_buff *skb;
	void *pPacket = NULL;

	skb = __dev_alloc_skb(HdrLen + DataSize + 2, MEM_ALLOC_FLAG);
	if (skb != NULL) {
		skb_reserve(skb, 2);
		NdisMoveMemory(skb_tail_pointer(skb), pHeader802_3, HdrLen);
		skb_put(skb, HdrLen);
		NdisMoveMemory(skb_tail_pointer(skb), pData, DataSize);
		skb_put(skb, DataSize);
		skb->dev = get_netdev_from_bssid(pAd, FromWhichBSSID);
		pPacket = OSPKT_TO_RTPKT(skb);
	}

	return pPacket;
}

#define TKIP_TX_MIC_SIZE		8
void *duplicate_pkt_with_TKIP_MIC(struct rt_rtmp_adapter *pAd,
					 void *pPacket)
{
	struct sk_buff *skb, *newskb;

	skb = RTPKT_TO_OSPKT(pPacket);
	if (skb_tailroom(skb) < TKIP_TX_MIC_SIZE) {
		/* alloc a new skb and copy the packet */
		newskb =
		    skb_copy_expand(skb, skb_headroom(skb), TKIP_TX_MIC_SIZE,
				    GFP_ATOMIC);
		dev_kfree_skb_any(skb);
		if (newskb == NULL) {
			DBGPRINT(RT_DEBUG_ERROR,
				 ("Extend Tx.MIC for packet failed!, dropping packet!\n"));
			return NULL;
		}
		skb = newskb;
	}

	return OSPKT_TO_RTPKT(skb);
}

void *ClonePacket(struct rt_rtmp_adapter *pAd,
			 void *pPacket,
			 u8 *pData, unsigned long DataSize)
{
	struct sk_buff *pRxPkt;
	struct sk_buff *pClonedPkt;

	ASSERT(pPacket);
	pRxPkt = RTPKT_TO_OSPKT(pPacket);

	/* clone the packet */
	pClonedPkt = skb_clone(pRxPkt, MEM_ALLOC_FLAG);

	if (pClonedPkt) {
		/* set the correct dataptr and data len */
		pClonedPkt->dev = pRxPkt->dev;
		pClonedPkt->data = pData;
		pClonedPkt->len = DataSize;
		skb_set_tail_pointer(pClonedPkt, DataSize)
		ASSERT(DataSize < 1530);
	}
	return pClonedPkt;
}

/* */
/* change OS packet DataPtr and DataLen */
/* */
void update_os_packet_info(struct rt_rtmp_adapter *pAd,
			   struct rt_rx_blk *pRxBlk, u8 FromWhichBSSID)
{
	struct sk_buff *pOSPkt;

	ASSERT(pRxBlk->pRxPacket);
	pOSPkt = RTPKT_TO_OSPKT(pRxBlk->pRxPacket);

	pOSPkt->dev = get_netdev_from_bssid(pAd, FromWhichBSSID);
	pOSPkt->data = pRxBlk->pData;
	pOSPkt->len = pRxBlk->DataSize;
	skb_set_tail_pointer(pOSPkt, pOSPkt->len);
}

void wlan_802_11_to_802_3_packet(struct rt_rtmp_adapter *pAd,
				 struct rt_rx_blk *pRxBlk,
				 u8 *pHeader802_3,
				 u8 FromWhichBSSID)
{
	struct sk_buff *pOSPkt;

	ASSERT(pRxBlk->pRxPacket);
	ASSERT(pHeader802_3);

	pOSPkt = RTPKT_TO_OSPKT(pRxBlk->pRxPacket);

	pOSPkt->dev = get_netdev_from_bssid(pAd, FromWhichBSSID);
	pOSPkt->data = pRxBlk->pData;
	pOSPkt->len = pRxBlk->DataSize;
	skb_set_tail_pointer(pOSPkt, pOSPkt->len);

	/* */
	/* copy 802.3 header */
	/* */
	/* */

	NdisMoveMemory(skb_push(pOSPkt, LENGTH_802_3), pHeader802_3,
		       LENGTH_802_3);
}

void announce_802_3_packet(struct rt_rtmp_adapter *pAd, void *pPacket)
{

	struct sk_buff *pRxPkt;

	ASSERT(pPacket);

	pRxPkt = RTPKT_TO_OSPKT(pPacket);

	/* Push up the protocol stack */
	pRxPkt->protocol = eth_type_trans(pRxPkt, pRxPkt->dev);

	netif_rx(pRxPkt);
}

struct rt_rtmp_sg_list *
rt_get_sg_list_from_packet(void *pPacket, struct rt_rtmp_sg_list *sg)
{
	sg->NumberOfElements = 1;
	sg->Elements[0].Address = GET_OS_PKT_DATAPTR(pPacket);
	sg->Elements[0].Length = GET_OS_PKT_LEN(pPacket);
	return sg;
}

void hex_dump(char *str, unsigned char *pSrcBufVA, unsigned int SrcBufLen)
{
	unsigned char *pt;
	int x;

	if (RTDebugLevel < RT_DEBUG_TRACE)
		return;

	pt = pSrcBufVA;
	printk("%s: %p, len = %d\n", str, pSrcBufVA, SrcBufLen);
	for (x = 0; x < SrcBufLen; x++) {
		if (x % 16 == 0)
			printk("0x%04x : ", x);
		printk("%02x ", ((unsigned char)pt[x]));
		if (x % 16 == 15)
			printk("\n");
	}
	printk("\n");
}

/*
	========================================================================

	Routine Description:
		Send log message through wireless event

		Support standard iw_event with IWEVCUSTOM. It is used below.

		iwreq_data.data.flags is used to store event_flag that is defined by user.
		iwreq_data.data.length is the length of the event log.

		The format of the event log is composed of the entry's MAC address and
		the desired log message (refer to pWirelessEventText).

			ex: 11:22:33:44:55:66 has associated successfully

		p.s. The requirement of Wireless Extension is v15 or newer.

	========================================================================
*/
void RTMPSendWirelessEvent(struct rt_rtmp_adapter *pAd,
			   u16 Event_flag,
			   u8 *pAddr, u8 BssIdx, char Rssi)
{

	/*union         iwreq_data      wrqu; */
	char *pBuf = NULL, *pBufPtr = NULL;
	u16 event, type, BufLen;
	u8 event_table_len = 0;

	type = Event_flag & 0xFF00;
	event = Event_flag & 0x00FF;

	switch (type) {
	case IW_SYS_EVENT_FLAG_START:
		event_table_len = IW_SYS_EVENT_TYPE_NUM;
		break;

	case IW_SPOOF_EVENT_FLAG_START:
		event_table_len = IW_SPOOF_EVENT_TYPE_NUM;
		break;

	case IW_FLOOD_EVENT_FLAG_START:
		event_table_len = IW_FLOOD_EVENT_TYPE_NUM;
		break;
	}

	if (event_table_len == 0) {
		DBGPRINT(RT_DEBUG_ERROR,
			 ("%s : The type(%0x02x) is not valid.\n", __func__,
			  type));
		return;
	}

	if (event >= event_table_len) {
		DBGPRINT(RT_DEBUG_ERROR,
			 ("%s : The event(%0x02x) is not valid.\n", __func__,
			  event));
		return;
	}
	/*Allocate memory and copy the msg. */
	pBuf = kmalloc(IW_CUSTOM_MAX_LEN, GFP_ATOMIC);
	if (pBuf != NULL) {
		/*Prepare the payload */
		memset(pBuf, 0, IW_CUSTOM_MAX_LEN);

		pBufPtr = pBuf;

		if (pAddr)
			pBufPtr +=
			    sprintf(pBufPtr,
				    "(RT2860) STA(%02x:%02x:%02x:%02x:%02x:%02x) ",
				    PRINT_MAC(pAddr));
		else if (BssIdx < MAX_MBSSID_NUM)
			pBufPtr +=
			    sprintf(pBufPtr, "(RT2860) BSS(wlan%d) ", BssIdx);
		else
			pBufPtr += sprintf(pBufPtr, "(RT2860) ");

		if (type == IW_SYS_EVENT_FLAG_START)
			pBufPtr +=
			    sprintf(pBufPtr, "%s",
				    pWirelessSysEventText[event]);
		else if (type == IW_SPOOF_EVENT_FLAG_START)
			pBufPtr +=
			    sprintf(pBufPtr, "%s (RSSI=%d)",
				    pWirelessSpoofEventText[event], Rssi);
		else if (type == IW_FLOOD_EVENT_FLAG_START)
			pBufPtr +=
			    sprintf(pBufPtr, "%s",
				    pWirelessFloodEventText[event]);
		else
			pBufPtr += sprintf(pBufPtr, "%s", "unknown event");

		pBufPtr[pBufPtr - pBuf] = '\0';
		BufLen = pBufPtr - pBuf;

		RtmpOSWrielessEventSend(pAd, IWEVCUSTOM, Event_flag, NULL,
					(u8 *)pBuf, BufLen);
		/*DBGPRINT(RT_DEBUG_TRACE, ("%s : %s\n", __func__, pBuf)); */

		kfree(pBuf);
	} else
		DBGPRINT(RT_DEBUG_ERROR,
			 ("%s : Can't allocate memory for wireless event.\n",
			  __func__));
}

void send_monitor_packets(struct rt_rtmp_adapter *pAd, struct rt_rx_blk *pRxBlk)
{
	struct sk_buff *pOSPkt;
	struct rt_wlan_ng_prism2_header *ph;
	int rate_index = 0;
	u16 header_len = 0;
	u8 temp_header[40] = { 0 };

	u_int32_t ralinkrate[256] = { 2, 4, 11, 22, 12, 18, 24, 36, 48, 72, 96, 108, 109, 110, 111, 112, 13, 26, 39, 52, 78, 104, 117, 130, 26, 52, 78, 104, 156, 208, 234, 260, 27, 54, 81, 108, 162, 216, 243, 270,	/* Last 38 */
		54, 108, 162, 216, 324, 432, 486, 540, 14, 29, 43, 57, 87, 115,
		    130, 144, 29, 59, 87, 115, 173, 230, 260, 288, 30, 60, 90,
		    120, 180, 240, 270, 300, 60, 120, 180, 240, 360, 480, 540,
		    600, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
		11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26,
		    27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41,
		    42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56,
		    57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71,
		    72, 73, 74, 75, 76, 77, 78, 79, 80
	};

	ASSERT(pRxBlk->pRxPacket);
	if (pRxBlk->DataSize < 10) {
		DBGPRINT(RT_DEBUG_ERROR,
			 ("%s : Size is too small! (%d)\n", __func__,
			  pRxBlk->DataSize));
		goto err_free_sk_buff;
	}

	if (pRxBlk->DataSize + sizeof(struct rt_wlan_ng_prism2_header) >
	    RX_BUFFER_AGGRESIZE) {
		DBGPRINT(RT_DEBUG_ERROR,
			 ("%s : Size is too large! (%zu)\n", __func__,
			  pRxBlk->DataSize + sizeof(struct rt_wlan_ng_prism2_header)));
		goto err_free_sk_buff;
	}

	pOSPkt = RTPKT_TO_OSPKT(pRxBlk->pRxPacket);
	pOSPkt->dev = get_netdev_from_bssid(pAd, BSS0);
	if (pRxBlk->pHeader->FC.Type == BTYPE_DATA) {
		pRxBlk->DataSize -= LENGTH_802_11;
		if ((pRxBlk->pHeader->FC.ToDs == 1) &&
		    (pRxBlk->pHeader->FC.FrDs == 1))
			header_len = LENGTH_802_11_WITH_ADDR4;
		else
			header_len = LENGTH_802_11;

		/* QOS */
		if (pRxBlk->pHeader->FC.SubType & 0x08) {
			header_len += 2;
			/* Data skip QOS contorl field */
			pRxBlk->DataSize -= 2;
		}
		/* Order bit: A-Ralink or HTC+ */
		if (pRxBlk->pHeader->FC.Order) {
			header_len += 4;
			/* Data skip HTC contorl field */
			pRxBlk->DataSize -= 4;
		}
		/* Copy Header */
		if (header_len <= 40)
			NdisMoveMemory(temp_header, pRxBlk->pData, header_len);

		/* skip HW padding */
		if (pRxBlk->RxD.L2PAD)
			pRxBlk->pData += (header_len + 2);
		else
			pRxBlk->pData += header_len;
	}			/*end if */

	if (pRxBlk->DataSize < pOSPkt->len) {
		skb_trim(pOSPkt, pRxBlk->DataSize);
	} else {
		skb_put(pOSPkt, (pRxBlk->DataSize - pOSPkt->len));
	}			/*end if */

	if ((pRxBlk->pData - pOSPkt->data) > 0) {
		skb_put(pOSPkt, (pRxBlk->pData - pOSPkt->data));
		skb_pull(pOSPkt, (pRxBlk->pData - pOSPkt->data));
	}			/*end if */

	if (skb_headroom(pOSPkt) < (sizeof(struct rt_wlan_ng_prism2_header) + header_len)) {
		if (pskb_expand_head
		    (pOSPkt, (sizeof(struct rt_wlan_ng_prism2_header) + header_len), 0,
		     GFP_ATOMIC)) {
			DBGPRINT(RT_DEBUG_ERROR,
				 ("%s : Reallocate header size of sk_buff fail!\n",
				  __func__));
			goto err_free_sk_buff;
		}		/*end if */
	}			/*end if */

	if (header_len > 0)
		NdisMoveMemory(skb_push(pOSPkt, header_len), temp_header,
			       header_len);

	ph = (struct rt_wlan_ng_prism2_header *)skb_push(pOSPkt,
						sizeof(struct rt_wlan_ng_prism2_header));
	NdisZeroMemory(ph, sizeof(struct rt_wlan_ng_prism2_header));

	ph->msgcode = DIDmsg_lnxind_wlansniffrm;
	ph->msglen = sizeof(struct rt_wlan_ng_prism2_header);
	strcpy((char *)ph->devname, (char *)pAd->net_dev->name);

	ph->hosttime.did = DIDmsg_lnxind_wlansniffrm_hosttime;
	ph->hosttime.status = 0;
	ph->hosttime.len = 4;
	ph->hosttime.data = jiffies;

	ph->mactime.did = DIDmsg_lnxind_wlansniffrm_mactime;
	ph->mactime.status = 0;
	ph->mactime.len = 0;
	ph->mactime.data = 0;

	ph->istx.did = DIDmsg_lnxind_wlansniffrm_istx;
	ph->istx.status = 0;
	ph->istx.len = 0;
	ph->istx.data = 0;

	ph->channel.did = DIDmsg_lnxind_wlansniffrm_channel;
	ph->channel.status = 0;
	ph->channel.len = 4;

	ph->channel.data = (u_int32_t) pAd->CommonCfg.Channel;

	ph->rssi.did = DIDmsg_lnxind_wlansniffrm_rssi;
	ph->rssi.status = 0;
	ph->rssi.len = 4;
	ph->rssi.data =
	    (u_int32_t) RTMPMaxRssi(pAd,
				    ConvertToRssi(pAd, pRxBlk->pRxWI->RSSI0,
						  RSSI_0), ConvertToRssi(pAd,
									 pRxBlk->
									 pRxWI->
									 RSSI1,
									 RSSI_1),
				    ConvertToRssi(pAd, pRxBlk->pRxWI->RSSI2,
						  RSSI_2));;

	ph->signal.did = DIDmsg_lnxind_wlansniffrm_signal;
	ph->signal.status = 0;
	ph->signal.len = 4;
	ph->signal.data = 0;	/*rssi + noise; */

	ph->noise.did = DIDmsg_lnxind_wlansniffrm_noise;
	ph->noise.status = 0;
	ph->noise.len = 4;
	ph->noise.data = 0;

	if (pRxBlk->pRxWI->PHYMODE >= MODE_HTMIX) {
		rate_index =
		    16 + ((u8)pRxBlk->pRxWI->BW * 16) +
		    ((u8)pRxBlk->pRxWI->ShortGI * 32) +
		    ((u8)pRxBlk->pRxWI->MCS);
	} else if (pRxBlk->pRxWI->PHYMODE == MODE_OFDM)
		rate_index = (u8)(pRxBlk->pRxWI->MCS) + 4;
	else
		rate_index = (u8)(pRxBlk->pRxWI->MCS);
	if (rate_index < 0)
		rate_index = 0;
	if (rate_index > 255)
		rate_index = 255;

	ph->rate.did = DIDmsg_lnxind_wlansniffrm_rate;
	ph->rate.status = 0;
	ph->rate.len = 4;
	ph->rate.data = ralinkrate[rate_index];

	ph->frmlen.did = DIDmsg_lnxind_wlansniffrm_frmlen;
	ph->frmlen.status = 0;
	ph->frmlen.len = 4;
	ph->frmlen.data = (u_int32_t) pRxBlk->DataSize;

	pOSPkt->pkt_type = PACKET_OTHERHOST;
	pOSPkt->protocol = eth_type_trans(pOSPkt, pOSPkt->dev);
	pOSPkt->ip_summed = CHECKSUM_NONE;
	netif_rx(pOSPkt);

	return;

err_free_sk_buff:
	RELEASE_NDIS_PACKET(pAd, pRxBlk->pRxPacket, NDIS_STATUS_FAILURE);
	return;

}

/*******************************************************************************

	Device IRQ related functions.

 *******************************************************************************/
int RtmpOSIRQRequest(struct net_device *pNetDev)
{
#ifdef RTMP_PCI_SUPPORT
	struct net_device *net_dev = pNetDev;
	struct rt_rtmp_adapter *pAd = NULL;
	int retval = 0;

	GET_PAD_FROM_NET_DEV(pAd, pNetDev);

	ASSERT(pAd);

	if (pAd->infType == RTMP_DEV_INF_PCI) {
		struct os_cookie *_pObj = (struct os_cookie *)(pAd->OS_Cookie);
		RTMP_MSI_ENABLE(pAd);
		retval =
		    request_irq(_pObj->pci_dev->irq, rt2860_interrupt, SA_SHIRQ,
				(net_dev)->name, (net_dev));
		if (retval != 0)
			printk("RT2860: request_irq  ERROR(%d)\n", retval);
	}

	return retval;
#else
	return 0;
#endif
}

int RtmpOSIRQRelease(struct net_device *pNetDev)
{
	struct net_device *net_dev = pNetDev;
	struct rt_rtmp_adapter *pAd = NULL;

	GET_PAD_FROM_NET_DEV(pAd, net_dev);

	ASSERT(pAd);

#ifdef RTMP_PCI_SUPPORT
	if (pAd->infType == RTMP_DEV_INF_PCI) {
		struct os_cookie *pObj = (struct os_cookie *)(pAd->OS_Cookie);
		synchronize_irq(pObj->pci_dev->irq);
		free_irq(pObj->pci_dev->irq, (net_dev));
		RTMP_MSI_DISABLE(pAd);
	}
#endif /* RTMP_PCI_SUPPORT // */

	return 0;
}

/*******************************************************************************

	File open/close related functions.

 *******************************************************************************/
struct file *RtmpOSFileOpen(char *pPath, int flag, int mode)
{
	struct file *filePtr;

	filePtr = filp_open(pPath, flag, 0);
	if (IS_ERR(filePtr)) {
		DBGPRINT(RT_DEBUG_ERROR,
			 ("%s(): Error %ld opening %s\n", __func__,
			  -PTR_ERR(filePtr), pPath));
	}

	return (struct file *)filePtr;
}

int RtmpOSFileClose(struct file *osfd)
{
	filp_close(osfd, NULL);
	return 0;
}

void RtmpOSFileSeek(struct file *osfd, int offset)
{
	osfd->f_pos = offset;
}

int RtmpOSFileRead(struct file *osfd, char *pDataPtr, int readLen)
{
	/* The object must have a read method */
	if (osfd->f_op && osfd->f_op->read) {
		return osfd->f_op->read(osfd, pDataPtr, readLen, &osfd->f_pos);
	} else {
		DBGPRINT(RT_DEBUG_ERROR, ("no file read method\n"));
		return -1;
	}
}

int RtmpOSFileWrite(struct file *osfd, char *pDataPtr, int writeLen)
{
	return osfd->f_op->write(osfd, pDataPtr, (size_t) writeLen,
				 &osfd->f_pos);
}

/*******************************************************************************

	Task create/management/kill related functions.

 *******************************************************************************/
int RtmpOSTaskKill(struct rt_rtmp_os_task *pTask)
{
	struct rt_rtmp_adapter *pAd;
	int ret = NDIS_STATUS_FAILURE;

	pAd = pTask->priv;

#ifdef KTHREAD_SUPPORT
	if (pTask->kthread_task) {
		kthread_stop(pTask->kthread_task);
		ret = NDIS_STATUS_SUCCESS;
	}
#else
	CHECK_PID_LEGALITY(pTask->taskPID) {
		printk("Terminate the task(%s) with pid(%d)!\n",
		       pTask->taskName, GET_PID_NUMBER(pTask->taskPID));
		mb();
		pTask->task_killed = 1;
		mb();
		ret = KILL_THREAD_PID(pTask->taskPID, SIGTERM, 1);
		if (ret) {
			printk(KERN_WARNING
			       "kill task(%s) with pid(%d) failed(retVal=%d)!\n",
			       pTask->taskName, GET_PID_NUMBER(pTask->taskPID),
			       ret);
		} else {
			wait_for_completion(&pTask->taskComplete);
			pTask->taskPID = THREAD_PID_INIT_VALUE;
			pTask->task_killed = 0;
			ret = NDIS_STATUS_SUCCESS;
		}
	}
#endif

	return ret;

}

int RtmpOSTaskNotifyToExit(struct rt_rtmp_os_task *pTask)
{

#ifndef KTHREAD_SUPPORT
	complete_and_exit(&pTask->taskComplete, 0);
#endif

	return 0;
}

void RtmpOSTaskCustomize(struct rt_rtmp_os_task *pTask)
{

#ifndef KTHREAD_SUPPORT

	daemonize((char *)&pTask->taskName[0] /*"%s",pAd->net_dev->name */);

	allow_signal(SIGTERM);
	allow_signal(SIGKILL);
	current->flags |= PF_NOFREEZE;

	/* signal that we've started the thread */
	complete(&pTask->taskComplete);

#endif
}

int RtmpOSTaskAttach(struct rt_rtmp_os_task *pTask,
			     IN int (*fn) (void *), IN void *arg)
{
	int status = NDIS_STATUS_SUCCESS;

#ifdef KTHREAD_SUPPORT
	pTask->task_killed = 0;
	pTask->kthread_task = NULL;
	pTask->kthread_task = kthread_run(fn, arg, pTask->taskName);
	if (IS_ERR(pTask->kthread_task))
		status = NDIS_STATUS_FAILURE;
#else
	pid_number = kernel_thread(fn, arg, RTMP_OS_MGMT_TASK_FLAGS);
	if (pid_number < 0) {
		DBGPRINT(RT_DEBUG_ERROR,
			 ("Attach task(%s) failed!\n", pTask->taskName));
		status = NDIS_STATUS_FAILURE;
	} else {
		pTask->taskPID = GET_PID(pid_number);

		/* Wait for the thread to start */
		wait_for_completion(&pTask->taskComplete);
		status = NDIS_STATUS_SUCCESS;
	}
#endif
	return status;
}

int RtmpOSTaskInit(struct rt_rtmp_os_task *pTask,
			   char *pTaskName, void * pPriv)
{
	int len;

	ASSERT(pTask);

#ifndef KTHREAD_SUPPORT
	NdisZeroMemory((u8 *)(pTask), sizeof(struct rt_rtmp_os_task));
#endif

	len = strlen(pTaskName);
	len =
	    len >
	    (RTMP_OS_TASK_NAME_LEN - 1) ? (RTMP_OS_TASK_NAME_LEN - 1) : len;
	NdisMoveMemory(&pTask->taskName[0], pTaskName, len);
	pTask->priv = pPriv;

#ifndef KTHREAD_SUPPORT
	RTMP_SEM_EVENT_INIT_LOCKED(&(pTask->taskSema));
	pTask->taskPID = THREAD_PID_INIT_VALUE;

	init_completion(&pTask->taskComplete);
#endif

	return NDIS_STATUS_SUCCESS;
}

void RTMP_IndicateMediaState(struct rt_rtmp_adapter *pAd)
{
	if (pAd->CommonCfg.bWirelessEvent) {
		if (pAd->IndicateMediaState == NdisMediaStateConnected) {
			RTMPSendWirelessEvent(pAd, IW_STA_LINKUP_EVENT_FLAG,
					      pAd->MacTab.Content[BSSID_WCID].
					      Addr, BSS0, 0);
		} else {
			RTMPSendWirelessEvent(pAd, IW_STA_LINKDOWN_EVENT_FLAG,
					      pAd->MacTab.Content[BSSID_WCID].
					      Addr, BSS0, 0);
		}
	}
}

int RtmpOSWrielessEventSend(struct rt_rtmp_adapter *pAd,
			    u32 eventType,
			    int flags,
			    u8 *pSrcMac,
			    u8 *pData, u32 dataLen)
{
	union iwreq_data wrqu;

	memset(&wrqu, 0, sizeof(wrqu));

	if (flags > -1)
		wrqu.data.flags = flags;

	if (pSrcMac)
		memcpy(wrqu.ap_addr.sa_data, pSrcMac, MAC_ADDR_LEN);

	if ((pData != NULL) && (dataLen > 0))
		wrqu.data.length = dataLen;

	wireless_send_event(pAd->net_dev, eventType, &wrqu, (char *)pData);
	return 0;
}

int RtmpOSNetDevAddrSet(struct net_device *pNetDev, u8 *pMacAddr)
{
	struct net_device *net_dev;
	struct rt_rtmp_adapter *pAd;

	net_dev = pNetDev;
	GET_PAD_FROM_NET_DEV(pAd, net_dev);

	/* work-around for the SuSE due to it has it's own interface name management system. */
	{
		NdisZeroMemory(pAd->StaCfg.dev_name, 16);
		NdisMoveMemory(pAd->StaCfg.dev_name, net_dev->name,
			       strlen(net_dev->name));
	}

	NdisMoveMemory(net_dev->dev_addr, pMacAddr, 6);

	return 0;
}

/*
  *	Assign the network dev name for created Ralink WiFi interface.
  */
static int RtmpOSNetDevRequestName(struct rt_rtmp_adapter *pAd,
				   struct net_device *dev,
				   char *pPrefixStr, int devIdx)
{
	struct net_device *existNetDev;
	char suffixName[IFNAMSIZ];
	char desiredName[IFNAMSIZ];
	int ifNameIdx, prefixLen, slotNameLen;
	int Status;

	prefixLen = strlen(pPrefixStr);
	ASSERT((prefixLen < IFNAMSIZ));

	for (ifNameIdx = devIdx; ifNameIdx < 32; ifNameIdx++) {
		memset(suffixName, 0, IFNAMSIZ);
		memset(desiredName, 0, IFNAMSIZ);
		strncpy(&desiredName[0], pPrefixStr, prefixLen);

		sprintf(suffixName, "%d", ifNameIdx);

		slotNameLen = strlen(suffixName);
		ASSERT(((slotNameLen + prefixLen) < IFNAMSIZ));
		strcat(desiredName, suffixName);

		existNetDev = RtmpOSNetDevGetByName(dev, &desiredName[0]);
		if (existNetDev == NULL)
			break;
		else
			RtmpOSNetDeviceRefPut(existNetDev);
	}

	if (ifNameIdx < 32) {
		strcpy(&dev->name[0], &desiredName[0]);
		Status = NDIS_STATUS_SUCCESS;
	} else {
		DBGPRINT(RT_DEBUG_ERROR,
			 ("Cannot request DevName with preifx(%s) and in range(0~32) as suffix from OS!\n",
			  pPrefixStr));
		Status = NDIS_STATUS_FAILURE;
	}

	return Status;
}

void RtmpOSNetDevClose(struct net_device *pNetDev)
{
	dev_close(pNetDev);
}

void RtmpOSNetDevFree(struct net_device *pNetDev)
{
	ASSERT(pNetDev);

	free_netdev(pNetDev);
}

int RtmpOSNetDevAlloc(struct net_device **new_dev_p, u32 privDataSize)
{
	/* assign it as null first. */
	*new_dev_p = NULL;

	DBGPRINT(RT_DEBUG_TRACE,
		 ("Allocate a net device with private data size=%d!\n",
		  privDataSize));
	*new_dev_p = alloc_etherdev(privDataSize);
	if (*new_dev_p)
		return NDIS_STATUS_SUCCESS;
	else
		return NDIS_STATUS_FAILURE;
}

struct net_device *RtmpOSNetDevGetByName(struct net_device *pNetDev, char *pDevName)
{
	struct net_device *pTargetNetDev = NULL;

	pTargetNetDev = dev_get_by_name(dev_net(pNetDev), pDevName);

	return pTargetNetDev;
}

void RtmpOSNetDeviceRefPut(struct net_device *pNetDev)
{
	/*
	   every time dev_get_by_name is called, and it has returned a valid struct
	   net_device*, dev_put should be called afterwards, because otherwise the
	   machine hangs when the device is unregistered (since dev->refcnt > 1).
	 */
	if (pNetDev)
		dev_put(pNetDev);
}

int RtmpOSNetDevDestory(struct rt_rtmp_adapter *pAd, struct net_device *pNetDev)
{

	/* TODO: Need to fix this */
	printk("WARNING: This function(%s) not implement yet!\n", __func__);
	return 0;
}

void RtmpOSNetDevDetach(struct net_device *pNetDev)
{
	unregister_netdev(pNetDev);
}

int RtmpOSNetDevAttach(struct net_device *pNetDev,
		       struct rt_rtmp_os_netdev_op_hook *pDevOpHook)
{
	int ret, rtnl_locked = FALSE;

	DBGPRINT(RT_DEBUG_TRACE, ("RtmpOSNetDevAttach()--->\n"));
	/* If we need hook some callback function to the net device structrue, now do it. */
	if (pDevOpHook) {
		struct rt_rtmp_adapter *pAd = NULL;

		GET_PAD_FROM_NET_DEV(pAd, pNetDev);

		pNetDev->netdev_ops = pDevOpHook->netdev_ops;

		/* OS specific flags, here we used to indicate if we are virtual interface */
		pNetDev->priv_flags = pDevOpHook->priv_flags;

		if (pAd->OpMode == OPMODE_STA) {
			pNetDev->wireless_handlers = &rt28xx_iw_handler_def;
		}

		/* copy the net device mac address to the net_device structure. */
		NdisMoveMemory(pNetDev->dev_addr, &pDevOpHook->devAddr[0],
			       MAC_ADDR_LEN);

		rtnl_locked = pDevOpHook->needProtcted;
	}

	if (rtnl_locked)
		ret = register_netdevice(pNetDev);
	else
		ret = register_netdev(pNetDev);

	DBGPRINT(RT_DEBUG_TRACE, ("<---RtmpOSNetDevAttach(), ret=%d\n", ret));
	if (ret == 0)
		return NDIS_STATUS_SUCCESS;
	else
		return NDIS_STATUS_FAILURE;
}

struct net_device *RtmpOSNetDevCreate(struct rt_rtmp_adapter *pAd,
			    int devType,
			    int devNum,
			    int privMemSize, char *pNamePrefix)
{
	struct net_device *pNetDev = NULL;
	int status;

	/* allocate a new network device */
	status = RtmpOSNetDevAlloc(&pNetDev, 0 /*privMemSize */);
	if (status != NDIS_STATUS_SUCCESS) {
		/* allocation fail, exit */
		DBGPRINT(RT_DEBUG_ERROR,
			 ("Allocate network device fail (%s)...\n",
			  pNamePrefix));
		return NULL;
	}

	/* find a available interface name, max 32 interfaces */
	status = RtmpOSNetDevRequestName(pAd, pNetDev, pNamePrefix, devNum);
	if (status != NDIS_STATUS_SUCCESS) {
		/* error! no any available ra name can be used! */
		DBGPRINT(RT_DEBUG_ERROR,
			 ("Assign interface name (%s with suffix 0~32) failed...\n",
			  pNamePrefix));
		RtmpOSNetDevFree(pNetDev);

		return NULL;
	} else {
		DBGPRINT(RT_DEBUG_TRACE,
			 ("The name of the new %s interface is %s...\n",
			  pNamePrefix, pNetDev->name));
	}

	return pNetDev;
}
