1 /*******************************************************************************
3 * Wireless device driver for Linux (wlags49).
5 * Copyright (c) 1998-2003 Agere Systems Inc.
9 * Initially developed by TriplePoint, Inc.
10 * http://www.triplepoint.com
12 *------------------------------------------------------------------------------
14 * This file contains processing and initialization specific to PCI/miniPCI
17 *------------------------------------------------------------------------------
21 * This software is provided subject to the following terms and conditions,
22 * which you should read carefully before using the software. Using this
23 * software indicates your acceptance of these terms and conditions. If you do
24 * not agree with these terms and conditions, do not use the software.
26 * Copyright © 2003 Agere Systems Inc.
27 * All rights reserved.
29 * Redistribution and use in source or binary forms, with or without
30 * modifications, are permitted provided that the following conditions are met:
32 * . Redistributions of source code must retain the above copyright notice, this
33 * list of conditions and the following Disclaimer as comments in the code as
34 * well as in the documentation and/or other materials provided with the
37 * . Redistributions in binary form must reproduce the above copyright notice,
38 * this list of conditions and the following Disclaimer in the documentation
39 * and/or other materials provided with the distribution.
41 * . Neither the name of Agere Systems Inc. nor the names of the contributors
42 * may be used to endorse or promote products derived from this software
43 * without specific prior written permission.
47 * THIS SOFTWARE IS PROVIDED
\93AS IS
\94 AND ANY EXPRESS OR IMPLIED WARRANTIES,
48 * INCLUDING, BUT NOT LIMITED TO, INFRINGEMENT AND THE IMPLIED WARRANTIES OF
49 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. ANY
50 * USE, MODIFICATION OR DISTRIBUTION OF THIS SOFTWARE IS SOLELY AT THE USERS OWN
51 * RISK. IN NO EVENT SHALL AGERE SYSTEMS INC. OR CONTRIBUTORS BE LIABLE FOR ANY
52 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
53 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
54 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
55 * ON ANY THEORY OF LIABILITY, INCLUDING, BUT NOT LIMITED TO, CONTRACT, STRICT
56 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
57 * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH
60 ******************************************************************************/
62 /*******************************************************************************
64 ******************************************************************************/
65 #include <wireless/wl_version.h>
67 #include <linux/module.h>
68 #include <linux/kernel.h>
69 #include <linux/errno.h>
70 #include <linux/pci.h>
71 #include <linux/sched.h>
72 #include <linux/ptrace.h>
73 #include <linux/ctype.h>
74 #include <linux/string.h>
75 //#include <linux/timer.h>
76 #include <linux/interrupt.h>
78 #include <linux/delay.h>
81 #include <asm/bitops.h>
82 #include <asm/uaccess.h>
84 #include <linux/ethtool.h>
85 #include <linux/netdevice.h>
86 #include <linux/etherdevice.h>
87 #include <linux/skbuff.h>
88 #include <linux/if_arp.h>
89 #include <linux/ioport.h>
91 #include <hcf/debug.h>
97 #include <wireless/wl_if.h>
98 #include <wireless/wl_internal.h>
99 #include <wireless/wl_util.h>
100 #include <wireless/wl_main.h>
101 #include <wireless/wl_netdev.h>
102 #include <wireless/wl_pci.h>
105 /*******************************************************************************
107 ******************************************************************************/
109 extern dbg_info_t *DbgInfo;
112 /* define the PCI device Table Cardname and id tables */
113 static struct pci_device_id wl_pci_tbl[] = {
114 { PCI_DEVICE(PCI_VENDOR_ID_WL_LKM, PCI_DEVICE_ID_WL_LKM_0), },
115 { PCI_DEVICE(PCI_VENDOR_ID_WL_LKM, PCI_DEVICE_ID_WL_LKM_1), },
116 { PCI_DEVICE(PCI_VENDOR_ID_WL_LKM, PCI_DEVICE_ID_WL_LKM_2), },
118 { } /* Terminating entry */
121 MODULE_DEVICE_TABLE(pci, wl_pci_tbl);
123 /*******************************************************************************
124 * function prototypes
125 ******************************************************************************/
126 int wl_pci_probe( struct pci_dev *pdev,
127 const struct pci_device_id *ent );
128 void wl_pci_remove(struct pci_dev *pdev);
129 int wl_pci_setup( struct pci_dev *pdev );
130 void wl_pci_enable_cardbus_interrupts( struct pci_dev *pdev );
133 int wl_pci_dma_alloc( struct pci_dev *pdev, struct wl_private *lp );
134 int wl_pci_dma_free( struct pci_dev *pdev, struct wl_private *lp );
135 int wl_pci_dma_alloc_tx_packet( struct pci_dev *pdev, struct wl_private *lp,
137 int wl_pci_dma_free_tx_packet( struct pci_dev *pdev, struct wl_private *lp,
139 int wl_pci_dma_alloc_rx_packet( struct pci_dev *pdev, struct wl_private *lp,
141 int wl_pci_dma_free_rx_packet( struct pci_dev *pdev, struct wl_private *lp,
143 int wl_pci_dma_alloc_desc_and_buf( struct pci_dev *pdev, struct wl_private *lp,
144 DESC_STRCT **desc, int size );
145 int wl_pci_dma_free_desc_and_buf( struct pci_dev *pdev, struct wl_private *lp,
147 int wl_pci_dma_alloc_desc( struct pci_dev *pdev, struct wl_private *lp,
149 int wl_pci_dma_free_desc( struct pci_dev *pdev, struct wl_private *lp,
151 int wl_pci_dma_alloc_buf( struct pci_dev *pdev, struct wl_private *lp,
152 DESC_STRCT *desc, int size );
153 int wl_pci_dma_free_buf( struct pci_dev *pdev, struct wl_private *lp,
156 void wl_pci_dma_hcf_reclaim_rx( struct wl_private *lp );
159 /*******************************************************************************
160 * PCI module function registration
161 ******************************************************************************/
162 static struct pci_driver wl_driver = {
164 .id_table = wl_pci_tbl,
165 .probe = wl_pci_probe,
166 .remove = wl_pci_remove,
171 /*******************************************************************************
172 * wl_adapter_init_module()
173 *******************************************************************************
177 * Called by init_module() to perform PCI-specific driver initialization.
187 ******************************************************************************/
188 int wl_adapter_init_module( void )
191 /*------------------------------------------------------------------------*/
193 DBG_ENTER( DbgInfo );
194 DBG_TRACE( DbgInfo, "wl_adapter_init_module() -- PCI\n" );
196 result = pci_register_driver( &wl_driver ); //;?replace with pci_module_init, Rubini pg 490
197 //;? why not do something with the result
199 DBG_LEAVE( DbgInfo );
201 } // wl_adapter_init_module
202 /*============================================================================*/
204 /*******************************************************************************
205 * wl_adapter_cleanup_module()
206 *******************************************************************************
210 * Called by cleanup_module() to perform PCI-specific driver cleanup.
220 ******************************************************************************/
221 void wl_adapter_cleanup_module( void )
223 //;?how come wl_adapter_cleanup_module is located in a seemingly pci specific module
224 DBG_ENTER( DbgInfo );
226 //;?DBG_TRACE below feels like nearly redundant in the light of DBG_ENTER above
227 DBG_TRACE( DbgInfo, "wl_adapter_cleanup_module() -- PCI\n" );
229 pci_unregister_driver( &wl_driver );
231 DBG_LEAVE( DbgInfo );
233 } // wl_adapter_cleanup_module
234 /*============================================================================*/
236 /*******************************************************************************
237 * wl_adapter_insert()
238 *******************************************************************************
242 * Called by wl_pci_probe() to continue the process of device insertion.
246 * dev - a pointer to the device's net_device structure
252 ******************************************************************************/
253 int wl_adapter_insert( struct net_device *dev )
256 /*------------------------------------------------------------------------*/
258 DBG_ENTER( DbgInfo );
260 DBG_TRACE( DbgInfo, "wl_adapter_insert() -- PCI\n" );
263 DBG_ERROR( DbgInfo, "net_device pointer is NULL!!!\n" );
264 } else if( dev->priv == NULL ) {
265 DBG_ERROR( DbgInfo, "wl_private pointer is NULL!!!\n" );
266 } else if( wl_insert( dev ) ) { /* Perform remaining device initialization */
269 DBG_TRACE( DbgInfo, "wl_insert() FAILED\n" );
271 DBG_LEAVE( DbgInfo );
273 } // wl_adapter_insert
274 /*============================================================================*/
276 /*******************************************************************************
278 *******************************************************************************
286 * dev - a pointer to the device's net_device structure
292 ******************************************************************************/
293 int wl_adapter_open( struct net_device *dev )
296 int hcf_status = HCF_SUCCESS;
297 /*------------------------------------------------------------------------*/
299 DBG_ENTER( DbgInfo );
301 DBG_TRACE( DbgInfo, "wl_adapter_open() -- PCI\n" );
303 hcf_status = wl_open( dev );
305 if( hcf_status != HCF_SUCCESS ) {
309 DBG_LEAVE( DbgInfo );
312 /*============================================================================*/
314 /*******************************************************************************
316 *******************************************************************************
324 * dev - a pointer to the device's net_device structure
330 ******************************************************************************/
331 int wl_adapter_close( struct net_device *dev )
333 DBG_ENTER( DbgInfo );
335 DBG_TRACE( DbgInfo, "wl_adapter_close() -- PCI\n" );
336 DBG_TRACE( DbgInfo, "%s: Shutting down adapter.\n", dev->name );
340 DBG_LEAVE( DbgInfo );
342 } // wl_adapter_close
343 /*============================================================================*/
345 /*******************************************************************************
346 * wl_adapter_is_open()
347 *******************************************************************************
351 * Check whether this device is open. Returns
355 * dev - a pointer to the device's net_device structure
359 * nonzero if device is open.
361 ******************************************************************************/
362 int wl_adapter_is_open( struct net_device *dev )
364 /* This function is used in PCMCIA to check the status of the 'open' field
365 in the dev_link_t structure associated with a network device. There
366 doesn't seem to be an analog to this for PCI, and checking the status
367 contained in the net_device structure doesn't have the same effect.
368 For now, return TRUE, but find out if this is necessary for PCI. */
371 } // wl_adapter_is_open
372 /*============================================================================*/
374 /*******************************************************************************
376 *******************************************************************************
380 * Registered in the pci_driver structure, this function is called when the
381 * PCI subsystem finds a new PCI device which matches the information contained
382 * in the pci_device_id table.
386 * pdev - a pointer to the device's pci_dev structure
387 * ent - this device's entry in the pci_device_id table
392 * errno value otherwise
394 ******************************************************************************/
395 int wl_pci_probe( struct pci_dev *pdev,
396 const struct pci_device_id *ent )
399 /*------------------------------------------------------------------------*/
401 DBG_ENTER( DbgInfo );
402 DBG_PRINT( "%s\n", VERSION_INFO );
404 result = wl_pci_setup( pdev );
406 DBG_LEAVE( DbgInfo );
410 /*============================================================================*/
412 /*******************************************************************************
414 *******************************************************************************
418 * Registered in the pci_driver structure, this function is called when the
419 * PCI subsystem detects that a PCI device which matches the information
420 * contained in the pci_device_id table has been removed.
424 * pdev - a pointer to the device's pci_dev structure
430 ******************************************************************************/
431 void wl_pci_remove(struct pci_dev *pdev)
433 struct net_device *dev = NULL;
434 /*------------------------------------------------------------------------*/
436 DBG_ENTER( DbgInfo );
438 /* Make sure the pci_dev pointer passed in is valid */
440 DBG_ERROR( DbgInfo, "PCI subsys passed in an invalid pci_dev pointer\n" );
444 dev = pci_get_drvdata( pdev );
446 DBG_ERROR( DbgInfo, "Could not retrieve net_device structure\n" );
450 /* Perform device cleanup */
452 free_irq( dev->irq, dev );
455 wl_pci_dma_free( pdev, dev->priv );
458 wl_device_dealloc( dev );
460 DBG_LEAVE( DbgInfo );
463 /*============================================================================*/
465 /*******************************************************************************
467 *******************************************************************************
471 * Called by wl_pci_probe() to begin a device's initialization process.
475 * pdev - a pointer to the device's pci_dev structure
480 * errno value otherwise
482 ******************************************************************************/
483 int wl_pci_setup( struct pci_dev *pdev )
486 struct net_device *dev = NULL;
487 struct wl_private *lp = NULL;
488 /*------------------------------------------------------------------------*/
490 DBG_ENTER( DbgInfo );
492 /* Make sure the pci_dev pointer passed in is valid */
494 DBG_ERROR( DbgInfo, "PCI subsys passed in an invalid pci_dev pointer\n" );
498 result = pci_enable_device( pdev );
500 DBG_ERROR( DbgInfo, "pci_enable_device() failed\n" );
501 DBG_LEAVE( DbgInfo );
505 /* We found our device! Let's register it with the system */
506 DBG_TRACE( DbgInfo, "Found our device, now registering\n" );
507 dev = wl_device_alloc( );
509 DBG_ERROR( DbgInfo, "Could not register device!!!\n" );
510 DBG_LEAVE( DbgInfo );
514 /* Make sure that space was allocated for our private adapter struct */
515 if( dev->priv == NULL ) {
516 DBG_ERROR( DbgInfo, "Private adapter struct was not allocated!!!\n" );
517 wl_device_dealloc(dev);
518 DBG_LEAVE( DbgInfo );
523 /* Allocate DMA Descriptors */
524 if( wl_pci_dma_alloc( pdev, dev->priv ) < 0 ) {
525 DBG_ERROR( DbgInfo, "Could not allocate DMA descriptor memory!!!\n" );
526 wl_device_dealloc(dev);
527 DBG_LEAVE( DbgInfo );
532 /* Register our private adapter structure with PCI */
533 pci_set_drvdata( pdev, dev );
535 /* Fill out bus specific information in the net_device struct */
536 dev->irq = pdev->irq;
537 SET_MODULE_OWNER( dev );
539 DBG_TRACE( DbgInfo, "Device Base Address: %#03lx\n", pdev->resource[0].start );
540 dev->base_addr = pdev->resource[0].start;
542 /* Initialize our device here */
543 if( !wl_adapter_insert( dev )) {
544 DBG_ERROR( DbgInfo, "wl_adapter_insert() FAILED!!!\n" );
545 wl_device_dealloc( dev );
546 DBG_LEAVE( DbgInfo );
550 /* Register our ISR */
551 DBG_TRACE( DbgInfo, "Registering ISR...\n" );
553 result = request_irq(dev->irq, wl_isr, SA_SHIRQ, dev->name, dev);
555 DBG_WARNING( DbgInfo, "Could not register ISR!!!\n" );
557 wl_device_dealloc(dev);
558 DBG_LEAVE( DbgInfo );
562 /* Make sure interrupts are enabled properly for CardBus */
565 if( lp->hcfCtx.IFB_BusType == CFG_NIC_BUS_TYPE_CARDBUS ||
566 lp->hcfCtx.IFB_BusType == CFG_NIC_BUS_TYPE_PCI ) {
567 DBG_TRACE( DbgInfo, "This is a PCI/CardBus card, enable interrupts\n" );
568 wl_pci_enable_cardbus_interrupts( pdev );
571 /* Enable bus mastering */
572 pci_set_master( pdev );
574 DBG_LEAVE( DbgInfo );
577 /*============================================================================*/
579 /*******************************************************************************
580 * wl_pci_enable_cardbus_interrupts()
581 *******************************************************************************
585 * Called by wl_pci_setup() to enable interrupts on a CardBus device. This
586 * is done by writing bit 15 to the function event mask register. This
587 * CardBus-specific register is located in BAR2 (counting from BAR0), in memory
588 * space at byte offset 1f4 (7f4 for WARP).
592 * pdev - a pointer to the device's pci_dev structure
598 ******************************************************************************/
599 void wl_pci_enable_cardbus_interrupts( struct pci_dev *pdev )
603 u32 func_evt_mask_reg;
604 void *mem_addr_kern = NULL;
605 /*------------------------------------------------------------------------*/
607 DBG_ENTER( DbgInfo );
609 /* Initialize to known bad values */
610 bar2_reg = 0xdeadbeef;
611 mem_addr_bus = 0xdeadbeef;
613 /* Read the BAR2 register; this register contains the base address of the
614 memory region where the function event mask register lives */
615 pci_read_config_dword( pdev, PCI_BASE_ADDRESS_2, &bar2_reg );
616 mem_addr_bus = bar2_reg & PCI_BASE_ADDRESS_MEM_MASK;
618 /* Once the base address is obtained, remap the memory region to kernel
619 space so we can retrieve the register */
620 mem_addr_kern = ioremap( mem_addr_bus, 0x200 );
623 #define REG_OFFSET 0x07F4
625 #define REG_OFFSET 0x01F4
630 /* Retrieve the functional event mask register, enable interrupts by
631 setting Bit 15, and write back the value */
632 func_evt_mask_reg = *(u32 *)( mem_addr_kern + REG_OFFSET );
633 func_evt_mask_reg |= BIT15;
634 *(u32 *)( mem_addr_kern + REG_OFFSET ) = func_evt_mask_reg;
636 /* Once complete, unmap the region and exit */
637 iounmap( mem_addr_kern );
639 DBG_LEAVE( DbgInfo );
641 } // wl_pci_enable_cardbus_interrupts
642 /*============================================================================*/
645 /*******************************************************************************
647 *******************************************************************************
651 * Allocates all resources needed for PCI/CardBus DMA operation
655 * pdev - a pointer to the device's pci_dev structure
656 * lp - the device's private adapter structure
661 * errno value otherwise
663 ******************************************************************************/
664 int wl_pci_dma_alloc( struct pci_dev *pdev, struct wl_private *lp )
668 /*------------------------------------------------------------------------*/
670 DBG_ENTER( DbgInfo );
672 // lp->dma.tx_rsc_ind = lp->dma.rx_rsc_ind = 0;
674 // /* Alloc for the Tx chain and its reclaim descriptor */
675 // for( i = 0; i < NUM_TX_DESC; i++ ) {
676 // status = wl_pci_dma_alloc_tx_packet( pdev, lp, &lp->dma.tx_packet[i] );
677 // if( status == 0 ) {
678 // DBG_PRINT( "lp->dma.tx_packet[%d] : 0x%p\n", i, lp->dma.tx_packet[i] );
679 // DBG_PRINT( "lp->dma.tx_packet[%d]->next_desc_addr : 0x%p\n", i, lp->dma.tx_packet[i]->next_desc_addr );
680 // lp->dma.tx_rsc_ind++;
682 // DBG_ERROR( DbgInfo, "Could not alloc DMA Tx Packet\n" );
686 // if( status == 0 ) {
687 // status = wl_pci_dma_alloc_desc( pdev, lp, &lp->dma.tx_reclaim_desc );
688 // DBG_PRINT( "lp->dma.tx_reclaim_desc: 0x%p\n", lp->dma.tx_reclaim_desc );
690 // /* Alloc for the Rx chain and its reclaim descriptor */
691 // if( status == 0 ) {
692 // for( i = 0; i < NUM_RX_DESC; i++ ) {
693 // status = wl_pci_dma_alloc_rx_packet( pdev, lp, &lp->dma.rx_packet[i] );
694 // if( status == 0 ) {
695 // DBG_PRINT( "lp->dma.rx_packet[%d] : 0x%p\n", i, lp->dma.rx_packet[i] );
696 // DBG_PRINT( "lp->dma.rx_packet[%d]->next_desc_addr : 0x%p\n", i, lp->dma.rx_packet[i]->next_desc_addr );
697 // lp->dma.rx_rsc_ind++;
699 // DBG_ERROR( DbgInfo, "Could not alloc DMA Rx Packet\n" );
704 // if( status == 0 ) {
705 // status = wl_pci_dma_alloc_desc( pdev, lp, &lp->dma.rx_reclaim_desc );
706 // DBG_PRINT( "lp->dma.rx_reclaim_desc: 0x%p\n", lp->dma.rx_reclaim_desc );
708 // /* Store status, as host should not call HCF functions if this fails */
709 // lp->dma.status = status; //;?all useages of dma.status have been commented out
710 // DBG_LEAVE( DbgInfo );
712 } // wl_pci_dma_alloc
713 /*============================================================================*/
715 /*******************************************************************************
717 *******************************************************************************
721 * Deallocated all resources needed for PCI/CardBus DMA operation
725 * pdev - a pointer to the device's pci_dev structure
726 * lp - the device's private adapter structure
731 * errno value otherwise
733 ******************************************************************************/
734 int wl_pci_dma_free( struct pci_dev *pdev, struct wl_private *lp )
738 /*------------------------------------------------------------------------*/
740 DBG_ENTER( DbgInfo );
742 /* Reclaim all Rx packets that were handed over to the HCF */
743 /* Do I need to do this? Before this free is called, I've already disabled
744 the port which will call wl_pci_dma_hcf_reclaim */
745 //if( lp->dma.status == 0 )
747 // wl_pci_dma_hcf_reclaim( lp );
750 /* Free everything needed for DMA Rx */
751 for( i = 0; i < NUM_RX_DESC; i++ ) {
752 if( lp->dma.rx_packet[i] ) {
753 status = wl_pci_dma_free_rx_packet( pdev, lp, &lp->dma.rx_packet[i] );
755 DBG_WARNING( DbgInfo, "Problem freeing Rx packet\n" );
759 lp->dma.rx_rsc_ind = 0;
761 if( lp->dma.rx_reclaim_desc ) {
762 status = wl_pci_dma_free_desc( pdev, lp, &lp->dma.rx_reclaim_desc );
764 DBG_WARNING( DbgInfo, "Problem freeing Rx reclaim descriptor\n" );
768 /* Free everything needed for DMA Tx */
769 for( i = 0; i < NUM_TX_DESC; i++ ) {
770 if( lp->dma.tx_packet[i] ) {
771 status = wl_pci_dma_free_tx_packet( pdev, lp, &lp->dma.tx_packet[i] );
773 DBG_WARNING( DbgInfo, "Problem freeing Tx packet\n" );
777 lp->dma.tx_rsc_ind = 0;
779 if( lp->dma.tx_reclaim_desc ) {
780 status = wl_pci_dma_free_desc( pdev, lp, &lp->dma.tx_reclaim_desc );
782 DBG_WARNING( DbgInfo, "Problem freeing Tx reclaim descriptor\n" );
786 DBG_LEAVE( DbgInfo );
790 /*============================================================================*/
792 /*******************************************************************************
793 * wl_pci_dma_alloc_tx_packet()
794 *******************************************************************************
798 * Allocates a single Tx packet, consisting of several descriptors and
799 * buffers. Data to transmit is first copied into the 'payload' buffer
800 * before being transmitted.
804 * pdev - a pointer to the device's pci_dev structure
805 * lp - the device's private adapter structure
806 * desc - a pointer which will reference the descriptor to be alloc'd.
811 * errno value otherwise
813 ******************************************************************************/
814 int wl_pci_dma_alloc_tx_packet( struct pci_dev *pdev, struct wl_private *lp,
818 // /*------------------------------------------------------------------------*/
820 // if( desc == NULL ) {
823 // if( status == 0 ) {
824 // status = wl_pci_dma_alloc_desc_and_buf( pdev, lp, desc,
825 // HCF_DMA_TX_BUF1_SIZE );
827 // if( status == 0 ) {
828 // status = wl_pci_dma_alloc_desc_and_buf( pdev, lp,
829 // &( (*desc)->next_desc_addr ),
830 // HCF_MAX_PACKET_SIZE );
833 // if( status == 0 ) {
834 // (*desc)->next_desc_phys_addr = (*desc)->next_desc_addr->desc_phys_addr;
837 } // wl_pci_dma_alloc_tx_packet
838 /*============================================================================*/
840 /*******************************************************************************
841 * wl_pci_dma_free_tx_packet()
842 *******************************************************************************
846 * Frees a single Tx packet, described in the corresponding alloc function.
850 * pdev - a pointer to the device's pci_dev structure
851 * lp - the device's private adapter structure
852 * desc - a pointer which will reference the descriptor to be alloc'd.
857 * errno value otherwise
859 ******************************************************************************/
860 int wl_pci_dma_free_tx_packet( struct pci_dev *pdev, struct wl_private *lp,
864 /*------------------------------------------------------------------------*/
866 if( *desc == NULL ) {
867 DBG_PRINT( "Null descriptor\n" );
870 //;?the "limited" NDIS strategy, assuming a frame consists ALWAYS out of 2
871 //descriptors, make this robust
872 if( status == 0 && (*desc)->next_desc_addr ) {
873 status = wl_pci_dma_free_desc_and_buf( pdev, lp, &(*desc)->next_desc_addr );
876 status = wl_pci_dma_free_desc_and_buf( pdev, lp, desc );
879 } // wl_pci_dma_free_tx_packet
880 /*============================================================================*/
882 /*******************************************************************************
883 * wl_pci_dma_alloc_rx_packet()
884 *******************************************************************************
888 * Allocates a single Rx packet, consisting of two descriptors and one
889 * contiguous buffer. The buffer starts with the hermes-specific header.
890 * One descriptor points at the start, the other at offset 0x3a of the
895 * pdev - a pointer to the device's pci_dev structure
896 * lp - the device's private adapter structure
897 * desc - a pointer which will reference the descriptor to be alloc'd.
902 * errno value otherwise
904 ******************************************************************************/
905 int wl_pci_dma_alloc_rx_packet( struct pci_dev *pdev, struct wl_private *lp,
910 /*------------------------------------------------------------------------*/
912 // if( desc == NULL ) {
915 // //;?the "limited" NDIS strategy, assuming a frame consists ALWAYS out of 2
916 // //descriptors, make this robust
917 // if( status == 0 ) {
918 // status = wl_pci_dma_alloc_desc( pdev, lp, desc );
920 // if( status == 0 ) {
921 // status = wl_pci_dma_alloc_buf( pdev, lp, *desc, HCF_MAX_PACKET_SIZE );
923 // if( status == 0 ) {
924 // status = wl_pci_dma_alloc_desc( pdev, lp, &p );
926 // if( status == 0 ) {
927 // /* Size of 1st descriptor becomes 0x3a bytes */
928 // SET_BUF_SIZE( *desc, HCF_DMA_RX_BUF1_SIZE );
930 // /* Make 2nd descriptor point at offset 0x3a of the buffer */
931 // SET_BUF_SIZE( p, ( HCF_MAX_PACKET_SIZE - HCF_DMA_RX_BUF1_SIZE ));
932 // p->buf_addr = (*desc)->buf_addr + HCF_DMA_RX_BUF1_SIZE;
933 // p->buf_phys_addr = (*desc)->buf_phys_addr + HCF_DMA_RX_BUF1_SIZE;
934 // p->next_desc_addr = NULL;
936 // /* Chain 2nd descriptor to 1st descriptor */
937 // (*desc)->next_desc_addr = p;
938 // (*desc)->next_desc_phys_addr = p->desc_phys_addr;
942 } // wl_pci_dma_alloc_rx_packet
943 /*============================================================================*/
945 /*******************************************************************************
946 * wl_pci_dma_free_rx_packet()
947 *******************************************************************************
951 * Frees a single Rx packet, described in the corresponding alloc function.
955 * pdev - a pointer to the device's pci_dev structure
956 * lp - the device's private adapter structure
957 * desc - a pointer which will reference the descriptor to be alloc'd.
962 * errno value otherwise
964 ******************************************************************************/
965 int wl_pci_dma_free_rx_packet( struct pci_dev *pdev, struct wl_private *lp,
970 /*------------------------------------------------------------------------*/
972 if( *desc == NULL ) {
976 p = (*desc)->next_desc_addr;
978 /* Free the 2nd descriptor */
981 p->buf_phys_addr = 0;
983 status = wl_pci_dma_free_desc( pdev, lp, &p );
987 /* Free the buffer and 1st descriptor */
989 SET_BUF_SIZE( *desc, HCF_MAX_PACKET_SIZE );
990 status = wl_pci_dma_free_desc_and_buf( pdev, lp, desc );
993 } // wl_pci_dma_free_rx_packet
994 /*============================================================================*/
996 /*******************************************************************************
997 * wl_pci_dma_alloc_desc_and_buf()
998 *******************************************************************************
1002 * Allocates a DMA descriptor and buffer, and associates them with one
1007 * pdev - a pointer to the device's pci_dev structure
1008 * lp - the device's private adapter structure
1009 * desc - a pointer which will reference the descriptor to be alloc'd
1014 * errno value otherwise
1016 ******************************************************************************/
1017 int wl_pci_dma_alloc_desc_and_buf( struct pci_dev *pdev, struct wl_private *lp,
1018 DESC_STRCT **desc, int size )
1021 /*------------------------------------------------------------------------*/
1023 // if( desc == NULL ) {
1024 // status = -EFAULT;
1026 // if( status == 0 ) {
1027 // status = wl_pci_dma_alloc_desc( pdev, lp, desc );
1029 // if( status == 0 ) {
1030 // status = wl_pci_dma_alloc_buf( pdev, lp, *desc, size );
1034 } // wl_pci_dma_alloc_desc_and_buf
1035 /*============================================================================*/
1037 /*******************************************************************************
1038 * wl_pci_dma_free_desc_and_buf()
1039 *******************************************************************************
1043 * Frees a DMA descriptor and associated buffer.
1047 * pdev - a pointer to the device's pci_dev structure
1048 * lp - the device's private adapter structure
1049 * desc - a pointer which will reference the descriptor to be alloc'd
1054 * errno value otherwise
1056 ******************************************************************************/
1057 int wl_pci_dma_free_desc_and_buf( struct pci_dev *pdev, struct wl_private *lp,
1061 /*------------------------------------------------------------------------*/
1063 if( desc == NULL ) {
1066 if( status == 0 && *desc == NULL ) {
1070 status = wl_pci_dma_free_buf( pdev, lp, *desc );
1073 status = wl_pci_dma_free_desc( pdev, lp, desc );
1077 } // wl_pci_dma_free_desc_and_buf
1078 /*============================================================================*/
1080 /*******************************************************************************
1081 * wl_pci_dma_alloc_desc()
1082 *******************************************************************************
1086 * Allocates one DMA descriptor in cache coherent memory.
1090 * pdev - a pointer to the device's pci_dev structure
1091 * lp - the device's private adapter structure
1096 * errno value otherwise
1098 ******************************************************************************/
1099 int wl_pci_dma_alloc_desc( struct pci_dev *pdev, struct wl_private *lp,
1104 // /*------------------------------------------------------------------------*/
1106 // DBG_ENTER( DbgInfo );
1108 // if( desc == NULL ) {
1109 // status = -EFAULT;
1111 // if( status == 0 ) {
1112 // *desc = pci_alloc_consistent( pdev, sizeof( DESC_STRCT ), &pa );
1114 // if( *desc == NULL ) {
1115 // DBG_ERROR( DbgInfo, "pci_alloc_consistent() failed\n" );
1116 // status = -ENOMEM;
1118 // memset( *desc, 0, sizeof( DESC_STRCT ));
1119 // (*desc)->desc_phys_addr = cpu_to_le32( pa );
1121 // DBG_LEAVE( DbgInfo );
1123 } // wl_pci_dma_alloc_desc
1124 /*============================================================================*/
1126 /*******************************************************************************
1127 * wl_pci_dma_free_desc()
1128 *******************************************************************************
1132 * Frees one DMA descriptor in cache coherent memory.
1136 * pdev - a pointer to the device's pci_dev structure
1137 * lp - the device's private adapter structure
1142 * errno value otherwise
1144 ******************************************************************************/
1145 int wl_pci_dma_free_desc( struct pci_dev *pdev, struct wl_private *lp,
1149 /*------------------------------------------------------------------------*/
1151 if( *desc == NULL ) {
1155 pci_free_consistent( pdev, sizeof( DESC_STRCT ), *desc,
1156 (*desc)->desc_phys_addr );
1160 } // wl_pci_dma_free_desc
1161 /*============================================================================*/
1163 /*******************************************************************************
1164 * wl_pci_dma_alloc_buf()
1165 *******************************************************************************
1169 * Allocates one DMA buffer in cache coherent memory, and associates a DMA
1170 * descriptor with this buffer.
1174 * pdev - a pointer to the device's pci_dev structure
1175 * lp - the device's private adapter structure
1180 * errno value otherwise
1182 ******************************************************************************/
1183 int wl_pci_dma_alloc_buf( struct pci_dev *pdev, struct wl_private *lp,
1184 DESC_STRCT *desc, int size )
1188 /*------------------------------------------------------------------------*/
1190 // DBG_ENTER( DbgInfo );
1192 // if( desc == NULL ) {
1193 // status = -EFAULT;
1195 // if( status == 0 && desc->buf_addr != NULL ) {
1196 // status = -EFAULT;
1198 // if( status == 0 ) {
1199 // desc->buf_addr = pci_alloc_consistent( pdev, size, &pa );
1201 // if( desc->buf_addr == NULL ) {
1202 // DBG_ERROR( DbgInfo, "pci_alloc_consistent() failed\n" );
1203 // status = -ENOMEM;
1205 // desc->buf_phys_addr = cpu_to_le32( pa );
1206 // SET_BUF_SIZE( desc, size );
1208 // DBG_LEAVE( DbgInfo );
1210 } // wl_pci_dma_alloc_buf
1211 /*============================================================================*/
1213 /*******************************************************************************
1214 * wl_pci_dma_free_buf()
1215 *******************************************************************************
1219 * Allocates one DMA buffer in cache coherent memory, and associates a DMA
1220 * descriptor with this buffer.
1224 * pdev - a pointer to the device's pci_dev structure
1225 * lp - the device's private adapter structure
1230 * errno value otherwise
1232 ******************************************************************************/
1233 int wl_pci_dma_free_buf( struct pci_dev *pdev, struct wl_private *lp,
1237 /*------------------------------------------------------------------------*/
1239 if( desc == NULL ) {
1242 if( status == 0 && desc->buf_addr == NULL ) {
1246 pci_free_consistent( pdev, GET_BUF_SIZE( desc ), desc->buf_addr,
1247 desc->buf_phys_addr );
1250 desc->buf_phys_addr = 0;
1251 SET_BUF_SIZE( desc, 0 );
1254 } // wl_pci_dma_free_buf
1255 /*============================================================================*/
1257 /*******************************************************************************
1258 * wl_pci_dma_hcf_supply()
1259 *******************************************************************************
1263 * Supply HCF with DMA-related resources. These consist of:
1264 * - buffers and descriptors for receive purposes
1265 * - one 'reclaim' descriptor for the transmit path, used to fulfill a
1266 * certain H25 DMA engine requirement
1267 * - one 'reclaim' descriptor for the receive path, used to fulfill a
1268 * certain H25 DMA engine requirement
1270 * This function is called at start-of-day or at re-initialization.
1274 * lp - the device's private adapter structure
1279 * errno value otherwise
1281 ******************************************************************************/
1282 void wl_pci_dma_hcf_supply( struct wl_private *lp )
1285 /*------------------------------------------------------------------------*/
1287 DBG_ENTER( DbgInfo );
1289 //if( lp->dma.status == 0 );
1291 /* Hand over the Rx/Tx reclaim descriptors to the HCF */
1292 if( lp->dma.tx_reclaim_desc ) {
1293 DBG_PRINT( "lp->dma.tx_reclaim_desc: 0x%p\n", lp->dma.tx_reclaim_desc );
1294 hcf_dma_tx_put( &lp->hcfCtx, lp->dma.tx_reclaim_desc, 0 );
1295 lp->dma.tx_reclaim_desc = NULL;
1296 DBG_PRINT( "lp->dma.tx_reclaim_desc: 0x%p\n", lp->dma.tx_reclaim_desc );
1298 if( lp->dma.rx_reclaim_desc ) {
1299 DBG_PRINT( "lp->dma.rx_reclaim_desc: 0x%p\n", lp->dma.rx_reclaim_desc );
1300 hcf_dma_rx_put( &lp->hcfCtx, lp->dma.rx_reclaim_desc );
1301 lp->dma.rx_reclaim_desc = NULL;
1302 DBG_PRINT( "lp->dma.rx_reclaim_desc: 0x%p\n", lp->dma.rx_reclaim_desc );
1304 /* Hand over the Rx descriptor chain to the HCF */
1305 for( i = 0; i < NUM_RX_DESC; i++ ) {
1306 DBG_PRINT( "lp->dma.rx_packet[%d]: 0x%p\n", i, lp->dma.rx_packet[i] );
1307 hcf_dma_rx_put( &lp->hcfCtx, lp->dma.rx_packet[i] );
1308 lp->dma.rx_packet[i] = NULL;
1309 DBG_PRINT( "lp->dma.rx_packet[%d]: 0x%p\n", i, lp->dma.rx_packet[i] );
1313 DBG_LEAVE( DbgInfo );
1315 } // wl_pci_dma_hcf_supply
1316 /*============================================================================*/
1318 /*******************************************************************************
1319 * wl_pci_dma_hcf_reclaim()
1320 *******************************************************************************
1324 * Return DMA-related resources from the HCF. These consist of:
1325 * - buffers and descriptors for receive purposes
1326 * - buffers and descriptors for transmit purposes
1327 * - one 'reclaim' descriptor for the transmit path, used to fulfill a
1328 * certain H25 DMA engine requirement
1329 * - one 'reclaim' descriptor for the receive path, used to fulfill a
1330 * certain H25 DMA engine requirement
1332 * This function is called at end-of-day or at re-initialization.
1336 * lp - the device's private adapter structure
1341 * errno value otherwise
1343 ******************************************************************************/
1344 void wl_pci_dma_hcf_reclaim( struct wl_private *lp )
1347 /*------------------------------------------------------------------------*/
1349 DBG_ENTER( DbgInfo );
1351 wl_pci_dma_hcf_reclaim_rx( lp );
1352 for( i = 0; i < NUM_RX_DESC; i++ ) {
1353 DBG_PRINT( "rx_packet[%d] 0x%p\n", i, lp->dma.rx_packet[i] );
1354 // if( lp->dma.rx_packet[i] == NULL ) {
1355 // DBG_PRINT( "wl_pci_dma_hcf_reclaim: rx_packet[%d] NULL\n", i );
1359 wl_pci_dma_hcf_reclaim_tx( lp );
1360 for( i = 0; i < NUM_TX_DESC; i++ ) {
1361 DBG_PRINT( "tx_packet[%d] 0x%p\n", i, lp->dma.tx_packet[i] );
1362 // if( lp->dma.tx_packet[i] == NULL ) {
1363 // DBG_PRINT( "wl_pci_dma_hcf_reclaim: tx_packet[%d] NULL\n", i );
1367 DBG_LEAVE( DbgInfo );
1369 } // wl_pci_dma_hcf_reclaim
1370 /*============================================================================*/
1372 /*******************************************************************************
1373 * wl_pci_dma_hcf_reclaim_rx()
1374 *******************************************************************************
1378 * Reclaim Rx packets that have already been processed by the HCF.
1382 * lp - the device's private adapter structure
1387 * errno value otherwise
1389 ******************************************************************************/
1390 void wl_pci_dma_hcf_reclaim_rx( struct wl_private *lp )
1394 /*------------------------------------------------------------------------*/
1396 DBG_ENTER( DbgInfo );
1398 //if( lp->dma.status == 0 )
1400 while ( ( p = hcf_dma_rx_get( &lp->hcfCtx ) ) != NULL ) {
1401 if( p && p->buf_addr == NULL ) {
1402 /* A reclaim descriptor is being given back by the HCF. Reclaim
1403 descriptors have a NULL buf_addr */
1404 lp->dma.rx_reclaim_desc = p;
1405 DBG_PRINT( "reclaim_descriptor: 0x%p\n", p );
1408 for( i = 0; i < NUM_RX_DESC; i++ ) {
1409 if( lp->dma.rx_packet[i] == NULL ) {
1413 /* An Rx buffer descriptor is being given back by the HCF */
1414 lp->dma.rx_packet[i] = p;
1415 lp->dma.rx_rsc_ind++;
1416 DBG_PRINT( "rx_packet[%d] 0x%p\n", i, lp->dma.rx_packet[i] );
1419 DBG_LEAVE( DbgInfo );
1420 } // wl_pci_dma_hcf_reclaim_rx
1421 /*============================================================================*/
1423 /*******************************************************************************
1424 * wl_pci_dma_get_tx_packet()
1425 *******************************************************************************
1429 * Obtains a Tx descriptor from the chain to use for Tx.
1433 * lp - a pointer to the device's wl_private structure.
1437 * A pointer to the retrieved descriptor
1439 ******************************************************************************/
1440 DESC_STRCT * wl_pci_dma_get_tx_packet( struct wl_private *lp )
1443 DESC_STRCT *desc = NULL;
1444 /*------------------------------------------------------------------------*/
1446 for( i = 0; i < NUM_TX_DESC; i++ ) {
1447 if( lp->dma.tx_packet[i] ) {
1452 if( i != NUM_TX_DESC ) {
1453 desc = lp->dma.tx_packet[i];
1455 lp->dma.tx_packet[i] = NULL;
1456 lp->dma.tx_rsc_ind--;
1458 memset( desc->buf_addr, 0, HCF_DMA_TX_BUF1_SIZE );
1462 } // wl_pci_dma_get_tx_packet
1463 /*============================================================================*/
1465 /*******************************************************************************
1466 * wl_pci_dma_put_tx_packet()
1467 *******************************************************************************
1471 * Returns a Tx descriptor to the chain.
1475 * lp - a pointer to the device's wl_private structure.
1476 * desc - a pointer to the descriptor to return.
1482 ******************************************************************************/
1483 void wl_pci_dma_put_tx_packet( struct wl_private *lp, DESC_STRCT *desc )
1486 /*------------------------------------------------------------------------*/
1488 for( i = 0; i < NUM_TX_DESC; i++ ) {
1489 if( lp->dma.tx_packet[i] == NULL ) {
1494 if( i != NUM_TX_DESC ) {
1495 lp->dma.tx_packet[i] = desc;
1496 lp->dma.tx_rsc_ind++;
1498 } // wl_pci_dma_put_tx_packet
1499 /*============================================================================*/
1501 /*******************************************************************************
1502 * wl_pci_dma_hcf_reclaim_tx()
1503 *******************************************************************************
1507 * Reclaim Tx packets that have either been processed by the HCF due to a
1508 * port disable or a Tx completion.
1512 * lp - the device's private adapter structure
1517 * errno value otherwise
1519 ******************************************************************************/
1520 void wl_pci_dma_hcf_reclaim_tx( struct wl_private *lp )
1524 /*------------------------------------------------------------------------*/
1526 DBG_ENTER( DbgInfo );
1528 //if( lp->dma.status == 0 )
1530 while ( ( p = hcf_dma_tx_get( &lp->hcfCtx ) ) != NULL ) {
1532 if( p != NULL && p->buf_addr == NULL ) {
1533 /* A Reclaim descriptor is being given back by the HCF. Reclaim
1534 descriptors have a NULL buf_addr */
1535 lp->dma.tx_reclaim_desc = p;
1536 DBG_PRINT( "reclaim_descriptor: 0x%p\n", p );
1539 for( i = 0; i < NUM_TX_DESC; i++ ) {
1540 if( lp->dma.tx_packet[i] == NULL ) {
1544 /* An Rx buffer descriptor is being given back by the HCF */
1545 lp->dma.tx_packet[i] = p;
1546 lp->dma.tx_rsc_ind++;
1547 DBG_PRINT( "tx_packet[%d] 0x%p\n", i, lp->dma.tx_packet[i] );
1551 if( lp->netif_queue_on == FALSE ) {
1552 netif_wake_queue( lp->dev );
1553 WL_WDS_NETIF_WAKE_QUEUE( lp );
1554 lp->netif_queue_on = TRUE;
1556 DBG_LEAVE( DbgInfo );
1558 } // wl_pci_dma_hcf_reclaim_tx
1559 /*============================================================================*/
1560 #endif // ENABLE_DMA