LCOV - code coverage report
Current view: top level - dev/cardbus - if_ath_cardbus.c (source / functions) Hit Total Coverage
Test: 6.4 Lines: 0 95 0.0 %
Date: 2018-10-19 03:25:38 Functions: 0 7 0.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /*      $OpenBSD: if_ath_cardbus.c,v 1.19 2015/11/24 17:11:39 mpi Exp $   */
       2             : /*      $NetBSD: if_ath_cardbus.c,v 1.4 2004/08/02 19:14:28 mycroft Exp $ */
       3             : 
       4             : /*
       5             :  * Copyright (c) 2003
       6             :  *      Ichiro FUKUHARA <ichiro@ichiro.org>.
       7             :  * All rights reserved.
       8             :  *
       9             :  * Redistribution and use in source and binary forms, with or without
      10             :  * modification, are permitted provided that the following conditions
      11             :  * are met:
      12             :  * 1. Redistributions of source code must retain the above copyright
      13             :  *    notice, this list of conditions and the following disclaimer.
      14             :  * 2. Redistributions in binary form must reproduce the above copyright
      15             :  *    notice, this list of conditions and the following disclaimer in the
      16             :  *    documentation and/or other materials provided with the distribution.
      17             :  * 3. All advertising materials mentioning features or use of this software
      18             :  *    must display the following acknowledgement:
      19             :  *      This product includes software developed by Ichiro FUKUHARA.
      20             :  * 4. The name of the company nor the name of the author may be used to
      21             :  *    endorse or promote products derived from this software without specific
      22             :  *    prior written permission.
      23             :  *
      24             :  * THIS SOFTWARE IS PROVIDED BY ICHIRO FUKUHARA ``AS IS'' AND ANY EXPRESS OR
      25             :  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
      26             :  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
      27             :  * IN NO EVENT SHALL ICHIRO FUKUHARA OR THE VOICES IN HIS HEAD BE LIABLE FOR
      28             :  * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
      29             :  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
      30             :  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
      31             :  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
      32             :  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
      33             :  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
      34             :  * SUCH DAMAGE.
      35             :  */
      36             : 
      37             : /*
      38             :  * CardBus bus front-end for the AR5001 Wireless LAN 802.11a/b/g CardBus.
      39             :  */
      40             : 
      41             : #include <sys/param.h>
      42             : #include <sys/systm.h> 
      43             : #include <sys/mbuf.h>   
      44             : #include <sys/malloc.h>
      45             : #include <sys/kernel.h>
      46             : #include <sys/socket.h>
      47             : #include <sys/ioctl.h>
      48             : #include <sys/errno.h>
      49             : #include <sys/device.h>
      50             : #include <sys/gpio.h>
      51             : #include <sys/endian.h>
      52             :  
      53             : #include <net/if.h>
      54             : #include <net/if_media.h>
      55             : 
      56             : #include <netinet/in.h> 
      57             : #include <netinet/if_ether.h>
      58             : 
      59             : #include <net80211/ieee80211_var.h>
      60             : #include <net80211/ieee80211_rssadapt.h>
      61             : 
      62             : #include <machine/bus.h>
      63             : #include <machine/intr.h>
      64             : 
      65             : #include <dev/gpio/gpiovar.h>
      66             : 
      67             : #include <dev/pci/pcivar.h>
      68             : #include <dev/pci/pcireg.h>
      69             : #include <dev/pci/pcidevs.h>
      70             : 
      71             : #include <dev/cardbus/cardbusvar.h>
      72             : 
      73             : #include <dev/ic/athvar.h>
      74             : 
      75             : /*
      76             :  * PCI configuration space registers
      77             :  */
      78             : #define ATH_PCI_MMBA            0x10    /* memory mapped base */
      79             : 
      80             : struct ath_cardbus_softc {
      81             :         struct ath_softc        sc_ath;
      82             : 
      83             :         /* CardBus-specific goo. */
      84             :         void    *sc_ih;                 /* interrupt handle */
      85             :         cardbus_devfunc_t sc_ct;        /* our CardBus devfuncs */
      86             :         pcitag_t sc_tag;                /* our CardBus tag */
      87             : 
      88             :         pcireg_t sc_bar_val;            /* value of the BAR */
      89             : 
      90             :         int     sc_intrline;            /* interrupt line */
      91             :         pci_chipset_tag_t sc_pc;
      92             : };
      93             : 
      94             : int     ath_cardbus_match(struct device *, void *, void *);
      95             : void    ath_cardbus_attach(struct device *, struct device *, void *);
      96             : int     ath_cardbus_detach(struct device *, int);
      97             : 
      98             : struct cfattach ath_cardbus_ca = {
      99             :         sizeof(struct ath_cardbus_softc),
     100             :         ath_cardbus_match,
     101             :         ath_cardbus_attach,
     102             :         ath_cardbus_detach
     103             : };
     104             : 
     105             : 
     106             : void    ath_cardbus_setup(struct ath_cardbus_softc *);
     107             : 
     108             : int     ath_cardbus_enable(struct ath_softc *);
     109             : void    ath_cardbus_disable(struct ath_softc *);
     110             : void    ath_cardbus_power(struct ath_softc *, int);
     111             : 
     112             : int
     113           0 : ath_cardbus_match(struct device *parent, void *match, void *aux)
     114             : {
     115           0 :         struct cardbus_attach_args *ca = aux;
     116             :         const char* devname;
     117             : 
     118           0 :         devname = ath_hal_probe(PCI_VENDOR(ca->ca_id),
     119           0 :                                 PCI_PRODUCT(ca->ca_id));
     120             : 
     121           0 :         if (devname)
     122           0 :                 return (1);
     123             : 
     124           0 :         return (0);
     125           0 : }
     126             : 
     127             : void
     128           0 : ath_cardbus_attach(struct device *parent, struct device *self, void *aux)
     129             : {
     130           0 :         struct ath_cardbus_softc *csc = (void *)self;
     131           0 :         struct ath_softc *sc = &csc->sc_ath;
     132           0 :         struct cardbus_attach_args *ca = aux;
     133           0 :         cardbus_devfunc_t ct = ca->ca_ct;
     134           0 :         bus_addr_t adr;
     135             : 
     136           0 :         sc->sc_dmat = ca->ca_dmat;
     137           0 :         csc->sc_ct = ct;
     138           0 :         csc->sc_tag = ca->ca_tag;
     139           0 :         csc->sc_pc = ca->ca_pc;
     140             : 
     141             :         /*
     142             :          * Power management hooks.
     143             :          */
     144           0 :         sc->sc_enable = ath_cardbus_enable;
     145           0 :         sc->sc_disable = ath_cardbus_disable;
     146           0 :         sc->sc_power = ath_cardbus_power;
     147             : 
     148             :         /*
     149             :          * Map the device.
     150             :          */
     151           0 :         if (Cardbus_mapreg_map(ct, ATH_PCI_MMBA, PCI_MAPREG_TYPE_MEM, 0,
     152           0 :             &sc->sc_st, &sc->sc_sh, &adr, &sc->sc_ss) == 0) {
     153           0 :                 csc->sc_bar_val = adr | PCI_MAPREG_TYPE_MEM;
     154             :         }
     155             : 
     156             :         else {
     157           0 :                 printf(": unable to map device registers\n");
     158           0 :                 return;
     159             :         }
     160             : 
     161             :         /*
     162             :          * Set up the PCI configuration registers.
     163             :          */
     164           0 :         ath_cardbus_setup(csc);
     165             : 
     166             :         /* Remember which interrupt line. */
     167           0 :         csc->sc_intrline = ca->ca_intrline;
     168             : 
     169           0 :         printf(": irq %d\n", csc->sc_intrline);
     170             : 
     171             :         /*
     172             :          * Finish off the attach.
     173             :          */
     174           0 :         ath_attach(PCI_PRODUCT(ca->ca_id), sc);
     175             : 
     176             :         /*
     177             :          * Power down the socket.
     178             :          */
     179           0 :         Cardbus_function_disable(csc->sc_ct);
     180           0 : }
     181             : 
     182             : int
     183           0 : ath_cardbus_detach(struct device *self, int flags)
     184             : {
     185           0 :         struct ath_cardbus_softc *csc = (void *)self;
     186           0 :         struct ath_softc *sc = &csc->sc_ath;
     187           0 :         struct cardbus_devfunc *ct = csc->sc_ct;
     188             :         int rv;
     189             : 
     190             : #if defined(DIAGNOSTIC)
     191           0 :         if (ct == NULL)
     192           0 :                 panic("%s: data structure lacks", sc->sc_dev.dv_xname);
     193             : #endif
     194             : 
     195           0 :         rv = ath_detach(sc, flags);
     196           0 :         if (rv)
     197           0 :                 return (rv);
     198             : 
     199             :         /*
     200             :          * Unhook the interrupt handler.
     201             :          */
     202           0 :         if (csc->sc_ih != NULL) {
     203           0 :                 cardbus_intr_disestablish(ct->ct_cc, ct->ct_cf, csc->sc_ih);
     204           0 :                 csc->sc_ih = NULL;
     205           0 :         }
     206             : 
     207             :         /*
     208             :          * Release bus space and close window.
     209             :          */
     210           0 :         Cardbus_mapreg_unmap(ct, ATH_PCI_MMBA,
     211             :                     sc->sc_st, sc->sc_sh, sc->sc_ss);
     212             : 
     213           0 :         return (0);
     214           0 : }
     215             : 
     216             : int
     217           0 : ath_cardbus_enable(struct ath_softc *sc)
     218             : {
     219           0 :         struct ath_cardbus_softc *csc = (void *) sc;
     220           0 :         cardbus_devfunc_t ct = csc->sc_ct;
     221           0 :         cardbus_chipset_tag_t cc = ct->ct_cc;
     222           0 :         cardbus_function_tag_t cf = ct->ct_cf;
     223             : 
     224             :         /*
     225             :          * Power on the socket.
     226             :          */
     227           0 :         Cardbus_function_enable(ct);
     228             : 
     229             :         /*
     230             :          * Set up the PCI configuration registers.
     231             :          */
     232           0 :         ath_cardbus_setup(csc);
     233             : 
     234             :         /*
     235             :          * Map and establish the interrupt.
     236             :          */
     237           0 :         csc->sc_ih = cardbus_intr_establish(cc, cf, csc->sc_intrline, IPL_NET,
     238           0 :             ath_intr, sc, sc->sc_dev.dv_xname);
     239           0 :         if (csc->sc_ih == NULL) {
     240           0 :                 printf(": unable to establish irq %d\n",
     241           0 :                        csc->sc_intrline);
     242           0 :                 Cardbus_function_disable(csc->sc_ct);
     243           0 :                 return (1);
     244             :         }
     245           0 :         return (0);
     246           0 : }
     247             : 
     248             : void
     249           0 : ath_cardbus_disable(struct ath_softc *sc)
     250             : {
     251           0 :         struct ath_cardbus_softc *csc = (void *) sc;
     252           0 :         cardbus_devfunc_t ct = csc->sc_ct;
     253           0 :         cardbus_chipset_tag_t cc = ct->ct_cc;
     254           0 :         cardbus_function_tag_t cf = ct->ct_cf;
     255             : 
     256             :         /* Unhook the interrupt handler. */
     257           0 :         cardbus_intr_disestablish(cc, cf, csc->sc_ih);
     258           0 :         csc->sc_ih = NULL;
     259             : 
     260             :         /* Power down the socket. */
     261           0 :         Cardbus_function_disable(ct);
     262           0 : }
     263             : 
     264             : void
     265           0 : ath_cardbus_power(struct ath_softc *sc, int why)
     266             : {
     267           0 :         if (why == DVACT_RESUME)
     268           0 :                 ath_enable(sc);
     269           0 : }
     270             : 
     271             : void
     272           0 : ath_cardbus_setup(struct ath_cardbus_softc *csc)
     273             : {
     274           0 :         cardbus_devfunc_t ct = csc->sc_ct;
     275           0 :         cardbus_chipset_tag_t cc = ct->ct_cc;
     276           0 :         pci_chipset_tag_t pc = csc->sc_pc;
     277             :         pcireg_t reg;
     278             : 
     279             : #ifdef notyet
     280             :         (void)cardbus_setpowerstate(sc->sc_dev.dv_xname, ct, csc->sc_tag,
     281             :             PCI_PWR_D0);
     282             : #endif
     283             : 
     284             :         /* Program the BAR. */
     285           0 :         pci_conf_write(pc, csc->sc_tag, ATH_PCI_MMBA,
     286           0 :             csc->sc_bar_val);
     287             : 
     288             :         /* Make sure the right access type is on the CardBus bridge. */
     289           0 :         (*ct->ct_cf->cardbus_ctrl)(cc, CARDBUS_MEM_ENABLE);
     290           0 :         (*ct->ct_cf->cardbus_ctrl)(cc, CARDBUS_BM_ENABLE);
     291             : 
     292             :         /* Enable the appropriate bits in the PCI CSR. */
     293           0 :         reg = pci_conf_read(pc, csc->sc_tag,
     294             :             PCI_COMMAND_STATUS_REG);
     295           0 :         reg |= PCI_COMMAND_MASTER_ENABLE | PCI_COMMAND_MEM_ENABLE;
     296           0 :         pci_conf_write(pc, csc->sc_tag, PCI_COMMAND_STATUS_REG,
     297             :             reg);
     298             : 
     299             :         /*
     300             :          * Make sure the latency timer is set to some reasonable
     301             :          * value.
     302             :          */
     303           0 :         reg = pci_conf_read(pc, csc->sc_tag, PCI_BHLC_REG);
     304           0 :         if (PCI_LATTIMER(reg) < 0x20) {
     305           0 :                 reg &= ~(PCI_LATTIMER_MASK << PCI_LATTIMER_SHIFT);
     306           0 :                 reg |= (0x20 << PCI_LATTIMER_SHIFT);
     307           0 :                 pci_conf_write(pc, csc->sc_tag, PCI_BHLC_REG, reg);
     308           0 :         }
     309           0 : }

Generated by: LCOV version 1.13