1/* 2 ************************************************************************* 3 * Ralink Tech Inc. 4 * 5F., No.36, Taiyuan St., Jhubei City, 5 * Hsinchu County 302, 6 * Taiwan, R.O.C. 7 * 8 * (c) Copyright 2002-2007, Ralink Technology, Inc. 9 * 10 * This program is free software; you can redistribute it and/or modify * 11 * it under the terms of the GNU General Public License as published by * 12 * the Free Software Foundation; either version 2 of the License, or * 13 * (at your option) any later version. * 14 * * 15 * This program is distributed in the hope that it will be useful, * 16 * but WITHOUT ANY WARRANTY; without even the implied warranty of * 17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * 18 * GNU General Public License for more details. * 19 * * 20 * You should have received a copy of the GNU General Public License * 21 * along with this program; if not, write to the * 22 * Free Software Foundation, Inc., * 23 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * 24 * * 25 ************************************************************************* 26 27 Module Name: 28 rt_main_dev.c 29 30 Abstract: 31 Create and register network interface. 32 33 Revision History: 34 Who When What 35 -------- ---------- ---------------------------------------------- 36*/ 37 38#include "rt_config.h" 39 40/*---------------------------------------------------------------------*/ 41/* Private Variables Used */ 42/*---------------------------------------------------------------------*/ 43 44char *mac = ""; /* default 00:00:00:00:00:00 */ 45char *hostname = ""; /* default CMPC */ 46module_param(mac, charp, 0); 47MODULE_PARM_DESC(mac, "rt28xx: wireless mac addr"); 48 49/*---------------------------------------------------------------------*/ 50/* Prototypes of Functions Used */ 51/*---------------------------------------------------------------------*/ 52 53/* public function prototype */ 54int rt28xx_close(IN struct net_device *net_dev); 55int rt28xx_open(struct net_device *net_dev); 56 57/* private function prototype */ 58static int rt28xx_send_packets(IN struct sk_buff *skb_p, 59 IN struct net_device *net_dev); 60 61static struct net_device_stats *RT28xx_get_ether_stats(IN struct net_device 62 *net_dev); 63 64/* 65======================================================================== 66Routine Description: 67 Close raxx interface. 68 69Arguments: 70 *net_dev the raxx interface pointer 71 72Return Value: 73 0 Open OK 74 otherwise Open Fail 75 76Note: 77 1. if open fail, kernel will not call the close function. 78 2. Free memory for 79 (1) Mlme Memory Handler: MlmeHalt() 80 (2) TX & RX: RTMPFreeTxRxRingMemory() 81 (3) BA Reordering: ba_reordering_resource_release() 82======================================================================== 83*/ 84int MainVirtualIF_close(IN struct net_device *net_dev) 85{ 86 struct rt_rtmp_adapter *pAd = NULL; 87 88 GET_PAD_FROM_NET_DEV(pAd, net_dev); 89 90 /* Sanity check for pAd */ 91 if (pAd == NULL) 92 return 0; /* close ok */ 93 94 netif_carrier_off(pAd->net_dev); 95 netif_stop_queue(pAd->net_dev); 96 97 { 98 BOOLEAN Cancelled; 99 100 if (INFRA_ON(pAd) && 101 (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_NIC_NOT_EXIST))) { 102 struct rt_mlme_disassoc_req DisReq; 103 struct rt_mlme_queue_elem *MsgElem = 104 (struct rt_mlme_queue_elem *)kmalloc(sizeof(struct rt_mlme_queue_elem), 105 MEM_ALLOC_FLAG); 106 107 if (MsgElem) { 108 COPY_MAC_ADDR(DisReq.Addr, 109 pAd->CommonCfg.Bssid); 110 DisReq.Reason = REASON_DEAUTH_STA_LEAVING; 111 112 MsgElem->Machine = ASSOC_STATE_MACHINE; 113 MsgElem->MsgType = MT2_MLME_DISASSOC_REQ; 114 MsgElem->MsgLen = 115 sizeof(struct rt_mlme_disassoc_req); 116 NdisMoveMemory(MsgElem->Msg, &DisReq, 117 sizeof 118 (struct rt_mlme_disassoc_req)); 119 120 /* Prevent to connect AP again in STAMlmePeriodicExec */ 121 pAd->MlmeAux.AutoReconnectSsidLen = 32; 122 NdisZeroMemory(pAd->MlmeAux.AutoReconnectSsid, 123 pAd->MlmeAux. 124 AutoReconnectSsidLen); 125 126 pAd->Mlme.CntlMachine.CurrState = 127 CNTL_WAIT_OID_DISASSOC; 128 MlmeDisassocReqAction(pAd, MsgElem); 129 kfree(MsgElem); 130 } 131 132 RTMPusecDelay(1000); 133 } 134 135 RTMPCancelTimer(&pAd->StaCfg.StaQuickResponeForRateUpTimer, 136 &Cancelled); 137 RTMPCancelTimer(&pAd->StaCfg.WpaDisassocAndBlockAssocTimer, 138 &Cancelled); 139 } 140 141 VIRTUAL_IF_DOWN(pAd); 142 143 RT_MOD_DEC_USE_COUNT(); 144 145 return 0; /* close ok */ 146} 147 148/* 149======================================================================== 150Routine Description: 151 Open raxx interface. 152 153Arguments: 154 *net_dev the raxx interface pointer 155 156Return Value: 157 0 Open OK 158 otherwise Open Fail 159 160Note: 161 1. if open fail, kernel will not call the close function. 162 2. Free memory for 163 (1) Mlme Memory Handler: MlmeHalt() 164 (2) TX & RX: RTMPFreeTxRxRingMemory() 165 (3) BA Reordering: ba_reordering_resource_release() 166======================================================================== 167*/ 168int MainVirtualIF_open(IN struct net_device *net_dev) 169{ 170 struct rt_rtmp_adapter *pAd = NULL; 171 172 GET_PAD_FROM_NET_DEV(pAd, net_dev); 173 174 /* Sanity check for pAd */ 175 if (pAd == NULL) 176 return 0; /* close ok */ 177 178 if (VIRTUAL_IF_UP(pAd) != 0) 179 return -1; 180 181 /* increase MODULE use count */ 182 RT_MOD_INC_USE_COUNT(); 183 184 netif_start_queue(net_dev); 185 netif_carrier_on(net_dev); 186 netif_wake_queue(net_dev); 187 188 return 0; 189} 190 191/* 192======================================================================== 193Routine Description: 194 Close raxx interface. 195 196Arguments: 197 *net_dev the raxx interface pointer 198 199Return Value: 200 0 Open OK 201 otherwise Open Fail 202 203Note: 204 1. if open fail, kernel will not call the close function. 205 2. Free memory for 206 (1) Mlme Memory Handler: MlmeHalt() 207 (2) TX & RX: RTMPFreeTxRxRingMemory() 208 (3) BA Reordering: ba_reordering_resource_release() 209======================================================================== 210*/ 211int rt28xx_close(struct net_device *dev) 212{ 213 struct net_device *net_dev = (struct net_device *)dev; 214 struct rt_rtmp_adapter *pAd = NULL; 215 BOOLEAN Cancelled; 216 u32 i = 0; 217 218#ifdef RTMP_MAC_USB 219 DECLARE_WAIT_QUEUE_HEAD_ONSTACK(unlink_wakeup); 220 DECLARE_WAITQUEUE(wait, current); 221#endif /* RTMP_MAC_USB // */ 222 223 GET_PAD_FROM_NET_DEV(pAd, net_dev); 224 225 DBGPRINT(RT_DEBUG_TRACE, ("===> rt28xx_close\n")); 226 227 Cancelled = FALSE; 228 /* Sanity check for pAd */ 229 if (pAd == NULL) 230 return 0; /* close ok */ 231 232 { 233#ifdef RTMP_MAC_PCI 234 RTMPPCIeLinkCtrlValueRestore(pAd, RESTORE_CLOSE); 235#endif /* RTMP_MAC_PCI // */ 236 237 /* If dirver doesn't wake up firmware here, */ 238 /* NICLoadFirmware will hang forever when interface is up again. */ 239 if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_DOZE)) { 240 AsicForceWakeup(pAd, TRUE); 241 } 242#ifdef RTMP_MAC_USB 243 RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_REMOVE_IN_PROGRESS); 244#endif /* RTMP_MAC_USB // */ 245 246 MlmeRadioOff(pAd); 247#ifdef RTMP_MAC_PCI 248 pAd->bPCIclkOff = FALSE; 249#endif /* RTMP_MAC_PCI // */ 250 } 251 252 RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS); 253 254 for (i = 0; i < NUM_OF_TX_RING; i++) { 255 while (pAd->DeQueueRunning[i] == TRUE) { 256 DBGPRINT(RT_DEBUG_TRACE, 257 ("Waiting for TxQueue[%d] done..........\n", 258 i)); 259 RTMPusecDelay(1000); 260 } 261 } 262 263#ifdef RTMP_MAC_USB 264 /* ensure there are no more active urbs. */ 265 add_wait_queue(&unlink_wakeup, &wait); 266 pAd->wait = &unlink_wakeup; 267 268 /* maybe wait for deletions to finish. */ 269 i = 0; 270 /*while((i < 25) && atomic_read(&pAd->PendingRx) > 0) */ 271 while (i < 25) { 272 unsigned long IrqFlags; 273 274 RTMP_IRQ_LOCK(&pAd->BulkInLock, IrqFlags); 275 if (pAd->PendingRx == 0) { 276 RTMP_IRQ_UNLOCK(&pAd->BulkInLock, IrqFlags); 277 break; 278 } 279 RTMP_IRQ_UNLOCK(&pAd->BulkInLock, IrqFlags); 280 281 msleep(UNLINK_TIMEOUT_MS); /*Time in millisecond */ 282 i++; 283 } 284 pAd->wait = NULL; 285 remove_wait_queue(&unlink_wakeup, &wait); 286#endif /* RTMP_MAC_USB // */ 287 288 /* Stop Mlme state machine */ 289 MlmeHalt(pAd); 290 291 /* Close net tasklets */ 292 RtmpNetTaskExit(pAd); 293 294 { 295 MacTableReset(pAd); 296 } 297 298 MeasureReqTabExit(pAd); 299 TpcReqTabExit(pAd); 300 301 /* Close kernel threads */ 302 RtmpMgmtTaskExit(pAd); 303 304#ifdef RTMP_MAC_PCI 305 { 306 BOOLEAN brc; 307 /* unsigned long Value; */ 308 309 if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_ACTIVE)) { 310 RTMP_ASIC_INTERRUPT_DISABLE(pAd); 311 } 312 /* Receive packets to clear DMA index after disable interrupt. */ 313 /*RTMPHandleRxDoneInterrupt(pAd); */ 314 /* put to radio off to save power when driver unload. After radiooff, can't write /read register. So need to finish all */ 315 /* register access before Radio off. */ 316 317 brc = RT28xxPciAsicRadioOff(pAd, RTMP_HALT, 0); 318 319/*In solution 3 of 3090F, the bPCIclkOff will be set to TRUE after calling RT28xxPciAsicRadioOff */ 320 pAd->bPCIclkOff = FALSE; 321 322 if (brc == FALSE) { 323 DBGPRINT(RT_DEBUG_ERROR, 324 ("%s call RT28xxPciAsicRadioOff fail!\n", 325 __func__)); 326 } 327 } 328 329/* 330 if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_ACTIVE)) 331 { 332 RTMP_ASIC_INTERRUPT_DISABLE(pAd); 333 } 334 335 // Disable Rx, register value supposed will remain after reset 336 NICIssueReset(pAd); 337*/ 338#endif /* RTMP_MAC_PCI // */ 339 340 /* Free IRQ */ 341 if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_IN_USE)) { 342#ifdef RTMP_MAC_PCI 343 /* Deregister interrupt function */ 344 RtmpOSIRQRelease(net_dev); 345#endif /* RTMP_MAC_PCI // */ 346 RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_IN_USE); 347 } 348 /* Free Ring or USB buffers */ 349 RTMPFreeTxRxRingMemory(pAd); 350 351 RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS); 352 353 /* Free BA reorder resource */ 354 ba_reordering_resource_release(pAd); 355 356 RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_START_UP); 357 358/*+++Modify by woody to solve the bulk fail+++*/ 359 { 360 } 361 362 DBGPRINT(RT_DEBUG_TRACE, ("<=== rt28xx_close\n")); 363 return 0; /* close ok */ 364} /* End of rt28xx_close */ 365 366/* 367======================================================================== 368Routine Description: 369 Open raxx interface. 370 371Arguments: 372 *net_dev the raxx interface pointer 373 374Return Value: 375 0 Open OK 376 otherwise Open Fail 377 378Note: 379======================================================================== 380*/ 381int rt28xx_open(struct net_device *dev) 382{ 383 struct net_device *net_dev = (struct net_device *)dev; 384 struct rt_rtmp_adapter *pAd = NULL; 385 int retval = 0; 386 /*struct os_cookie *pObj; */ 387 388 GET_PAD_FROM_NET_DEV(pAd, net_dev); 389 390 /* Sanity check for pAd */ 391 if (pAd == NULL) { 392 /* if 1st open fail, pAd will be free; 393 So the net_dev->ml_priv will be NULL in 2rd open */ 394 return -1; 395 } 396 397 if (net_dev->priv_flags == INT_MAIN) { 398 if (pAd->OpMode == OPMODE_STA) 399 net_dev->wireless_handlers = 400 (struct iw_handler_def *)&rt28xx_iw_handler_def; 401 } 402 /* Request interrupt service routine for PCI device */ 403 /* register the interrupt routine with the os */ 404 RtmpOSIRQRequest(net_dev); 405 406 /* Init IRQ parameters stored in pAd */ 407 RTMP_IRQ_INIT(pAd); 408 409 /* Chip & other init */ 410 if (rt28xx_init(pAd, mac, hostname) == FALSE) 411 goto err; 412 413 /* Enable Interrupt */ 414 RTMP_IRQ_ENABLE(pAd); 415 416 /* Now Enable RxTx */ 417 RTMPEnableRxTx(pAd); 418 RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_START_UP); 419 420 { 421 u32 reg = 0; 422 RTMP_IO_READ32(pAd, 0x1300, ®); /* clear garbage interrupts */ 423 printk("0x1300 = %08x\n", reg); 424 } 425 426 { 427/* u32 reg; */ 428/* u8 byte; */ 429/* u16 tmp; */ 430 431/* RTMP_IO_READ32(pAd, XIFS_TIME_CFG, ®); */ 432 433/* tmp = 0x0805; */ 434/* reg = (reg & 0xffff0000) | tmp; */ 435/* RTMP_IO_WRITE32(pAd, XIFS_TIME_CFG, reg); */ 436 437 } 438#ifdef RTMP_MAC_PCI 439 RTMPInitPCIeLinkCtrlValue(pAd); 440#endif /* RTMP_MAC_PCI // */ 441 442 return retval; 443 444err: 445/*+++Add by shiang, move from rt28xx_init() to here. */ 446 RtmpOSIRQRelease(net_dev); 447/*---Add by shiang, move from rt28xx_init() to here. */ 448 return -1; 449} /* End of rt28xx_open */ 450 451static const struct net_device_ops rt2860_netdev_ops = { 452 .ndo_open = MainVirtualIF_open, 453 .ndo_stop = MainVirtualIF_close, 454 .ndo_do_ioctl = rt28xx_sta_ioctl, 455 .ndo_get_stats = RT28xx_get_ether_stats, 456 .ndo_validate_addr = NULL, 457 .ndo_set_mac_address = eth_mac_addr, 458 .ndo_change_mtu = eth_change_mtu, 459 .ndo_start_xmit = rt28xx_send_packets, 460}; 461 462struct net_device *RtmpPhyNetDevInit(struct rt_rtmp_adapter *pAd, 463 struct rt_rtmp_os_netdev_op_hook *pNetDevHook) 464{ 465 struct net_device *net_dev = NULL; 466/* int Status; */ 467 468 net_dev = 469 RtmpOSNetDevCreate(pAd, INT_MAIN, 0, sizeof(struct rt_rtmp_adapter *), 470 INF_MAIN_DEV_NAME); 471 if (net_dev == NULL) { 472 printk 473 ("RtmpPhyNetDevInit(): creation failed for main physical net device!\n"); 474 return NULL; 475 } 476 477 NdisZeroMemory((unsigned char *)pNetDevHook, 478 sizeof(struct rt_rtmp_os_netdev_op_hook)); 479 pNetDevHook->netdev_ops = &rt2860_netdev_ops; 480 pNetDevHook->priv_flags = INT_MAIN; 481 pNetDevHook->needProtcted = FALSE; 482 483 net_dev->ml_priv = (void *)pAd; 484 pAd->net_dev = net_dev; 485 486 return net_dev; 487 488} 489 490/* 491======================================================================== 492Routine Description: 493 The entry point for Linux kernel sent packet to our driver. 494 495Arguments: 496 sk_buff *skb the pointer refer to a sk_buffer. 497 498Return Value: 499 0 500 501Note: 502 This function is the entry point of Tx Path for Os delivery packet to 503 our driver. You only can put OS-depened & STA/AP common handle procedures 504 in here. 505======================================================================== 506*/ 507int rt28xx_packet_xmit(struct sk_buff *skb) 508{ 509 struct net_device *net_dev = skb->dev; 510 struct rt_rtmp_adapter *pAd = NULL; 511 int status = NETDEV_TX_OK; 512 void *pPacket = (void *)skb; 513 514 GET_PAD_FROM_NET_DEV(pAd, net_dev); 515 516 /* RT2870STA does this in RTMPSendPackets() */ 517 518 { 519 /* Drop send request since we are in monitor mode */ 520 if (MONITOR_ON(pAd)) { 521 RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_FAILURE); 522 goto done; 523 } 524 } 525 526 /* EapolStart size is 18 */ 527 if (skb->len < 14) { 528 /*printk("bad packet size: %d\n", pkt->len); */ 529 hex_dump("bad packet", skb->data, skb->len); 530 RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_FAILURE); 531 goto done; 532 } 533 534 RTMP_SET_PACKET_5VT(pPacket, 0); 535 STASendPackets((void *)pAd, (void **)&pPacket, 1); 536 537 status = NETDEV_TX_OK; 538done: 539 540 return status; 541} 542 543/* 544======================================================================== 545Routine Description: 546 Send a packet to WLAN. 547 548Arguments: 549 skb_p points to our adapter 550 dev_p which WLAN network interface 551 552Return Value: 553 0: transmit successfully 554 otherwise: transmit fail 555 556Note: 557======================================================================== 558*/ 559static int rt28xx_send_packets(IN struct sk_buff *skb_p, 560 IN struct net_device *net_dev) 561{ 562 struct rt_rtmp_adapter *pAd = NULL; 563 564 GET_PAD_FROM_NET_DEV(pAd, net_dev); 565 566 if (!(net_dev->flags & IFF_UP)) { 567 RELEASE_NDIS_PACKET(pAd, (void *)skb_p, 568 NDIS_STATUS_FAILURE); 569 return NETDEV_TX_OK; 570 } 571 572 NdisZeroMemory((u8 *)&skb_p->cb[CB_OFF], 15); 573 RTMP_SET_PACKET_NET_DEVICE_MBSSID(skb_p, MAIN_MBSSID); 574 575 return rt28xx_packet_xmit(skb_p); 576} 577 578/* This function will be called when query /proc */ 579struct iw_statistics *rt28xx_get_wireless_stats(IN struct net_device *net_dev) 580{ 581 struct rt_rtmp_adapter *pAd = NULL; 582 583 GET_PAD_FROM_NET_DEV(pAd, net_dev); 584 585 DBGPRINT(RT_DEBUG_TRACE, ("rt28xx_get_wireless_stats --->\n")); 586 587 pAd->iw_stats.status = 0; /* Status - device dependent for now */ 588 589 /* link quality */ 590 if (pAd->OpMode == OPMODE_STA) 591 pAd->iw_stats.qual.qual = 592 ((pAd->Mlme.ChannelQuality * 12) / 10 + 10); 593 594 if (pAd->iw_stats.qual.qual > 100) 595 pAd->iw_stats.qual.qual = 100; 596 597 if (pAd->OpMode == OPMODE_STA) { 598 pAd->iw_stats.qual.level = 599 RTMPMaxRssi(pAd, pAd->StaCfg.RssiSample.LastRssi0, 600 pAd->StaCfg.RssiSample.LastRssi1, 601 pAd->StaCfg.RssiSample.LastRssi2); 602 } 603 604 pAd->iw_stats.qual.noise = pAd->BbpWriteLatch[66]; /* noise level (dBm) */ 605 606 pAd->iw_stats.qual.noise += 256 - 143; 607 pAd->iw_stats.qual.updated = 1; /* Flags to know if updated */ 608#ifdef IW_QUAL_DBM 609 pAd->iw_stats.qual.updated |= IW_QUAL_DBM; /* Level + Noise are dBm */ 610#endif /* IW_QUAL_DBM // */ 611 612 pAd->iw_stats.discard.nwid = 0; /* Rx : Wrong nwid/essid */ 613 pAd->iw_stats.miss.beacon = 0; /* Missed beacons/superframe */ 614 615 DBGPRINT(RT_DEBUG_TRACE, ("<--- rt28xx_get_wireless_stats\n")); 616 return &pAd->iw_stats; 617} 618 619void tbtt_tasklet(unsigned long data) 620{ 621/*#define MAX_TX_IN_TBTT (16) */ 622 623} 624 625/* 626 ======================================================================== 627 628 Routine Description: 629 return ethernet statistics counter 630 631 Arguments: 632 net_dev Pointer to net_device 633 634 Return Value: 635 net_device_stats* 636 637 Note: 638 639 ======================================================================== 640*/ 641static struct net_device_stats *RT28xx_get_ether_stats(IN struct net_device 642 *net_dev) 643{ 644 struct rt_rtmp_adapter *pAd = NULL; 645 646 if (net_dev) 647 GET_PAD_FROM_NET_DEV(pAd, net_dev); 648 649 if (pAd) { 650 651 pAd->stats.rx_packets = 652 pAd->WlanCounters.ReceivedFragmentCount.QuadPart; 653 pAd->stats.tx_packets = 654 pAd->WlanCounters.TransmittedFragmentCount.QuadPart; 655 656 pAd->stats.rx_bytes = pAd->RalinkCounters.ReceivedByteCount; 657 pAd->stats.tx_bytes = pAd->RalinkCounters.TransmittedByteCount; 658 659 pAd->stats.rx_errors = pAd->Counters8023.RxErrors; 660 pAd->stats.tx_errors = pAd->Counters8023.TxErrors; 661 662 pAd->stats.rx_dropped = 0; 663 pAd->stats.tx_dropped = 0; 664 665 pAd->stats.multicast = pAd->WlanCounters.MulticastReceivedFrameCount.QuadPart; /* multicast packets received */ 666 pAd->stats.collisions = pAd->Counters8023.OneCollision + pAd->Counters8023.MoreCollisions; /* Collision packets */ 667 668 pAd->stats.rx_length_errors = 0; 669 pAd->stats.rx_over_errors = pAd->Counters8023.RxNoBuffer; /* receiver ring buff overflow */ 670 pAd->stats.rx_crc_errors = 0; /*pAd->WlanCounters.FCSErrorCount; // recved pkt with crc error */ 671 pAd->stats.rx_frame_errors = pAd->Counters8023.RcvAlignmentErrors; /* recv'd frame alignment error */ 672 pAd->stats.rx_fifo_errors = pAd->Counters8023.RxNoBuffer; /* recv'r fifo overrun */ 673 pAd->stats.rx_missed_errors = 0; /* receiver missed packet */ 674 675 /* detailed tx_errors */ 676 pAd->stats.tx_aborted_errors = 0; 677 pAd->stats.tx_carrier_errors = 0; 678 pAd->stats.tx_fifo_errors = 0; 679 pAd->stats.tx_heartbeat_errors = 0; 680 pAd->stats.tx_window_errors = 0; 681 682 /* for cslip etc */ 683 pAd->stats.rx_compressed = 0; 684 pAd->stats.tx_compressed = 0; 685 686 return &pAd->stats; 687 } else 688 return NULL; 689} 690 691BOOLEAN RtmpPhyNetDevExit(struct rt_rtmp_adapter *pAd, struct net_device *net_dev) 692{ 693 694 /* Unregister network device */ 695 if (net_dev != NULL) { 696 printk 697 ("RtmpOSNetDevDetach(): RtmpOSNetDeviceDetach(), dev->name=%s!\n", 698 net_dev->name); 699 RtmpOSNetDevDetach(net_dev); 700 } 701 702 return TRUE; 703 704} 705 706/* 707======================================================================== 708Routine Description: 709 Allocate memory for adapter control block. 710 711Arguments: 712 pAd Pointer to our adapter 713 714Return Value: 715 NDIS_STATUS_SUCCESS 716 NDIS_STATUS_FAILURE 717 NDIS_STATUS_RESOURCES 718 719Note: 720======================================================================== 721*/ 722int AdapterBlockAllocateMemory(void *handle, void ** ppAd) 723{ 724 725 *ppAd = (void *)vmalloc(sizeof(struct rt_rtmp_adapter)); /*pci_alloc_consistent(pci_dev, sizeof(struct rt_rtmp_adapter), phy_addr); */ 726 727 if (*ppAd) { 728 NdisZeroMemory(*ppAd, sizeof(struct rt_rtmp_adapter)); 729 ((struct rt_rtmp_adapter *)*ppAd)->OS_Cookie = handle; 730 return NDIS_STATUS_SUCCESS; 731 } else { 732 return NDIS_STATUS_FAILURE; 733 } 734} 735