xref: /dflybsd-src/sys/dev/netif/ral/if_ral_pci.c (revision f354e0e64689159f00d07d7caa59dab0cea92fcb)
1feb94d24SRui Paulo /*-
25fdff524SSepherosa Ziehau  * Copyright (c) 2005, 2006
35fdff524SSepherosa Ziehau  *	Damien Bergamini <damien.bergamini@free.fr>
45fdff524SSepherosa Ziehau  *
55fdff524SSepherosa Ziehau  * Permission to use, copy, modify, and distribute this software for any
65fdff524SSepherosa Ziehau  * purpose with or without fee is hereby granted, provided that the above
75fdff524SSepherosa Ziehau  * copyright notice and this permission notice appear in all copies.
85fdff524SSepherosa Ziehau  *
95fdff524SSepherosa Ziehau  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
105fdff524SSepherosa Ziehau  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
115fdff524SSepherosa Ziehau  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
125fdff524SSepherosa Ziehau  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
135fdff524SSepherosa Ziehau  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
145fdff524SSepherosa Ziehau  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
155fdff524SSepherosa Ziehau  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
165fdff524SSepherosa Ziehau  */
175fdff524SSepherosa Ziehau 
1891b30d50SMatthew Dillon #include <sys/cdefs.h>
1991b30d50SMatthew Dillon __FBSDID("$FreeBSD$");
20feb94d24SRui Paulo 
215fdff524SSepherosa Ziehau /*
225fdff524SSepherosa Ziehau  * PCI/Cardbus front-end for the Ralink RT2560/RT2561/RT2561S/RT2661 driver.
235fdff524SSepherosa Ziehau  */
245fdff524SSepherosa Ziehau 
255fdff524SSepherosa Ziehau #include <sys/param.h>
265fdff524SSepherosa Ziehau #include <sys/systm.h>
275fdff524SSepherosa Ziehau #include <sys/bus.h>
2891b30d50SMatthew Dillon #include <sys/kernel.h>
2991b30d50SMatthew Dillon #include <sys/lock.h>
3091b30d50SMatthew Dillon #include <sys/malloc.h>
3191b30d50SMatthew Dillon #include <sys/mbuf.h>
3291b30d50SMatthew Dillon #include <sys/module.h>
33feb94d24SRui Paulo #include <sys/rman.h>
3491b30d50SMatthew Dillon #include <sys/socket.h>
35feb94d24SRui Paulo 
3693d249f7SMatthew Dillon #if defined(__DragonFly__)
3793d249f7SMatthew Dillon /* empty */
3893d249f7SMatthew Dillon #else
3991b30d50SMatthew Dillon #include <machine/bus.h>
4091b30d50SMatthew Dillon #include <machine/resource.h>
4193d249f7SMatthew Dillon #endif
4291b30d50SMatthew Dillon 
435fdff524SSepherosa Ziehau #include <net/ethernet.h>
4491b30d50SMatthew Dillon #include <net/if.h>
45*bff82488SAaron LI #include <net/if_var.h>
465fdff524SSepherosa Ziehau #include <net/if_media.h>
4791b30d50SMatthew Dillon #include <net/route.h>
485fdff524SSepherosa Ziehau 
4993d249f7SMatthew Dillon #include <netproto/802_11/ieee80211_var.h>
5093d249f7SMatthew Dillon #include <netproto/802_11/ieee80211_radiotap.h>
515fdff524SSepherosa Ziehau 
5293d249f7SMatthew Dillon #include <bus/pci/pcireg.h>
5393d249f7SMatthew Dillon #include <bus/pci/pcivar.h>
545fdff524SSepherosa Ziehau 
5593d249f7SMatthew Dillon #include <dev/netif/ral/rt2560var.h>
5693d249f7SMatthew Dillon #include <dev/netif/ral/rt2661var.h>
5793d249f7SMatthew Dillon #include <dev/netif/ral/rt2860var.h>
585fdff524SSepherosa Ziehau 
59feb94d24SRui Paulo MODULE_DEPEND(ral, pci, 1, 1, 1);
60feb94d24SRui Paulo MODULE_DEPEND(ral, firmware, 1, 1, 1);
61feb94d24SRui Paulo MODULE_DEPEND(ral, wlan, 1, 1, 1);
62feb94d24SRui Paulo MODULE_DEPEND(ral, wlan_amrr, 1, 1, 1);
63feb94d24SRui Paulo 
6491b30d50SMatthew Dillon static int ral_msi_disable;
6591b30d50SMatthew Dillon TUNABLE_INT("hw.ral.msi_disable", &ral_msi_disable);
6691b30d50SMatthew Dillon 
67feb94d24SRui Paulo struct ral_pci_ident {
68feb94d24SRui Paulo 	uint16_t	vendor;
69feb94d24SRui Paulo 	uint16_t	device;
70feb94d24SRui Paulo 	const char	*name;
71feb94d24SRui Paulo };
72feb94d24SRui Paulo 
73feb94d24SRui Paulo static const struct ral_pci_ident ral_pci_ids[] = {
7491b30d50SMatthew Dillon 	{ 0x1432, 0x7708, "Edimax RT2860" },
7591b30d50SMatthew Dillon 	{ 0x1432, 0x7711, "Edimax RT3591" },
7691b30d50SMatthew Dillon 	{ 0x1432, 0x7722, "Edimax RT3591" },
7791b30d50SMatthew Dillon 	{ 0x1432, 0x7727, "Edimax RT2860" },
7891b30d50SMatthew Dillon 	{ 0x1432, 0x7728, "Edimax RT2860" },
7991b30d50SMatthew Dillon 	{ 0x1432, 0x7738, "Edimax RT2860" },
8091b30d50SMatthew Dillon 	{ 0x1432, 0x7748, "Edimax RT2860" },
8191b30d50SMatthew Dillon 	{ 0x1432, 0x7758, "Edimax RT2860" },
8291b30d50SMatthew Dillon 	{ 0x1432, 0x7768, "Edimax RT2860" },
8391b30d50SMatthew Dillon 	{ 0x1462, 0x891a, "MSI RT3090" },
8491b30d50SMatthew Dillon 	{ 0x1814, 0x0201, "Ralink Technology RT2560" },
8591b30d50SMatthew Dillon 	{ 0x1814, 0x0301, "Ralink Technology RT2561S" },
8691b30d50SMatthew Dillon 	{ 0x1814, 0x0302, "Ralink Technology RT2561" },
8791b30d50SMatthew Dillon 	{ 0x1814, 0x0401, "Ralink Technology RT2661" },
8891b30d50SMatthew Dillon 	{ 0x1814, 0x0601, "Ralink Technology RT2860" },
8991b30d50SMatthew Dillon 	{ 0x1814, 0x0681, "Ralink Technology RT2890" },
9091b30d50SMatthew Dillon 	{ 0x1814, 0x0701, "Ralink Technology RT2760" },
9191b30d50SMatthew Dillon 	{ 0x1814, 0x0781, "Ralink Technology RT2790" },
9291b30d50SMatthew Dillon 	{ 0x1814, 0x3060, "Ralink Technology RT3060" },
9391b30d50SMatthew Dillon 	{ 0x1814, 0x3062, "Ralink Technology RT3062" },
9491b30d50SMatthew Dillon 	{ 0x1814, 0x3090, "Ralink Technology RT3090" },
9591b30d50SMatthew Dillon 	{ 0x1814, 0x3091, "Ralink Technology RT3091" },
9691b30d50SMatthew Dillon 	{ 0x1814, 0x3092, "Ralink Technology RT3092" },
9791b30d50SMatthew Dillon 	{ 0x1814, 0x3390, "Ralink Technology RT3390" },
9891b30d50SMatthew Dillon 	{ 0x1814, 0x3562, "Ralink Technology RT3562" },
9991b30d50SMatthew Dillon 	{ 0x1814, 0x3592, "Ralink Technology RT3592" },
10091b30d50SMatthew Dillon 	{ 0x1814, 0x3593, "Ralink Technology RT3593" },
10191b30d50SMatthew Dillon 	{ 0x1814, 0x5360, "Ralink Technology RT5390" },
10291b30d50SMatthew Dillon 	{ 0x1814, 0x5362, "Ralink Technology RT5392" },
10391b30d50SMatthew Dillon 	{ 0x1814, 0x5390, "Ralink Technology RT5390" },
10491b30d50SMatthew Dillon 	{ 0x1814, 0x5392, "Ralink Technology RT5392" },
10591b30d50SMatthew Dillon 	{ 0x1814, 0x539a, "Ralink Technology RT5390" },
10691b30d50SMatthew Dillon 	{ 0x1814, 0x539f, "Ralink Technology RT5390" },
10791b30d50SMatthew Dillon 	{ 0x1a3b, 0x1059, "AWT RT2890" },
108feb94d24SRui Paulo 	{ 0, 0, NULL }
109feb94d24SRui Paulo };
110feb94d24SRui Paulo 
11191b30d50SMatthew Dillon static const struct ral_opns {
1125fdff524SSepherosa Ziehau 	int	(*attach)(device_t, int);
1135fdff524SSepherosa Ziehau 	int	(*detach)(void *);
1145fdff524SSepherosa Ziehau 	void	(*shutdown)(void *);
1155fdff524SSepherosa Ziehau 	void	(*suspend)(void *);
1165fdff524SSepherosa Ziehau 	void	(*resume)(void *);
117feb94d24SRui Paulo 	void	(*intr)(void *);
1185fdff524SSepherosa Ziehau 
119feb94d24SRui Paulo }  ral_rt2560_opns = {
120feb94d24SRui Paulo 	rt2560_attach,
121feb94d24SRui Paulo 	rt2560_detach,
122feb94d24SRui Paulo 	rt2560_stop,
123feb94d24SRui Paulo 	rt2560_stop,
124feb94d24SRui Paulo 	rt2560_resume,
125feb94d24SRui Paulo 	rt2560_intr
1265fdff524SSepherosa Ziehau 
127feb94d24SRui Paulo }, ral_rt2661_opns = {
128feb94d24SRui Paulo 	rt2661_attach,
129feb94d24SRui Paulo 	rt2661_detach,
130feb94d24SRui Paulo 	rt2661_shutdown,
131feb94d24SRui Paulo 	rt2661_suspend,
132feb94d24SRui Paulo 	rt2661_resume,
133feb94d24SRui Paulo 	rt2661_intr
13476c21ea3SSascha Wildner }, ral_rt2860_opns = {
13576c21ea3SSascha Wildner 	rt2860_attach,
13676c21ea3SSascha Wildner 	rt2860_detach,
13776c21ea3SSascha Wildner 	rt2860_shutdown,
13876c21ea3SSascha Wildner 	rt2860_suspend,
13976c21ea3SSascha Wildner 	rt2860_resume,
14076c21ea3SSascha Wildner 	rt2860_intr
1415fdff524SSepherosa Ziehau };
1425fdff524SSepherosa Ziehau 
1435fdff524SSepherosa Ziehau struct ral_pci_softc {
1445fdff524SSepherosa Ziehau 	union {
1455fdff524SSepherosa Ziehau 		struct rt2560_softc sc_rt2560;
1465fdff524SSepherosa Ziehau 		struct rt2661_softc sc_rt2661;
14776c21ea3SSascha Wildner 		struct rt2860_softc sc_rt2860;
1485fdff524SSepherosa Ziehau 	} u;
1495fdff524SSepherosa Ziehau 
15091b30d50SMatthew Dillon 	const struct ral_opns	*sc_opns;
151feb94d24SRui Paulo 	struct resource		*irq;
1525fdff524SSepherosa Ziehau 	struct resource		*mem;
153feb94d24SRui Paulo 	void			*sc_ih;
15493d249f7SMatthew Dillon 	int			sc_irq_type;
1555fdff524SSepherosa Ziehau };
1565fdff524SSepherosa Ziehau 
1575fdff524SSepherosa Ziehau static int ral_pci_probe(device_t);
1585fdff524SSepherosa Ziehau static int ral_pci_attach(device_t);
1595fdff524SSepherosa Ziehau static int ral_pci_detach(device_t);
1605fdff524SSepherosa Ziehau static int ral_pci_shutdown(device_t);
1615fdff524SSepherosa Ziehau static int ral_pci_suspend(device_t);
1625fdff524SSepherosa Ziehau static int ral_pci_resume(device_t);
1635fdff524SSepherosa Ziehau 
1645fdff524SSepherosa Ziehau static device_method_t ral_pci_methods[] = {
1655fdff524SSepherosa Ziehau 	/* Device interface */
1665fdff524SSepherosa Ziehau 	DEVMETHOD(device_probe,		ral_pci_probe),
1675fdff524SSepherosa Ziehau 	DEVMETHOD(device_attach,	ral_pci_attach),
1685fdff524SSepherosa Ziehau 	DEVMETHOD(device_detach,	ral_pci_detach),
1695fdff524SSepherosa Ziehau 	DEVMETHOD(device_shutdown,	ral_pci_shutdown),
1705fdff524SSepherosa Ziehau 	DEVMETHOD(device_suspend,	ral_pci_suspend),
1715fdff524SSepherosa Ziehau 	DEVMETHOD(device_resume,	ral_pci_resume),
1725fdff524SSepherosa Ziehau 
173d3c9c58eSSascha Wildner 	DEVMETHOD_END
1745fdff524SSepherosa Ziehau };
1755fdff524SSepherosa Ziehau 
1765fdff524SSepherosa Ziehau static driver_t ral_pci_driver = {
1775fdff524SSepherosa Ziehau 	"ral",
1785fdff524SSepherosa Ziehau 	ral_pci_methods,
1795fdff524SSepherosa Ziehau 	sizeof (struct ral_pci_softc)
1805fdff524SSepherosa Ziehau };
1815fdff524SSepherosa Ziehau 
1825fdff524SSepherosa Ziehau static devclass_t ral_devclass;
1835fdff524SSepherosa Ziehau 
184aa2b9d05SSascha Wildner DRIVER_MODULE(ral, pci, ral_pci_driver, ral_devclass, NULL, NULL);
1855fdff524SSepherosa Ziehau 
1865fdff524SSepherosa Ziehau static int
ral_pci_probe(device_t dev)1875fdff524SSepherosa Ziehau ral_pci_probe(device_t dev)
1885fdff524SSepherosa Ziehau {
1895fdff524SSepherosa Ziehau 	const struct ral_pci_ident *ident;
1905fdff524SSepherosa Ziehau 
1915fdff524SSepherosa Ziehau 	for (ident = ral_pci_ids; ident->name != NULL; ident++) {
192feb94d24SRui Paulo 		if (pci_get_vendor(dev) == ident->vendor &&
193feb94d24SRui Paulo 		    pci_get_device(dev) == ident->device) {
1945fdff524SSepherosa Ziehau 			device_set_desc(dev, ident->name);
19591b30d50SMatthew Dillon 			return (BUS_PROBE_DEFAULT);
1965fdff524SSepherosa Ziehau 		}
1975fdff524SSepherosa Ziehau 	}
1985fdff524SSepherosa Ziehau 	return ENXIO;
1995fdff524SSepherosa Ziehau }
2005fdff524SSepherosa Ziehau 
2015fdff524SSepherosa Ziehau static int
ral_pci_attach(device_t dev)2025fdff524SSepherosa Ziehau ral_pci_attach(device_t dev)
2035fdff524SSepherosa Ziehau {
2045fdff524SSepherosa Ziehau 	struct ral_pci_softc *psc = device_get_softc(dev);
2055fdff524SSepherosa Ziehau 	struct rt2560_softc *sc = &psc->u.sc_rt2560;
20693d249f7SMatthew Dillon #if defined(__DragonFly__)
20793d249f7SMatthew Dillon 	int error, rid;
20893d249f7SMatthew Dillon #else
20991b30d50SMatthew Dillon 	int count, error, rid;
21093d249f7SMatthew Dillon #endif
21193d249f7SMatthew Dillon #if defined(__DragonFly__)
21293d249f7SMatthew Dillon 	int irq_flags;
21393d249f7SMatthew Dillon #endif
21493d249f7SMatthew Dillon 
21593d249f7SMatthew Dillon #if defined(__DragonFly__)
21693d249f7SMatthew Dillon 	/* still needed? XXX */
21793d249f7SMatthew Dillon 	if (pci_get_powerstate(dev) != PCI_POWERSTATE_D0) {
21893d249f7SMatthew Dillon 		device_printf(dev, "chip is in D%d power mode "
21993d249f7SMatthew Dillon 		    "-- setting to D0\n", pci_get_powerstate(dev));
22093d249f7SMatthew Dillon 		pci_set_powerstate(dev, PCI_POWERSTATE_D0);
22193d249f7SMatthew Dillon 	}
22293d249f7SMatthew Dillon #endif
2235fdff524SSepherosa Ziehau 
2245fdff524SSepherosa Ziehau 	pci_enable_busmaster(dev);
2255fdff524SSepherosa Ziehau 
22676c21ea3SSascha Wildner 	switch (pci_get_device(dev)) {
22791b30d50SMatthew Dillon 	case 0x0201:
22876c21ea3SSascha Wildner 		psc->sc_opns = &ral_rt2560_opns;
22976c21ea3SSascha Wildner 		break;
23091b30d50SMatthew Dillon 	case 0x0301:
23191b30d50SMatthew Dillon 	case 0x0302:
23291b30d50SMatthew Dillon 	case 0x0401:
23376c21ea3SSascha Wildner 		psc->sc_opns = &ral_rt2661_opns;
23476c21ea3SSascha Wildner 		break;
23576c21ea3SSascha Wildner 	default:
23676c21ea3SSascha Wildner 		psc->sc_opns = &ral_rt2860_opns;
23776c21ea3SSascha Wildner 		break;
23876c21ea3SSascha Wildner 	}
239feb94d24SRui Paulo 
24091b30d50SMatthew Dillon 	rid = PCIR_BAR(0);
24191b30d50SMatthew Dillon 	psc->mem = bus_alloc_resource_any(dev, SYS_RES_MEMORY, &rid,
2425fdff524SSepherosa Ziehau 	    RF_ACTIVE);
2435fdff524SSepherosa Ziehau 	if (psc->mem == NULL) {
2445fdff524SSepherosa Ziehau 		device_printf(dev, "could not allocate memory resource\n");
2455fdff524SSepherosa Ziehau 		return ENXIO;
2465fdff524SSepherosa Ziehau 	}
247feb94d24SRui Paulo 
2485fdff524SSepherosa Ziehau 	sc->sc_st = rman_get_bustag(psc->mem);
2495fdff524SSepherosa Ziehau 	sc->sc_sh = rman_get_bushandle(psc->mem);
250feb94d24SRui Paulo 	sc->sc_invalid = 1;
2515fdff524SSepherosa Ziehau 
25293d249f7SMatthew Dillon #if defined(__DragonFly__)
25393d249f7SMatthew Dillon 	psc->sc_irq_type = pci_alloc_1intr(dev, ~ral_msi_disable,
25493d249f7SMatthew Dillon 					    &rid, &irq_flags);
25593d249f7SMatthew Dillon 	psc->irq = bus_alloc_resource_any(dev, SYS_RES_IRQ, &rid, irq_flags);
25693d249f7SMatthew Dillon #else
25791b30d50SMatthew Dillon 	rid = 0;
25891b30d50SMatthew Dillon 	if (ral_msi_disable == 0) {
25991b30d50SMatthew Dillon 		count = 1;
26091b30d50SMatthew Dillon 		if (pci_alloc_msi(dev, &count) == 0)
26191b30d50SMatthew Dillon 			rid = 1;
26291b30d50SMatthew Dillon 	}
26391b30d50SMatthew Dillon 	psc->irq = bus_alloc_resource_any(dev, SYS_RES_IRQ, &rid, RF_ACTIVE |
26491b30d50SMatthew Dillon 	    (rid != 0 ? 0 : RF_SHAREABLE));
26593d249f7SMatthew Dillon #endif
266feb94d24SRui Paulo 	if (psc->irq == NULL) {
267feb94d24SRui Paulo 		device_printf(dev, "could not allocate interrupt resource\n");
26891b30d50SMatthew Dillon 		pci_release_msi(dev);
26991b30d50SMatthew Dillon 		bus_release_resource(dev, SYS_RES_MEMORY,
27091b30d50SMatthew Dillon 		    rman_get_rid(psc->mem), psc->mem);
271feb94d24SRui Paulo 		return ENXIO;
272feb94d24SRui Paulo 	}
273feb94d24SRui Paulo 
274feb94d24SRui Paulo 	error = (*psc->sc_opns->attach)(dev, pci_get_device(dev));
275d8235d53SJoe Talbott 	if (error != 0) {
27691b30d50SMatthew Dillon 		(void)ral_pci_detach(dev);
2775fdff524SSepherosa Ziehau 		return error;
278d8235d53SJoe Talbott 	}
279feb94d24SRui Paulo 
280feb94d24SRui Paulo 	/*
281feb94d24SRui Paulo 	 * Hook our interrupt after all initialization is complete.
282feb94d24SRui Paulo 	 */
28393d249f7SMatthew Dillon #if defined(__DragonFly__)
28493d249f7SMatthew Dillon 	error = bus_setup_intr(dev, psc->irq, INTR_MPSAFE,
28593d249f7SMatthew Dillon 	    psc->sc_opns->intr, psc, &psc->sc_ih, &wlan_global_serializer);
28693d249f7SMatthew Dillon #else
28791b30d50SMatthew Dillon 	error = bus_setup_intr(dev, psc->irq, INTR_TYPE_NET | INTR_MPSAFE,
28891b30d50SMatthew Dillon 	    NULL, psc->sc_opns->intr, psc, &psc->sc_ih);
28993d249f7SMatthew Dillon #endif
290feb94d24SRui Paulo 	if (error != 0) {
291feb94d24SRui Paulo 		device_printf(dev, "could not set up interrupt\n");
29291b30d50SMatthew Dillon 		(void)ral_pci_detach(dev);
293feb94d24SRui Paulo 		return error;
294feb94d24SRui Paulo 	}
295feb94d24SRui Paulo 	sc->sc_invalid = 0;
296feb94d24SRui Paulo 
297feb94d24SRui Paulo 	return 0;
2985fdff524SSepherosa Ziehau }
2995fdff524SSepherosa Ziehau 
3005fdff524SSepherosa Ziehau static int
ral_pci_detach(device_t dev)3015fdff524SSepherosa Ziehau ral_pci_detach(device_t dev)
3025fdff524SSepherosa Ziehau {
3035fdff524SSepherosa Ziehau 	struct ral_pci_softc *psc = device_get_softc(dev);
304feb94d24SRui Paulo 	struct rt2560_softc *sc = &psc->u.sc_rt2560;
3055fdff524SSepherosa Ziehau 
306feb94d24SRui Paulo 	/* check if device was removed */
307feb94d24SRui Paulo 	sc->sc_invalid = !bus_child_present(dev);
308feb94d24SRui Paulo 
30991b30d50SMatthew Dillon 	if (psc->sc_ih != NULL)
31091b30d50SMatthew Dillon 		bus_teardown_intr(dev, psc->irq, psc->sc_ih);
311feb94d24SRui Paulo 	(*psc->sc_opns->detach)(psc);
3125fdff524SSepherosa Ziehau 
3135fdff524SSepherosa Ziehau 	bus_generic_detach(dev);
31493d249f7SMatthew Dillon 
31593d249f7SMatthew Dillon #if defined(__DragonFly__)
31693d249f7SMatthew Dillon 	if (psc->sc_irq_type == PCI_INTR_TYPE_MSI)
31793d249f7SMatthew Dillon 		pci_release_msi(dev);
31893d249f7SMatthew Dillon #endif
31991b30d50SMatthew Dillon 	bus_release_resource(dev, SYS_RES_IRQ, rman_get_rid(psc->irq),
32091b30d50SMatthew Dillon 	    psc->irq);
32191b30d50SMatthew Dillon 	pci_release_msi(dev);
3225fdff524SSepherosa Ziehau 
32391b30d50SMatthew Dillon 	bus_release_resource(dev, SYS_RES_MEMORY, rman_get_rid(psc->mem),
32491b30d50SMatthew Dillon 	    psc->mem);
325feb94d24SRui Paulo 
3265fdff524SSepherosa Ziehau 	return 0;
3275fdff524SSepherosa Ziehau }
3285fdff524SSepherosa Ziehau 
3295fdff524SSepherosa Ziehau static int
ral_pci_shutdown(device_t dev)3305fdff524SSepherosa Ziehau ral_pci_shutdown(device_t dev)
3315fdff524SSepherosa Ziehau {
3325fdff524SSepherosa Ziehau 	struct ral_pci_softc *psc = device_get_softc(dev);
3335fdff524SSepherosa Ziehau 
334feb94d24SRui Paulo 	(*psc->sc_opns->shutdown)(psc);
335feb94d24SRui Paulo 
3365fdff524SSepherosa Ziehau 	return 0;
3375fdff524SSepherosa Ziehau }
3385fdff524SSepherosa Ziehau 
3395fdff524SSepherosa Ziehau static int
ral_pci_suspend(device_t dev)3405fdff524SSepherosa Ziehau ral_pci_suspend(device_t dev)
3415fdff524SSepherosa Ziehau {
3425fdff524SSepherosa Ziehau 	struct ral_pci_softc *psc = device_get_softc(dev);
3435fdff524SSepherosa Ziehau 
344feb94d24SRui Paulo 	(*psc->sc_opns->suspend)(psc);
345feb94d24SRui Paulo 
3465fdff524SSepherosa Ziehau 	return 0;
3475fdff524SSepherosa Ziehau }
3485fdff524SSepherosa Ziehau 
3495fdff524SSepherosa Ziehau static int
ral_pci_resume(device_t dev)3505fdff524SSepherosa Ziehau ral_pci_resume(device_t dev)
3515fdff524SSepherosa Ziehau {
3525fdff524SSepherosa Ziehau 	struct ral_pci_softc *psc = device_get_softc(dev);
3535fdff524SSepherosa Ziehau 
354feb94d24SRui Paulo 	(*psc->sc_opns->resume)(psc);
355feb94d24SRui Paulo 
3565fdff524SSepherosa Ziehau 	return 0;
3575fdff524SSepherosa Ziehau }
358