acpi.c revision 1.331
1/* $OpenBSD: acpi.c,v 1.331 2017/08/09 10:15:31 dcoppa Exp $ */
2/*
3 * Copyright (c) 2005 Thorsten Lockert <tholo@sigmasoft.com>
4 * Copyright (c) 2005 Jordan Hargrave <jordan@openbsd.org>
5 *
6 * Permission to use, copy, modify, and distribute this software for any
7 * purpose with or without fee is hereby granted, provided that the above
8 * copyright notice and this permission notice appear in all copies.
9 *
10 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
11 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
12 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
13 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
14 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
15 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
16 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
17 */
18
19#include <sys/param.h>
20#include <sys/systm.h>
21#include <sys/buf.h>
22#include <sys/device.h>
23#include <sys/malloc.h>
24#include <sys/fcntl.h>
25#include <sys/ioccom.h>
26#include <sys/event.h>
27#include <sys/signalvar.h>
28#include <sys/proc.h>
29#include <sys/kthread.h>
30#include <sys/sched.h>
31#include <sys/reboot.h>
32#include <sys/sysctl.h>
33
34#ifdef HIBERNATE
35#include <sys/hibernate.h>
36#endif
37
38#include <machine/conf.h>
39#include <machine/cpufunc.h>
40#include <machine/bus.h>
41
42#include <dev/rndvar.h>
43#include <dev/pci/pcivar.h>
44#include <dev/acpi/acpireg.h>
45#include <dev/acpi/acpivar.h>
46#include <dev/acpi/amltypes.h>
47#include <dev/acpi/acpidev.h>
48#include <dev/acpi/dsdt.h>
49#include <dev/wscons/wsdisplayvar.h>
50
51#include <dev/pci/pcidevs.h>
52#include <dev/pci/ppbreg.h>
53
54#include <dev/pci/pciidevar.h>
55
56#include <machine/apmvar.h>
57#define APMUNIT(dev)	(minor(dev)&0xf0)
58#define APMDEV(dev)	(minor(dev)&0x0f)
59#define APMDEV_NORMAL	0
60#define APMDEV_CTL	8
61
62#include "wd.h"
63#include "wsdisplay.h"
64
65#ifdef ACPI_DEBUG
66int	acpi_debug = 16;
67#endif
68
69int	acpi_poll_enabled;
70int	acpi_hasprocfvs;
71
72#define ACPIEN_RETRIES 15
73
74void 	acpi_pci_match(struct device *, struct pci_attach_args *);
75pcireg_t acpi_pci_min_powerstate(pci_chipset_tag_t, pcitag_t);
76void	 acpi_pci_set_powerstate(pci_chipset_tag_t, pcitag_t, int, int);
77int	acpi_pci_notify(struct aml_node *, int, void *);
78
79int	acpi_match(struct device *, void *, void *);
80void	acpi_attach(struct device *, struct device *, void *);
81int	acpi_submatch(struct device *, void *, void *);
82int	acpi_print(void *, const char *);
83
84void	acpi_map_pmregs(struct acpi_softc *);
85void	acpi_unmap_pmregs(struct acpi_softc *);
86
87int	acpi_loadtables(struct acpi_softc *, struct acpi_rsdp *);
88
89int	_acpi_matchhids(const char *, const char *[]);
90
91int	acpi_inidev(struct aml_node *, void *);
92int	acpi_foundprt(struct aml_node *, void *);
93
94int	acpi_enable(struct acpi_softc *);
95void	acpi_init_states(struct acpi_softc *);
96
97void 	acpi_gpe_task(void *, int);
98void	acpi_sbtn_task(void *, int);
99void	acpi_pbtn_task(void *, int);
100
101int	acpi_enabled;
102
103void	acpi_init_gpes(struct acpi_softc *);
104void	acpi_disable_allgpes(struct acpi_softc *);
105struct gpe_block *acpi_find_gpe(struct acpi_softc *, int);
106void	acpi_enable_onegpe(struct acpi_softc *, int);
107int	acpi_gpe(struct acpi_softc *, int, void *);
108
109void	acpi_enable_rungpes(struct acpi_softc *);
110void	acpi_enable_wakegpes(struct acpi_softc *, int);
111
112
113int	acpi_foundec(struct aml_node *, void *);
114int	acpi_foundsony(struct aml_node *node, void *arg);
115int	acpi_foundhid(struct aml_node *, void *);
116int	acpi_add_device(struct aml_node *node, void *arg);
117
118void	acpi_thread(void *);
119void	acpi_create_thread(void *);
120
121#ifndef SMALL_KERNEL
122
123void	acpi_indicator(struct acpi_softc *, int);
124
125int	acpi_matchhids(struct acpi_attach_args *aa, const char *hids[],
126	    const char *driver);
127
128void	acpi_init_pm(struct acpi_softc *);
129
130int	acpi_founddock(struct aml_node *, void *);
131int	acpi_foundpss(struct aml_node *, void *);
132int	acpi_foundtmp(struct aml_node *, void *);
133int	acpi_foundprw(struct aml_node *, void *);
134int	acpi_foundvideo(struct aml_node *, void *);
135int	acpi_foundsbs(struct aml_node *node, void *);
136
137int	acpi_foundide(struct aml_node *node, void *arg);
138int	acpiide_notify(struct aml_node *, int, void *);
139void	wdcattach(struct channel_softc *);
140int	wdcdetach(struct channel_softc *, int);
141int	is_ejectable_bay(struct aml_node *node);
142int	is_ata(struct aml_node *node);
143int	is_ejectable(struct aml_node *node);
144
145struct idechnl {
146	struct acpi_softc *sc;
147	int64_t		addr;
148	int64_t		chnl;
149	int64_t		sta;
150};
151
152/*
153 * This is a list of Synaptics devices with a 'top button area'
154 * based on the list in Linux supplied by Synaptics
155 * Synaptics clickpads with the following pnp ids will get a unique
156 * wscons mouse type that is used to define trackpad regions that will
157 * emulate mouse buttons
158 */
159static const char *sbtn_pnp[] = {
160	"LEN0017",
161	"LEN0018",
162	"LEN0019",
163	"LEN0023",
164	"LEN002A",
165	"LEN002B",
166	"LEN002C",
167	"LEN002D",
168	"LEN002E",
169	"LEN0033",
170	"LEN0034",
171	"LEN0035",
172	"LEN0036",
173	"LEN0037",
174	"LEN0038",
175	"LEN0039",
176	"LEN0041",
177	"LEN0042",
178	"LEN0045",
179	"LEN0047",
180	"LEN0049",
181	"LEN2000",
182	"LEN2001",
183	"LEN2002",
184	"LEN2003",
185	"LEN2004",
186	"LEN2005",
187	"LEN2006",
188	"LEN2007",
189	"LEN2008",
190	"LEN2009",
191	"LEN200A",
192	"LEN200B",
193};
194
195int	mouse_has_softbtn;
196#endif /* SMALL_KERNEL */
197
198/* XXX move this into dsdt softc at some point */
199extern struct aml_node aml_root;
200
201struct cfattach acpi_ca = {
202	sizeof(struct acpi_softc), acpi_match, acpi_attach
203};
204
205struct cfdriver acpi_cd = {
206	NULL, "acpi", DV_DULL
207};
208
209struct acpi_softc *acpi_softc;
210
211#define acpi_bus_space_map	_bus_space_map
212#define acpi_bus_space_unmap	_bus_space_unmap
213
214uint8_t
215acpi_pci_conf_read_1(pci_chipset_tag_t pc, pcitag_t tag, int reg)
216{
217	uint32_t val = pci_conf_read(pc, tag, reg & ~0x3);
218	return (val >> ((reg & 0x3) << 3));
219}
220
221uint16_t
222acpi_pci_conf_read_2(pci_chipset_tag_t pc, pcitag_t tag, int reg)
223{
224	uint32_t val = pci_conf_read(pc, tag, reg & ~0x2);
225	return (val >> ((reg & 0x2) << 3));
226}
227
228uint32_t
229acpi_pci_conf_read_4(pci_chipset_tag_t pc, pcitag_t tag, int reg)
230{
231	return pci_conf_read(pc, tag, reg);
232}
233
234void
235acpi_pci_conf_write_1(pci_chipset_tag_t pc, pcitag_t tag, int reg, uint8_t val)
236{
237	uint32_t tmp = pci_conf_read(pc, tag, reg & ~0x3);
238	tmp &= ~(0xff << ((reg & 0x3) << 3));
239	tmp |= (val << ((reg & 0x3) << 3));
240	pci_conf_write(pc, tag, reg & ~0x3, tmp);
241}
242
243void
244acpi_pci_conf_write_2(pci_chipset_tag_t pc, pcitag_t tag, int reg, uint16_t val)
245{
246	uint32_t tmp = pci_conf_read(pc, tag, reg & ~0x2);
247	tmp &= ~(0xffff << ((reg & 0x2) << 3));
248	tmp |= (val << ((reg & 0x2) << 3));
249	pci_conf_write(pc, tag, reg & ~0x2, tmp);
250}
251
252void
253acpi_pci_conf_write_4(pci_chipset_tag_t pc, pcitag_t tag, int reg, uint32_t val)
254{
255	pci_conf_write(pc, tag, reg, val);
256}
257
258int
259acpi_gasio(struct acpi_softc *sc, int iodir, int iospace, uint64_t address,
260    int access_size, int len, void *buffer)
261{
262	u_int8_t *pb;
263	bus_space_tag_t iot;
264	bus_space_handle_t ioh;
265	pci_chipset_tag_t pc;
266	pcitag_t tag;
267	int reg, idx;
268
269	dnprintf(50, "gasio: %.2x 0x%.8llx %s\n",
270	    iospace, address, (iodir == ACPI_IOWRITE) ? "write" : "read");
271
272	KASSERT((len % access_size) == 0);
273
274	pb = (u_int8_t *)buffer;
275	switch (iospace) {
276	case GAS_SYSTEM_MEMORY:
277	case GAS_SYSTEM_IOSPACE:
278		if (iospace == GAS_SYSTEM_MEMORY)
279			iot = sc->sc_memt;
280		else
281			iot = sc->sc_iot;
282
283		if (acpi_bus_space_map(iot, address, len, 0, &ioh) != 0) {
284			printf("%s: unable to map iospace\n", DEVNAME(sc));
285			return (-1);
286		}
287		for (reg = 0; reg < len; reg += access_size) {
288			if (iodir == ACPI_IOREAD) {
289				switch (access_size) {
290				case 1:
291					*(uint8_t *)(pb + reg) =
292					    bus_space_read_1(iot, ioh, reg);
293					dnprintf(80, "os_in8(%llx) = %x\n",
294					    reg+address, *(uint8_t *)(pb+reg));
295					break;
296				case 2:
297					*(uint16_t *)(pb + reg) =
298					    bus_space_read_2(iot, ioh, reg);
299					dnprintf(80, "os_in16(%llx) = %x\n",
300					    reg+address, *(uint16_t *)(pb+reg));
301					break;
302				case 4:
303					*(uint32_t *)(pb + reg) =
304					    bus_space_read_4(iot, ioh, reg);
305					break;
306				default:
307					printf("%s: rdio: invalid size %d\n",
308					    DEVNAME(sc), access_size);
309					return (-1);
310				}
311			} else {
312				switch (access_size) {
313				case 1:
314					bus_space_write_1(iot, ioh, reg,
315					    *(uint8_t *)(pb + reg));
316					dnprintf(80, "os_out8(%llx,%x)\n",
317					    reg+address, *(uint8_t *)(pb+reg));
318					break;
319				case 2:
320					bus_space_write_2(iot, ioh, reg,
321					    *(uint16_t *)(pb + reg));
322					dnprintf(80, "os_out16(%llx,%x)\n",
323					    reg+address, *(uint16_t *)(pb+reg));
324					break;
325				case 4:
326					bus_space_write_4(iot, ioh, reg,
327					    *(uint32_t *)(pb + reg));
328					break;
329				default:
330					printf("%s: wrio: invalid size %d\n",
331					    DEVNAME(sc), access_size);
332					return (-1);
333				}
334			}
335		}
336		acpi_bus_space_unmap(iot, ioh, len, NULL);
337		break;
338
339	case GAS_PCI_CFG_SPACE:
340		/* format of address:
341		 *    bits 00..15 = register
342		 *    bits 16..31 = function
343		 *    bits 32..47 = device
344		 *    bits 48..63 = bus
345		 */
346
347		/*
348		 * The ACPI standard says that a function number of
349		 * FFFF can be used to refer to all functions on a
350		 * device.  This makes no sense though in the context
351		 * of accessing PCI config space.  Yet there is AML
352		 * out there that does this.  We simulate a read from
353		 * a nonexistent device here.  Writes will panic when
354		 * we try to construct the tag below.
355		 */
356		if (ACPI_PCI_FN(address) == 0xffff && iodir == ACPI_IOREAD) {
357			memset(buffer, 0xff, len);
358			return (0);
359		}
360
361		pc = NULL;
362		tag = pci_make_tag(pc,
363		    ACPI_PCI_BUS(address), ACPI_PCI_DEV(address),
364		    ACPI_PCI_FN(address));
365
366		reg = ACPI_PCI_REG(address);
367		for (idx = 0; idx < len; idx += access_size) {
368			if (iodir == ACPI_IOREAD) {
369				switch (access_size) {
370				case 1:
371					*(uint8_t *)(pb + idx) =
372					    acpi_pci_conf_read_1(pc, tag, reg + idx);
373					break;
374				case 2:
375					*(uint16_t *)(pb + idx) =
376					    acpi_pci_conf_read_2(pc, tag, reg + idx);
377					break;
378				case 4:
379					*(uint32_t *)(pb + idx) =
380					    acpi_pci_conf_read_4(pc, tag, reg + idx);
381					break;
382				default:
383					printf("%s: rdcfg: invalid size %d\n",
384					    DEVNAME(sc), access_size);
385					return (-1);
386				}
387			} else {
388				switch (access_size) {
389				case 1:
390					acpi_pci_conf_write_1(pc, tag, reg + idx,
391					    *(uint8_t *)(pb + idx));
392					break;
393				case 2:
394					acpi_pci_conf_write_2(pc, tag, reg + idx,
395					    *(uint16_t *)(pb + idx));
396					break;
397				case 4:
398					acpi_pci_conf_write_4(pc, tag, reg + idx,
399					    *(uint32_t *)(pb + idx));
400					break;
401				default:
402					printf("%s: wrcfg: invalid size %d\n",
403					    DEVNAME(sc), access_size);
404					return (-1);
405				}
406			}
407		}
408		break;
409
410	case GAS_EMBEDDED:
411		if (sc->sc_ec == NULL) {
412			printf("%s: WARNING EC not initialized\n", DEVNAME(sc));
413			return (-1);
414		}
415		if (iodir == ACPI_IOREAD)
416			acpiec_read(sc->sc_ec, (u_int8_t)address, len, buffer);
417		else
418			acpiec_write(sc->sc_ec, (u_int8_t)address, len, buffer);
419		break;
420	}
421	return (0);
422}
423
424int
425acpi_inidev(struct aml_node *node, void *arg)
426{
427	struct acpi_softc	*sc = (struct acpi_softc *)arg;
428	int64_t st;
429
430	/*
431	 * Per the ACPI spec 6.5.1, only run _INI when device is there or
432	 * when there is no _STA.  We terminate the tree walk (with return 1)
433	 * early if necessary.
434	 */
435
436	/* Evaluate _STA to decide _INI fate and walk fate */
437	if (aml_evalinteger(sc, node->parent, "_STA", 0, NULL, &st))
438		st = STA_PRESENT | STA_ENABLED | STA_DEV_OK | 0x1000;
439
440	/* Evaluate _INI if we are present */
441	if (st & STA_PRESENT)
442		aml_evalnode(sc, node, 0, NULL, NULL);
443
444	/* If we are functioning, we walk/search our children */
445	if (st & STA_DEV_OK)
446		return 0;
447
448	/* If we are not enabled, or not present, terminate search */
449	if (!(st & (STA_PRESENT|STA_ENABLED)))
450		return 1;
451
452	/* Default just continue search */
453	return 0;
454}
455
456int
457acpi_foundprt(struct aml_node *node, void *arg)
458{
459	struct acpi_softc	*sc = (struct acpi_softc *)arg;
460	struct device		*self = (struct device *)arg;
461	struct acpi_attach_args	aaa;
462	int64_t st = 0;
463
464	dnprintf(10, "found prt entry: %s\n", node->parent->name);
465
466	/* Evaluate _STA to decide _PRT fate and walk fate */
467	if (aml_evalinteger(sc, node->parent, "_STA", 0, NULL, &st))
468		st = STA_PRESENT | STA_ENABLED | STA_DEV_OK | 0x1000;
469
470	if (st & STA_PRESENT) {
471		memset(&aaa, 0, sizeof(aaa));
472		aaa.aaa_iot = sc->sc_iot;
473		aaa.aaa_memt = sc->sc_memt;
474		aaa.aaa_node = node;
475		aaa.aaa_name = "acpiprt";
476
477		config_found(self, &aaa, acpi_print);
478	}
479
480	/* If we are functioning, we walk/search our children */
481	if (st & STA_DEV_OK)
482		return 0;
483
484	/* If we are not enabled, or not present, terminate search */
485	if (!(st & (STA_PRESENT|STA_ENABLED)))
486		return 1;
487
488	/* Default just continue search */
489	return 0;
490}
491
492int
493acpi_match(struct device *parent, void *match, void *aux)
494{
495	struct bios_attach_args	*ba = aux;
496	struct cfdata		*cf = match;
497
498	/* sanity */
499	if (strcmp(ba->ba_name, cf->cf_driver->cd_name))
500		return (0);
501
502	if (!acpi_probe(parent, cf, ba))
503		return (0);
504
505	return (1);
506}
507
508TAILQ_HEAD(, acpi_pci) acpi_pcidevs =
509    TAILQ_HEAD_INITIALIZER(acpi_pcidevs);
510TAILQ_HEAD(, acpi_pci) acpi_pcirootdevs =
511    TAILQ_HEAD_INITIALIZER(acpi_pcirootdevs);
512
513int acpi_getpci(struct aml_node *node, void *arg);
514int acpi_getminbus(int crsidx, union acpi_resource *crs, void *arg);
515
516int
517acpi_getminbus(int crsidx, union acpi_resource *crs, void *arg)
518{
519	int *bbn = arg;
520	int typ = AML_CRSTYPE(crs);
521
522	/* Check for embedded bus number */
523	if (typ == LR_WORD && crs->lr_word.type == 2) {
524		/* If _MIN > _MAX, the resource is considered to be invalid. */
525		if (crs->lr_word._min > crs->lr_word._max)
526			return -1;
527		*bbn = crs->lr_word._min;
528	}
529	return 0;
530}
531
532int
533_acpi_matchhids(const char *hid, const char *hids[])
534{
535	int i;
536
537	for (i = 0; hids[i]; i++)
538		if (!strcmp(hid, hids[i]))
539			return (1);
540	return (0);
541}
542
543int
544acpi_matchhids(struct acpi_attach_args *aa, const char *hids[],
545    const char *driver)
546{
547	if (aa->aaa_dev == NULL || aa->aaa_node == NULL)
548		return (0);
549	if (_acpi_matchhids(aa->aaa_dev, hids)) {
550		dnprintf(5, "driver %s matches at least one hid\n", driver);
551		return (1);
552	}
553
554	return (0);
555}
556
557/* Map ACPI device node to PCI */
558int
559acpi_getpci(struct aml_node *node, void *arg)
560{
561	const char *pcihid[] = { ACPI_DEV_PCIB, ACPI_DEV_PCIEB, "HWP0002", 0 };
562	struct acpi_pci *pci, *ppci;
563	struct aml_value res;
564	struct acpi_softc *sc = arg;
565	pci_chipset_tag_t pc = NULL;
566	pcitag_t tag;
567	uint64_t val;
568	uint32_t reg;
569
570	if (!node->value || node->value->type != AML_OBJTYPE_DEVICE)
571		return 0;
572	if (!aml_evalhid(node, &res)) {
573		/* Check if this is a PCI Root node */
574		if (_acpi_matchhids(res.v_string, pcihid)) {
575			aml_freevalue(&res);
576
577			pci = malloc(sizeof(*pci), M_DEVBUF, M_WAITOK|M_ZERO);
578
579			pci->bus = -1;
580			if (!aml_evalinteger(sc, node, "_SEG", 0, NULL, &val))
581				pci->seg = val;
582			if (!aml_evalname(sc, node, "_CRS", 0, NULL, &res)) {
583				aml_parse_resource(&res, acpi_getminbus,
584				    &pci->bus);
585				dnprintf(10, "%s post-crs: %d\n", aml_nodename(node),
586				    pci->bus);
587			}
588			if (!aml_evalinteger(sc, node, "_BBN", 0, NULL, &val)) {
589				dnprintf(10, "%s post-bbn: %d, %lld\n", aml_nodename(node),
590				    pci->bus, val);
591				if (pci->bus == -1)
592					pci->bus = val;
593			}
594			pci->sub = pci->bus;
595			node->pci = pci;
596			dnprintf(10, "found PCI root: %s %d\n",
597			    aml_nodename(node), pci->bus);
598			TAILQ_INSERT_TAIL(&acpi_pcirootdevs, pci, next);
599		}
600		aml_freevalue(&res);
601		return 0;
602	}
603
604	/* If parent is not PCI, or device does not have _ADR, return */
605	if (!node->parent || (ppci = node->parent->pci) == NULL)
606		return 0;
607	if (aml_evalinteger(sc, node, "_ADR", 0, NULL, &val))
608		return 0;
609
610	pci = malloc(sizeof(*pci), M_DEVBUF, M_WAITOK|M_ZERO);
611	pci->bus = ppci->sub;
612	pci->dev = ACPI_ADR_PCIDEV(val);
613	pci->fun = ACPI_ADR_PCIFUN(val);
614	pci->node = node;
615	pci->sub = -1;
616
617	dnprintf(10, "%.2x:%.2x.%x -> %s\n",
618		pci->bus, pci->dev, pci->fun,
619		aml_nodename(node));
620
621	/* Collect device power state information. */
622	if (aml_evalinteger(sc, node, "_S3D", 0, NULL, &val) == 0)
623		pci->_s3d = val;
624	else
625		pci->_s3d = -1;
626	if (aml_evalinteger(sc, node, "_S3W", 0, NULL, &val) == 0)
627		pci->_s3w = val;
628	else
629		pci->_s3w = -1;
630	if (aml_evalinteger(sc, node, "_S4D", 0, NULL, &val) == 0)
631		pci->_s4d = val;
632	else
633		pci->_s4d = -1;
634	if (aml_evalinteger(sc, node, "_S4W", 0, NULL, &val) == 0)
635		pci->_s4w = val;
636	else
637		pci->_s4w = -1;
638
639	/* Check if PCI device exists */
640	if (pci->dev > 0x1F || pci->fun > 7) {
641		free(pci, M_DEVBUF, sizeof(*pci));
642		return (1);
643	}
644	tag = pci_make_tag(pc, pci->bus, pci->dev, pci->fun);
645	reg = pci_conf_read(pc, tag, PCI_ID_REG);
646	if (PCI_VENDOR(reg) == PCI_VENDOR_INVALID) {
647		free(pci, M_DEVBUF, sizeof(*pci));
648		return (1);
649	}
650	node->pci = pci;
651
652	TAILQ_INSERT_TAIL(&acpi_pcidevs, pci, next);
653
654	/* Check if this is a PCI bridge */
655	reg = pci_conf_read(pc, tag, PCI_CLASS_REG);
656	if (PCI_CLASS(reg) == PCI_CLASS_BRIDGE &&
657	    PCI_SUBCLASS(reg) == PCI_SUBCLASS_BRIDGE_PCI) {
658		reg = pci_conf_read(pc, tag, PPB_REG_BUSINFO);
659		pci->sub = PPB_BUSINFO_SECONDARY(reg);
660
661		dnprintf(10, "found PCI bridge: %s %d\n",
662		    aml_nodename(node), pci->sub);
663
664		/* Continue scanning */
665		return (0);
666	}
667
668	/* Device does not have children, stop scanning */
669	return (1);
670}
671
672void
673acpi_pci_match(struct device *dev, struct pci_attach_args *pa)
674{
675	struct acpi_pci *pdev;
676	int state;
677
678	TAILQ_FOREACH(pdev, &acpi_pcidevs, next) {
679		if (pdev->bus != pa->pa_bus ||
680		    pdev->dev != pa->pa_device ||
681		    pdev->fun != pa->pa_function)
682			continue;
683
684		dnprintf(10,"%s at acpi0 %s\n", dev->dv_xname,
685		    aml_nodename(pdev->node));
686
687		pdev->device = dev;
688
689		/*
690		 * If some Power Resources are dependent on this device
691		 * initialize them.
692		 */
693		state = pci_get_powerstate(pa->pa_pc, pa->pa_tag);
694		acpi_pci_set_powerstate(pa->pa_pc, pa->pa_tag, state, 1);
695		acpi_pci_set_powerstate(pa->pa_pc, pa->pa_tag, state, 0);
696
697		aml_register_notify(pdev->node, NULL, acpi_pci_notify, pdev, 0);
698	}
699}
700
701pcireg_t
702acpi_pci_min_powerstate(pci_chipset_tag_t pc, pcitag_t tag)
703{
704	struct acpi_pci *pdev;
705	int bus, dev, fun;
706	int state = -1, defaultstate = pci_get_powerstate(pc, tag);
707
708	pci_decompose_tag(pc, tag, &bus, &dev, &fun);
709	TAILQ_FOREACH(pdev, &acpi_pcidevs, next) {
710		if (pdev->bus == bus && pdev->dev == dev && pdev->fun == fun) {
711			switch (acpi_softc->sc_state) {
712			case ACPI_STATE_S3:
713				defaultstate = PCI_PMCSR_STATE_D3;
714				state = MAX(pdev->_s3d, pdev->_s3w);
715				break;
716			case ACPI_STATE_S4:
717				state = MAX(pdev->_s4d, pdev->_s4w);
718				break;
719			case ACPI_STATE_S5:
720			default:
721				break;
722			}
723
724			if (state >= PCI_PMCSR_STATE_D0 &&
725			    state <= PCI_PMCSR_STATE_D3)
726				return state;
727		}
728	}
729
730	return defaultstate;
731}
732
733void
734acpi_pci_set_powerstate(pci_chipset_tag_t pc, pcitag_t tag, int state, int pre)
735{
736#if NACPIPWRRES > 0
737	struct acpi_softc *sc = acpi_softc;
738	struct acpi_pwrres *pr;
739	struct acpi_pci *pdev;
740	int bus, dev, fun;
741	char name[5];
742
743	pci_decompose_tag(pc, tag, &bus, &dev, &fun);
744	TAILQ_FOREACH(pdev, &acpi_pcidevs, next) {
745		if (pdev->bus == bus && pdev->dev == dev && pdev->fun == fun)
746			break;
747	}
748
749	/* XXX Add a check to discard nodes without Power Resources? */
750	if (pdev == NULL)
751		return;
752
753	SIMPLEQ_FOREACH(pr, &sc->sc_pwrresdevs, p_next) {
754		if (pr->p_node != pdev->node)
755			continue;
756
757		/*
758		 * If the firmware is already aware that the device
759		 * is in the given state, there's nothing to do.
760		 */
761		if (pr->p_state == state)
762			continue;
763
764		if (pre) {
765			/*
766			 * If a Resource is dependent on this device for
767			 * the given state, make sure it is turned "_ON".
768			 */
769			if (pr->p_res_state == state)
770				acpipwrres_ref_incr(pr->p_res_sc, pr->p_node);
771		} else {
772			/*
773			 * If a Resource was referenced for the state we
774			 * left, drop a reference and turn it "_OFF" if
775			 * it was the last one.
776			 */
777			if (pr->p_res_state == pr->p_state)
778				acpipwrres_ref_decr(pr->p_res_sc, pr->p_node);
779
780			if (pr->p_res_state == state) {
781				snprintf(name, sizeof(name), "_PS%d", state);
782				aml_evalname(sc, pr->p_node, name, 0,
783				    NULL, NULL);
784			}
785
786			pr->p_state = state;
787		}
788
789	}
790#endif /* NACPIPWRRES > 0 */
791}
792
793int
794acpi_pci_notify(struct aml_node *node, int ntype, void *arg)
795{
796	struct acpi_pci *pdev = arg;
797	pci_chipset_tag_t pc = NULL;
798	pcitag_t tag;
799	pcireg_t reg;
800	int offset;
801
802	/* We're only interested in Device Wake notifications. */
803	if (ntype != 2)
804		return (0);
805
806	tag = pci_make_tag(pc, pdev->bus, pdev->dev, pdev->fun);
807	if (pci_get_capability(pc, tag, PCI_CAP_PWRMGMT, &offset, 0)) {
808		/* Clear the PME Status bit if it is set. */
809		reg = pci_conf_read(pc, tag, offset + PCI_PMCSR);
810		pci_conf_write(pc, tag, offset + PCI_PMCSR, reg);
811	}
812
813	return (0);
814}
815
816void
817acpi_pciroots_attach(struct device *dev, void *aux, cfprint_t pr)
818{
819	struct acpi_pci			*pdev;
820	struct pcibus_attach_args	*pba = aux;
821
822	KASSERT(pba->pba_busex != NULL);
823
824	TAILQ_FOREACH(pdev, &acpi_pcirootdevs, next) {
825		if (extent_alloc_region(pba->pba_busex, pdev->bus,
826		    1, EX_NOWAIT) != 0)
827			continue;
828		pba->pba_bus = pdev->bus;
829		config_found(dev, pba, pr);
830	}
831}
832
833void
834acpi_attach(struct device *parent, struct device *self, void *aux)
835{
836	struct bios_attach_args *ba = aux;
837	struct acpi_softc *sc = (struct acpi_softc *)self;
838	struct acpi_mem_map handle;
839	struct acpi_rsdp *rsdp;
840	struct acpi_q *entry;
841	struct acpi_dsdt *p_dsdt;
842#ifndef SMALL_KERNEL
843	int wakeup_dev_ct;
844	struct acpi_wakeq *wentry;
845	struct device *dev;
846#endif /* SMALL_KERNEL */
847	paddr_t facspa;
848	uint16_t pm1;
849	int s;
850
851	sc->sc_iot = ba->ba_iot;
852	sc->sc_memt = ba->ba_memt;
853
854	rw_init(&sc->sc_lck, "acpilk");
855
856	acpi_softc = sc;
857
858	if (acpi_map(ba->ba_acpipbase, sizeof(struct acpi_rsdp), &handle)) {
859		printf(": can't map memory\n");
860		return;
861	}
862
863	rsdp = (struct acpi_rsdp *)handle.va;
864	sc->sc_revision = (int)rsdp->rsdp_revision;
865	printf(": rev %d", sc->sc_revision);
866
867	SIMPLEQ_INIT(&sc->sc_tables);
868	SIMPLEQ_INIT(&sc->sc_wakedevs);
869#if NACPIPWRRES > 0
870	SIMPLEQ_INIT(&sc->sc_pwrresdevs);
871#endif /* NACPIPWRRES > 0 */
872
873
874#ifndef SMALL_KERNEL
875	sc->sc_note = malloc(sizeof(struct klist), M_DEVBUF, M_NOWAIT | M_ZERO);
876	if (sc->sc_note == NULL) {
877		printf(", can't allocate memory\n");
878		acpi_unmap(&handle);
879		return;
880	}
881#endif /* SMALL_KERNEL */
882
883	if (acpi_loadtables(sc, rsdp)) {
884		printf(", can't load tables\n");
885		acpi_unmap(&handle);
886		return;
887	}
888
889	acpi_unmap(&handle);
890
891	/*
892	 * Find the FADT
893	 */
894	SIMPLEQ_FOREACH(entry, &sc->sc_tables, q_next) {
895		if (memcmp(entry->q_table, FADT_SIG,
896		    sizeof(FADT_SIG) - 1) == 0) {
897			sc->sc_fadt = entry->q_table;
898			break;
899		}
900	}
901	if (sc->sc_fadt == NULL) {
902		printf(", no FADT\n");
903		return;
904	}
905
906	/*
907	 * A bunch of things need to be done differently for
908	 * Hardware-reduced ACPI.
909	 */
910	if (sc->sc_fadt->hdr_revision >= 5 &&
911	    sc->sc_fadt->flags & FADT_HW_REDUCED_ACPI)
912		sc->sc_hw_reduced = 1;
913
914	/* Map Power Management registers */
915	acpi_map_pmregs(sc);
916
917	/*
918	 * Check if we can and need to enable ACPI control.
919	 */
920	pm1 = acpi_read_pmreg(sc, ACPIREG_PM1_CNT, 0);
921	if ((pm1 & ACPI_PM1_SCI_EN) == 0 && sc->sc_fadt->smi_cmd &&
922	    (!sc->sc_fadt->acpi_enable && !sc->sc_fadt->acpi_disable)) {
923		printf(", ACPI control unavailable\n");
924		acpi_unmap_pmregs(sc);
925		return;
926	}
927
928	/*
929	 * Set up a pointer to the firmware control structure
930	 */
931	if (sc->sc_fadt->hdr_revision < 3 || sc->sc_fadt->x_firmware_ctl == 0)
932		facspa = sc->sc_fadt->firmware_ctl;
933	else
934		facspa = sc->sc_fadt->x_firmware_ctl;
935
936	if (acpi_map(facspa, sizeof(struct acpi_facs), &handle))
937		printf(" !FACS");
938	else
939		sc->sc_facs = (struct acpi_facs *)handle.va;
940
941	/* Create opcode hashtable */
942	aml_hashopcodes();
943
944	/* Create Default AML objects */
945	aml_create_defaultobjects();
946
947	/*
948	 * Load the DSDT from the FADT pointer -- use the
949	 * extended (64-bit) pointer if it exists
950	 */
951	if (sc->sc_fadt->hdr_revision < 3 || sc->sc_fadt->x_dsdt == 0)
952		entry = acpi_maptable(sc, sc->sc_fadt->dsdt, NULL, NULL, NULL, -1);
953	else
954		entry = acpi_maptable(sc, sc->sc_fadt->x_dsdt, NULL, NULL, NULL, -1);
955
956	if (entry == NULL)
957		printf(" !DSDT");
958
959	p_dsdt = entry->q_table;
960	acpi_parse_aml(sc, p_dsdt->aml, p_dsdt->hdr_length -
961	    sizeof(p_dsdt->hdr));
962
963	/* Load SSDT's */
964	SIMPLEQ_FOREACH(entry, &sc->sc_tables, q_next) {
965		if (memcmp(entry->q_table, SSDT_SIG,
966		    sizeof(SSDT_SIG) - 1) == 0) {
967			p_dsdt = entry->q_table;
968			acpi_parse_aml(sc, p_dsdt->aml, p_dsdt->hdr_length -
969			    sizeof(p_dsdt->hdr));
970		}
971	}
972
973	/* Perform post-parsing fixups */
974	aml_postparse();
975
976
977#ifndef SMALL_KERNEL
978	/* Find available sleeping states */
979	acpi_init_states(sc);
980
981	/* Find available sleep/resume related methods. */
982	acpi_init_pm(sc);
983#endif /* SMALL_KERNEL */
984
985	/* Initialize GPE handlers */
986	s = spltty();
987	acpi_init_gpes(sc);
988	splx(s);
989
990	/* some devices require periodic polling */
991	timeout_set(&sc->sc_dev_timeout, acpi_poll, sc);
992
993	acpi_enabled = 1;
994
995	/*
996	 * Take over ACPI control.  Note that once we do this, we
997	 * effectively tell the system that we have ownership of
998	 * the ACPI hardware registers, and that SMI should leave
999	 * them alone
1000	 *
1001	 * This may prevent thermal control on some systems where
1002	 * that actually does work
1003	 */
1004	if ((pm1 & ACPI_PM1_SCI_EN) == 0 && sc->sc_fadt->smi_cmd) {
1005		if (acpi_enable(sc)) {
1006			printf(", can't enable ACPI\n");
1007			return;
1008		}
1009	}
1010
1011	printf("\n%s: tables", DEVNAME(sc));
1012	SIMPLEQ_FOREACH(entry, &sc->sc_tables, q_next) {
1013		printf(" %.4s", (char *)entry->q_table);
1014	}
1015	printf("\n");
1016
1017#ifndef SMALL_KERNEL
1018	/* Display wakeup devices and lowest S-state */
1019	wakeup_dev_ct = 0;
1020	printf("%s: wakeup devices", DEVNAME(sc));
1021	SIMPLEQ_FOREACH(wentry, &sc->sc_wakedevs, q_next) {
1022		if (wakeup_dev_ct < 16)
1023			printf(" %.4s(S%d)", wentry->q_node->name,
1024			    wentry->q_state);
1025		else if (wakeup_dev_ct == 16)
1026			printf(" [...]");
1027		wakeup_dev_ct ++;
1028	}
1029	printf("\n");
1030
1031	/*
1032	 * ACPI is enabled now -- attach timer
1033	 */
1034	if (!sc->sc_hw_reduced &&
1035	    (sc->sc_fadt->pm_tmr_blk || sc->sc_fadt->x_pm_tmr_blk.address)) {
1036		struct acpi_attach_args aaa;
1037
1038		memset(&aaa, 0, sizeof(aaa));
1039		aaa.aaa_name = "acpitimer";
1040		aaa.aaa_iot = sc->sc_iot;
1041		aaa.aaa_memt = sc->sc_memt;
1042#if 0
1043		aaa.aaa_pcit = sc->sc_pcit;
1044		aaa.aaa_smbust = sc->sc_smbust;
1045#endif
1046		config_found(self, &aaa, acpi_print);
1047	}
1048#endif /* SMALL_KERNEL */
1049
1050	/*
1051	 * Attach table-defined devices
1052	 */
1053	SIMPLEQ_FOREACH(entry, &sc->sc_tables, q_next) {
1054		struct acpi_attach_args aaa;
1055
1056		memset(&aaa, 0, sizeof(aaa));
1057		aaa.aaa_iot = sc->sc_iot;
1058		aaa.aaa_memt = sc->sc_memt;
1059	#if 0
1060		aaa.aaa_pcit = sc->sc_pcit;
1061		aaa.aaa_smbust = sc->sc_smbust;
1062	#endif
1063		aaa.aaa_table = entry->q_table;
1064		config_found_sm(self, &aaa, acpi_print, acpi_submatch);
1065	}
1066
1067	/* initialize runtime environment */
1068	aml_find_node(&aml_root, "_INI", acpi_inidev, sc);
1069
1070	/* Get PCI mapping */
1071	aml_walknodes(&aml_root, AML_WALK_PRE, acpi_getpci, sc);
1072
1073	/* attach pci interrupt routing tables */
1074	aml_find_node(&aml_root, "_PRT", acpi_foundprt, sc);
1075
1076	aml_find_node(&aml_root, "_HID", acpi_foundec, sc);
1077
1078	/* check if we're running on a sony */
1079	aml_find_node(&aml_root, "GBRT", acpi_foundsony, sc);
1080
1081	aml_walknodes(&aml_root, AML_WALK_PRE, acpi_add_device, sc);
1082
1083#ifndef SMALL_KERNEL
1084	/* try to find smart battery first */
1085	aml_find_node(&aml_root, "_HID", acpi_foundsbs, sc);
1086#endif /* SMALL_KERNEL */
1087
1088	/* attach battery, power supply and button devices */
1089	aml_find_node(&aml_root, "_HID", acpi_foundhid, sc);
1090
1091#ifndef SMALL_KERNEL
1092#if NWD > 0
1093	/* Attach IDE bay */
1094	aml_walknodes(&aml_root, AML_WALK_PRE, acpi_foundide, sc);
1095#endif
1096
1097	/* attach docks */
1098	aml_find_node(&aml_root, "_DCK", acpi_founddock, sc);
1099
1100	/* attach video */
1101	aml_find_node(&aml_root, "_DOS", acpi_foundvideo, sc);
1102
1103	/* create list of devices we want to query when APM comes in */
1104	SLIST_INIT(&sc->sc_ac);
1105	SLIST_INIT(&sc->sc_bat);
1106	TAILQ_FOREACH(dev, &alldevs, dv_list) {
1107		if (!strcmp(dev->dv_cfdata->cf_driver->cd_name, "acpiac")) {
1108			struct acpi_ac *ac;
1109
1110			ac = malloc(sizeof(*ac), M_DEVBUF, M_WAITOK | M_ZERO);
1111			ac->aac_softc = (struct acpiac_softc *)dev;
1112			SLIST_INSERT_HEAD(&sc->sc_ac, ac, aac_link);
1113		} else if (!strcmp(dev->dv_cfdata->cf_driver->cd_name, "acpibat")) {
1114			struct acpi_bat *bat;
1115
1116			bat = malloc(sizeof(*bat), M_DEVBUF, M_WAITOK | M_ZERO);
1117			bat->aba_softc = (struct acpibat_softc *)dev;
1118			SLIST_INSERT_HEAD(&sc->sc_bat, bat, aba_link);
1119		} else if (!strcmp(dev->dv_cfdata->cf_driver->cd_name, "acpisbs")) {
1120			struct acpi_sbs *sbs;
1121
1122			sbs = malloc(sizeof(*sbs), M_DEVBUF, M_WAITOK | M_ZERO);
1123			sbs->asbs_softc = (struct acpisbs_softc *)dev;
1124			SLIST_INSERT_HEAD(&sc->sc_sbs, sbs, asbs_link);
1125		}
1126	}
1127
1128#endif /* SMALL_KERNEL */
1129
1130	/* Setup threads */
1131	sc->sc_thread = malloc(sizeof(struct acpi_thread), M_DEVBUF, M_WAITOK);
1132	sc->sc_thread->sc = sc;
1133	sc->sc_thread->running = 1;
1134
1135	/* Enable PCI Power Management. */
1136	pci_dopm = 1;
1137
1138	acpi_attach_machdep(sc);
1139
1140	kthread_create_deferred(acpi_create_thread, sc);
1141}
1142
1143int
1144acpi_submatch(struct device *parent, void *match, void *aux)
1145{
1146	struct acpi_attach_args *aaa = (struct acpi_attach_args *)aux;
1147	struct cfdata *cf = match;
1148
1149	if (aaa->aaa_table == NULL)
1150		return (0);
1151	return ((*cf->cf_attach->ca_match)(parent, match, aux));
1152}
1153
1154int
1155acpi_print(void *aux, const char *pnp)
1156{
1157	struct acpi_attach_args *aa = aux;
1158
1159	if (pnp) {
1160		if (aa->aaa_name)
1161			printf("%s at %s", aa->aaa_name, pnp);
1162		else if (aa->aaa_dev)
1163			printf("\"%s\" at %s", aa->aaa_dev, pnp);
1164		else
1165			return (QUIET);
1166	}
1167
1168	return (UNCONF);
1169}
1170
1171struct acpi_q *
1172acpi_maptable(struct acpi_softc *sc, paddr_t addr, const char *sig,
1173    const char *oem, const char *tbl, int flag)
1174{
1175	static int tblid;
1176	struct acpi_mem_map handle;
1177	struct acpi_table_header *hdr;
1178	struct acpi_q *entry;
1179	size_t len;
1180
1181	/* Check if we can map address */
1182	if (addr == 0)
1183		return NULL;
1184	if (acpi_map(addr, sizeof(*hdr), &handle))
1185		return NULL;
1186	hdr = (struct acpi_table_header *)handle.va;
1187	len = hdr->length;
1188	acpi_unmap(&handle);
1189
1190	/* Validate length/checksum */
1191	if (acpi_map(addr, len, &handle))
1192		return NULL;
1193	hdr = (struct acpi_table_header *)handle.va;
1194	if (acpi_checksum(hdr, len))
1195		printf("\n%s: %.4s checksum error",
1196		    DEVNAME(sc), hdr->signature);
1197
1198	if ((sig && memcmp(sig, hdr->signature, 4)) ||
1199	    (oem && memcmp(oem, hdr->oemid, 6)) ||
1200	    (tbl && memcmp(tbl, hdr->oemtableid, 8))) {
1201		acpi_unmap(&handle);
1202		return NULL;
1203	}
1204
1205	/* Allocate copy */
1206	entry = malloc(sizeof(*entry) + len, M_DEVBUF, M_NOWAIT);
1207	if (entry != NULL) {
1208		memcpy(entry->q_data, handle.va, len);
1209		entry->q_table = entry->q_data;
1210		entry->q_id = ++tblid;
1211
1212		if (flag < 0)
1213			SIMPLEQ_INSERT_HEAD(&sc->sc_tables, entry,
1214			    q_next);
1215		else if (flag > 0)
1216			SIMPLEQ_INSERT_TAIL(&sc->sc_tables, entry,
1217			    q_next);
1218	}
1219	acpi_unmap(&handle);
1220	return entry;
1221}
1222
1223int
1224acpi_loadtables(struct acpi_softc *sc, struct acpi_rsdp *rsdp)
1225{
1226	struct acpi_q *sdt;
1227	int i, ntables;
1228	size_t len;
1229
1230	if (rsdp->rsdp_revision == 2 && rsdp->rsdp_xsdt) {
1231		struct acpi_xsdt *xsdt;
1232
1233		sdt = acpi_maptable(sc, rsdp->rsdp_xsdt, NULL, NULL, NULL, 0);
1234		if (sdt == NULL) {
1235			printf("couldn't map rsdt\n");
1236			return (ENOMEM);
1237		}
1238
1239		xsdt = (struct acpi_xsdt *)sdt->q_data;
1240		len  = xsdt->hdr.length;
1241		ntables = (len - sizeof(struct acpi_table_header)) /
1242		    sizeof(xsdt->table_offsets[0]);
1243
1244		for (i = 0; i < ntables; i++)
1245			acpi_maptable(sc, xsdt->table_offsets[i], NULL, NULL,
1246			    NULL, 1);
1247
1248		free(sdt, M_DEVBUF, 0);
1249	} else {
1250		struct acpi_rsdt *rsdt;
1251
1252		sdt = acpi_maptable(sc, rsdp->rsdp_rsdt, NULL, NULL, NULL, 0);
1253		if (sdt == NULL) {
1254			printf("couldn't map rsdt\n");
1255			return (ENOMEM);
1256		}
1257
1258		rsdt = (struct acpi_rsdt *)sdt->q_data;
1259		len  = rsdt->hdr.length;
1260		ntables = (len - sizeof(struct acpi_table_header)) /
1261		    sizeof(rsdt->table_offsets[0]);
1262
1263		for (i = 0; i < ntables; i++)
1264			acpi_maptable(sc, rsdt->table_offsets[i], NULL, NULL,
1265			    NULL, 1);
1266
1267		free(sdt, M_DEVBUF, 0);
1268	}
1269
1270	return (0);
1271}
1272
1273/* Read from power management register */
1274int
1275acpi_read_pmreg(struct acpi_softc *sc, int reg, int offset)
1276{
1277	bus_space_handle_t ioh;
1278	bus_size_t size;
1279	int regval;
1280
1281	/*
1282	 * For Hardware-reduced ACPI we emulate PM1B_CNT to reflect
1283	 * that the system is always in ACPI mode.
1284	 */
1285	if (sc->sc_hw_reduced && reg == ACPIREG_PM1B_CNT) {
1286		KASSERT(offset == 0);
1287		return ACPI_PM1_SCI_EN;
1288	}
1289
1290	/*
1291	 * For Hardware-reduced ACPI we also emulate PM1A_STS using
1292	 * SLEEP_STATUS_REG.
1293	 */
1294	if (sc->sc_hw_reduced && reg == ACPIREG_PM1A_STS) {
1295		uint8_t value;
1296
1297		KASSERT(offset == 0);
1298		acpi_gasio(sc, ACPI_IOREAD,
1299		    sc->sc_fadt->sleep_status_reg.address_space_id,
1300		    sc->sc_fadt->sleep_status_reg.address,
1301		    sc->sc_fadt->sleep_status_reg.register_bit_width / 8,
1302		    sc->sc_fadt->sleep_status_reg.access_size, &value);
1303		return ((int)value << 8);
1304	}
1305
1306	/* Special cases: 1A/1B blocks can be OR'ed together */
1307	switch (reg) {
1308	case ACPIREG_PM1_EN:
1309		return (acpi_read_pmreg(sc, ACPIREG_PM1A_EN, offset) |
1310		    acpi_read_pmreg(sc, ACPIREG_PM1B_EN, offset));
1311	case ACPIREG_PM1_STS:
1312		return (acpi_read_pmreg(sc, ACPIREG_PM1A_STS, offset) |
1313		    acpi_read_pmreg(sc, ACPIREG_PM1B_STS, offset));
1314	case ACPIREG_PM1_CNT:
1315		return (acpi_read_pmreg(sc, ACPIREG_PM1A_CNT, offset) |
1316		    acpi_read_pmreg(sc, ACPIREG_PM1B_CNT, offset));
1317	case ACPIREG_GPE_STS:
1318		dnprintf(50, "read GPE_STS  offset: %.2x %.2x %.2x\n", offset,
1319		    sc->sc_fadt->gpe0_blk_len>>1, sc->sc_fadt->gpe1_blk_len>>1);
1320		if (offset < (sc->sc_fadt->gpe0_blk_len >> 1)) {
1321			reg = ACPIREG_GPE0_STS;
1322		}
1323		break;
1324	case ACPIREG_GPE_EN:
1325		dnprintf(50, "read GPE_EN   offset: %.2x %.2x %.2x\n",
1326		    offset, sc->sc_fadt->gpe0_blk_len>>1,
1327		    sc->sc_fadt->gpe1_blk_len>>1);
1328		if (offset < (sc->sc_fadt->gpe0_blk_len >> 1)) {
1329			reg = ACPIREG_GPE0_EN;
1330		}
1331		break;
1332	}
1333
1334	if (reg >= ACPIREG_MAXREG || sc->sc_pmregs[reg].size == 0)
1335		return (0);
1336
1337	regval = 0;
1338	ioh = sc->sc_pmregs[reg].ioh;
1339	size = sc->sc_pmregs[reg].size;
1340	if (size > sc->sc_pmregs[reg].access)
1341		size = sc->sc_pmregs[reg].access;
1342
1343	switch (size) {
1344	case 1:
1345		regval = bus_space_read_1(sc->sc_iot, ioh, offset);
1346		break;
1347	case 2:
1348		regval = bus_space_read_2(sc->sc_iot, ioh, offset);
1349		break;
1350	case 4:
1351		regval = bus_space_read_4(sc->sc_iot, ioh, offset);
1352		break;
1353	}
1354
1355	dnprintf(30, "acpi_readpm: %s = %.4x:%.4x %x\n",
1356	    sc->sc_pmregs[reg].name,
1357	    sc->sc_pmregs[reg].addr, offset, regval);
1358	return (regval);
1359}
1360
1361/* Write to power management register */
1362void
1363acpi_write_pmreg(struct acpi_softc *sc, int reg, int offset, int regval)
1364{
1365	bus_space_handle_t ioh;
1366	bus_size_t size;
1367
1368	/*
1369	 * For Hardware-reduced ACPI we also emulate PM1A_STS using
1370	 * SLEEP_STATUS_REG.
1371	 */
1372	if (sc->sc_hw_reduced && reg == ACPIREG_PM1A_STS) {
1373		uint8_t value = (regval >> 8);
1374
1375		KASSERT(offset == 0);
1376		acpi_gasio(sc, ACPI_IOWRITE,
1377		    sc->sc_fadt->sleep_status_reg.address_space_id,
1378		    sc->sc_fadt->sleep_status_reg.address,
1379		    sc->sc_fadt->sleep_status_reg.register_bit_width / 8,
1380		    sc->sc_fadt->sleep_status_reg.access_size, &value);
1381		return;
1382	}
1383
1384	/*
1385	 * For Hardware-reduced ACPI we also emulate PM1A_CNT using
1386	 * SLEEP_CONTROL_REG.
1387	 */
1388	if (sc->sc_hw_reduced && reg == ACPIREG_PM1A_CNT) {
1389		uint8_t value = (regval >> 8);
1390
1391		KASSERT(offset == 0);
1392		acpi_gasio(sc, ACPI_IOWRITE,
1393		    sc->sc_fadt->sleep_control_reg.address_space_id,
1394		    sc->sc_fadt->sleep_control_reg.address,
1395		    sc->sc_fadt->sleep_control_reg.register_bit_width / 8,
1396		    sc->sc_fadt->sleep_control_reg.access_size, &value);
1397		return;
1398	}
1399
1400	/* Special cases: 1A/1B blocks can be written with same value */
1401	switch (reg) {
1402	case ACPIREG_PM1_EN:
1403		acpi_write_pmreg(sc, ACPIREG_PM1A_EN, offset, regval);
1404		acpi_write_pmreg(sc, ACPIREG_PM1B_EN, offset, regval);
1405		break;
1406	case ACPIREG_PM1_STS:
1407		acpi_write_pmreg(sc, ACPIREG_PM1A_STS, offset, regval);
1408		acpi_write_pmreg(sc, ACPIREG_PM1B_STS, offset, regval);
1409		break;
1410	case ACPIREG_PM1_CNT:
1411		acpi_write_pmreg(sc, ACPIREG_PM1A_CNT, offset, regval);
1412		acpi_write_pmreg(sc, ACPIREG_PM1B_CNT, offset, regval);
1413		break;
1414	case ACPIREG_GPE_STS:
1415		dnprintf(50, "write GPE_STS offset: %.2x %.2x %.2x %.2x\n",
1416		    offset, sc->sc_fadt->gpe0_blk_len>>1,
1417		    sc->sc_fadt->gpe1_blk_len>>1, regval);
1418		if (offset < (sc->sc_fadt->gpe0_blk_len >> 1)) {
1419			reg = ACPIREG_GPE0_STS;
1420		}
1421		break;
1422	case ACPIREG_GPE_EN:
1423		dnprintf(50, "write GPE_EN  offset: %.2x %.2x %.2x %.2x\n",
1424		    offset, sc->sc_fadt->gpe0_blk_len>>1,
1425		    sc->sc_fadt->gpe1_blk_len>>1, regval);
1426		if (offset < (sc->sc_fadt->gpe0_blk_len >> 1)) {
1427			reg = ACPIREG_GPE0_EN;
1428		}
1429		break;
1430	}
1431
1432	/* All special case return here */
1433	if (reg >= ACPIREG_MAXREG)
1434		return;
1435
1436	ioh = sc->sc_pmregs[reg].ioh;
1437	size = sc->sc_pmregs[reg].size;
1438	if (size > sc->sc_pmregs[reg].access)
1439		size = sc->sc_pmregs[reg].access;
1440
1441	switch (size) {
1442	case 1:
1443		bus_space_write_1(sc->sc_iot, ioh, offset, regval);
1444		break;
1445	case 2:
1446		bus_space_write_2(sc->sc_iot, ioh, offset, regval);
1447		break;
1448	case 4:
1449		bus_space_write_4(sc->sc_iot, ioh, offset, regval);
1450		break;
1451	}
1452
1453	dnprintf(30, "acpi_writepm: %s = %.4x:%.4x %x\n",
1454	    sc->sc_pmregs[reg].name, sc->sc_pmregs[reg].addr, offset, regval);
1455}
1456
1457/* Map Power Management registers */
1458void
1459acpi_map_pmregs(struct acpi_softc *sc)
1460{
1461	bus_addr_t addr;
1462	bus_size_t size, access;
1463	const char *name;
1464	int reg;
1465
1466	/* Registers don't exist on Hardware-reduced ACPI. */
1467	if (sc->sc_hw_reduced)
1468		return;
1469
1470	for (reg = 0; reg < ACPIREG_MAXREG; reg++) {
1471		size = 0;
1472		access = 0;
1473		switch (reg) {
1474		case ACPIREG_SMICMD:
1475			name = "smi";
1476			size = access = 1;
1477			addr = sc->sc_fadt->smi_cmd;
1478			break;
1479		case ACPIREG_PM1A_STS:
1480		case ACPIREG_PM1A_EN:
1481			name = "pm1a_sts";
1482			size = sc->sc_fadt->pm1_evt_len >> 1;
1483			addr = sc->sc_fadt->pm1a_evt_blk;
1484			access = 2;
1485			if (reg == ACPIREG_PM1A_EN && addr) {
1486				addr += size;
1487				name = "pm1a_en";
1488			}
1489			break;
1490		case ACPIREG_PM1A_CNT:
1491			name = "pm1a_cnt";
1492			size = sc->sc_fadt->pm1_cnt_len;
1493			addr = sc->sc_fadt->pm1a_cnt_blk;
1494			access = 2;
1495			break;
1496		case ACPIREG_PM1B_STS:
1497		case ACPIREG_PM1B_EN:
1498			name = "pm1b_sts";
1499			size = sc->sc_fadt->pm1_evt_len >> 1;
1500			addr = sc->sc_fadt->pm1b_evt_blk;
1501			access = 2;
1502			if (reg == ACPIREG_PM1B_EN && addr) {
1503				addr += size;
1504				name = "pm1b_en";
1505			}
1506			break;
1507		case ACPIREG_PM1B_CNT:
1508			name = "pm1b_cnt";
1509			size = sc->sc_fadt->pm1_cnt_len;
1510			addr = sc->sc_fadt->pm1b_cnt_blk;
1511			access = 2;
1512			break;
1513		case ACPIREG_PM2_CNT:
1514			name = "pm2_cnt";
1515			size = sc->sc_fadt->pm2_cnt_len;
1516			addr = sc->sc_fadt->pm2_cnt_blk;
1517			access = size;
1518			break;
1519#if 0
1520		case ACPIREG_PM_TMR:
1521			/* Allocated in acpitimer */
1522			name = "pm_tmr";
1523			size = sc->sc_fadt->pm_tmr_len;
1524			addr = sc->sc_fadt->pm_tmr_blk;
1525			access = 4;
1526			break;
1527#endif
1528		case ACPIREG_GPE0_STS:
1529		case ACPIREG_GPE0_EN:
1530			name = "gpe0_sts";
1531			size = sc->sc_fadt->gpe0_blk_len >> 1;
1532			addr = sc->sc_fadt->gpe0_blk;
1533			access = 1;
1534
1535			dnprintf(20, "gpe0 block len : %x\n",
1536			    sc->sc_fadt->gpe0_blk_len >> 1);
1537			dnprintf(20, "gpe0 block addr: %x\n",
1538			    sc->sc_fadt->gpe0_blk);
1539			if (reg == ACPIREG_GPE0_EN && addr) {
1540				addr += size;
1541				name = "gpe0_en";
1542			}
1543			break;
1544		case ACPIREG_GPE1_STS:
1545		case ACPIREG_GPE1_EN:
1546			name = "gpe1_sts";
1547			size = sc->sc_fadt->gpe1_blk_len >> 1;
1548			addr = sc->sc_fadt->gpe1_blk;
1549			access = 1;
1550
1551			dnprintf(20, "gpe1 block len : %x\n",
1552			    sc->sc_fadt->gpe1_blk_len >> 1);
1553			dnprintf(20, "gpe1 block addr: %x\n",
1554			    sc->sc_fadt->gpe1_blk);
1555			if (reg == ACPIREG_GPE1_EN && addr) {
1556				addr += size;
1557				name = "gpe1_en";
1558			}
1559			break;
1560		}
1561		if (size && addr) {
1562			dnprintf(50, "mapping: %.4lx %.4lx %s\n",
1563			    addr, size, name);
1564
1565			/* Size and address exist; map register space */
1566			bus_space_map(sc->sc_iot, addr, size, 0,
1567			    &sc->sc_pmregs[reg].ioh);
1568
1569			sc->sc_pmregs[reg].name = name;
1570			sc->sc_pmregs[reg].size = size;
1571			sc->sc_pmregs[reg].addr = addr;
1572			sc->sc_pmregs[reg].access = min(access, 4);
1573		}
1574	}
1575}
1576
1577void
1578acpi_unmap_pmregs(struct acpi_softc *sc)
1579{
1580	int reg;
1581
1582	for (reg = 0; reg < ACPIREG_MAXREG; reg++) {
1583		if (sc->sc_pmregs[reg].size && sc->sc_pmregs[reg].addr)
1584			bus_space_unmap(sc->sc_iot, sc->sc_pmregs[reg].ioh,
1585			    sc->sc_pmregs[reg].size);
1586	}
1587}
1588
1589int
1590acpi_enable(struct acpi_softc *sc)
1591{
1592	int idx;
1593
1594	acpi_write_pmreg(sc, ACPIREG_SMICMD, 0, sc->sc_fadt->acpi_enable);
1595	idx = 0;
1596	do {
1597		if (idx++ > ACPIEN_RETRIES) {
1598			return ETIMEDOUT;
1599		}
1600	} while (!(acpi_read_pmreg(sc, ACPIREG_PM1_CNT, 0) & ACPI_PM1_SCI_EN));
1601
1602	return 0;
1603}
1604
1605/* ACPI Workqueue support */
1606SIMPLEQ_HEAD(,acpi_taskq) acpi_taskq =
1607    SIMPLEQ_HEAD_INITIALIZER(acpi_taskq);
1608
1609void
1610acpi_addtask(struct acpi_softc *sc, void (*handler)(void *, int),
1611    void *arg0, int arg1)
1612{
1613	struct acpi_taskq *wq;
1614	int s;
1615
1616	wq = malloc(sizeof(*wq), M_DEVBUF, M_ZERO | M_NOWAIT);
1617	if (wq == NULL)
1618		return;
1619	wq->handler = handler;
1620	wq->arg0 = arg0;
1621	wq->arg1 = arg1;
1622
1623	s = spltty();
1624	SIMPLEQ_INSERT_TAIL(&acpi_taskq, wq, next);
1625	splx(s);
1626}
1627
1628int
1629acpi_dotask(struct acpi_softc *sc)
1630{
1631	struct acpi_taskq *wq;
1632	int s;
1633
1634	s = spltty();
1635	if (SIMPLEQ_EMPTY(&acpi_taskq)) {
1636		splx(s);
1637
1638		/* we don't have anything to do */
1639		return (0);
1640	}
1641	wq = SIMPLEQ_FIRST(&acpi_taskq);
1642	SIMPLEQ_REMOVE_HEAD(&acpi_taskq, next);
1643	splx(s);
1644
1645	wq->handler(wq->arg0, wq->arg1);
1646
1647	free(wq, M_DEVBUF, sizeof(*wq));
1648
1649	/* We did something */
1650	return (1);
1651}
1652
1653#ifndef SMALL_KERNEL
1654
1655int
1656is_ata(struct aml_node *node)
1657{
1658	return (aml_searchname(node, "_GTM") != NULL ||
1659	    aml_searchname(node, "_GTF") != NULL ||
1660	    aml_searchname(node, "_STM") != NULL ||
1661	    aml_searchname(node, "_SDD") != NULL);
1662}
1663
1664int
1665is_ejectable(struct aml_node *node)
1666{
1667	return (aml_searchname(node, "_EJ0") != NULL);
1668}
1669
1670int
1671is_ejectable_bay(struct aml_node *node)
1672{
1673	return ((is_ata(node) || is_ata(node->parent)) && is_ejectable(node));
1674}
1675
1676#if NWD > 0
1677int
1678acpiide_notify(struct aml_node *node, int ntype, void *arg)
1679{
1680	struct idechnl 		*ide = arg;
1681	struct acpi_softc 	*sc = ide->sc;
1682	struct pciide_softc 	*wsc;
1683	struct device 		*dev;
1684	int 			b,d,f;
1685	int64_t 		sta;
1686
1687	if (aml_evalinteger(sc, node, "_STA", 0, NULL, &sta) != 0)
1688		return (0);
1689
1690	dnprintf(10, "IDE notify! %s %d status:%llx\n", aml_nodename(node),
1691	    ntype, sta);
1692
1693	/* Walk device list looking for IDE device match */
1694	TAILQ_FOREACH(dev, &alldevs, dv_list) {
1695		if (strcmp(dev->dv_cfdata->cf_driver->cd_name, "pciide"))
1696			continue;
1697
1698		wsc = (struct pciide_softc *)dev;
1699		pci_decompose_tag(NULL, wsc->sc_tag, &b, &d, &f);
1700		if (b != ACPI_PCI_BUS(ide->addr) ||
1701		    d != ACPI_PCI_DEV(ide->addr) ||
1702		    f != ACPI_PCI_FN(ide->addr))
1703			continue;
1704		dnprintf(10, "Found pciide: %s %x.%x.%x channel:%llx\n",
1705		    dev->dv_xname, b,d,f, ide->chnl);
1706
1707		if (sta == 0 && ide->sta)
1708			wdcdetach(
1709			    &wsc->pciide_channels[ide->chnl].wdc_channel, 0);
1710		else if (sta && !ide->sta)
1711			wdcattach(
1712			    &wsc->pciide_channels[ide->chnl].wdc_channel);
1713		ide->sta = sta;
1714	}
1715	return (0);
1716}
1717
1718int
1719acpi_foundide(struct aml_node *node, void *arg)
1720{
1721	struct acpi_softc 	*sc = arg;
1722	struct aml_node 	*pp;
1723	struct idechnl 		*ide;
1724	union amlpci_t 		pi;
1725	int 			lvl;
1726
1727	/* Check if this is an ejectable bay */
1728	if (!is_ejectable_bay(node))
1729		return (0);
1730
1731	ide = malloc(sizeof(struct idechnl), M_DEVBUF, M_NOWAIT | M_ZERO);
1732	ide->sc = sc;
1733
1734	/* GTM/GTF can be at 2/3 levels:  pciX.ideX.channelX[.driveX] */
1735	lvl = 0;
1736	for (pp=node->parent; pp; pp=pp->parent) {
1737		lvl++;
1738		if (aml_searchname(pp, "_HID"))
1739			break;
1740	}
1741
1742	/* Get PCI address and channel */
1743	if (lvl == 3) {
1744		aml_evalinteger(sc, node->parent, "_ADR", 0, NULL,
1745		    &ide->chnl);
1746		aml_rdpciaddr(node->parent->parent, &pi);
1747		ide->addr = pi.addr;
1748	} else if (lvl == 4) {
1749		aml_evalinteger(sc, node->parent->parent, "_ADR", 0, NULL,
1750		    &ide->chnl);
1751		aml_rdpciaddr(node->parent->parent->parent, &pi);
1752		ide->addr = pi.addr;
1753	}
1754	dnprintf(10, "%s %llx channel:%llx\n",
1755	    aml_nodename(node), ide->addr, ide->chnl);
1756
1757	aml_evalinteger(sc, node, "_STA", 0, NULL, &ide->sta);
1758	dnprintf(10, "Got Initial STA: %llx\n", ide->sta);
1759
1760	aml_register_notify(node, "acpiide", acpiide_notify, ide, 0);
1761	return (0);
1762}
1763#endif /* NWD > 0 */
1764
1765void
1766acpi_sleep_task(void *arg0, int sleepmode)
1767{
1768	struct acpi_softc *sc = arg0;
1769	struct acpi_ac *ac;
1770	struct acpi_bat *bat;
1771	struct acpi_sbs *sbs;
1772
1773	/* System goes to sleep here.. */
1774	acpi_sleep_state(sc, sleepmode);
1775
1776	/* AC and battery information needs refreshing */
1777	SLIST_FOREACH(ac, &sc->sc_ac, aac_link)
1778		aml_notify(ac->aac_softc->sc_devnode, 0x80);
1779	SLIST_FOREACH(bat, &sc->sc_bat, aba_link)
1780		aml_notify(bat->aba_softc->sc_devnode, 0x80);
1781	SLIST_FOREACH(sbs, &sc->sc_sbs, asbs_link)
1782		aml_notify(sbs->asbs_softc->sc_devnode, 0x80);
1783}
1784
1785#endif /* SMALL_KERNEL */
1786
1787void
1788acpi_reset(void)
1789{
1790	u_int32_t		 reset_as, reset_len;
1791	u_int32_t		 value;
1792	struct acpi_softc	*sc = acpi_softc;
1793	struct acpi_fadt	*fadt = sc->sc_fadt;
1794
1795	if (acpi_enabled == 0)
1796		return;
1797
1798	/*
1799	 * RESET_REG_SUP is not properly set in some implementations,
1800	 * but not testing against it breaks more machines than it fixes
1801	 */
1802	if (fadt->hdr_revision <= 1 ||
1803	    !(fadt->flags & FADT_RESET_REG_SUP) || fadt->reset_reg.address == 0)
1804		return;
1805
1806	value = fadt->reset_value;
1807
1808	reset_as = fadt->reset_reg.register_bit_width / 8;
1809	if (reset_as == 0)
1810		reset_as = 1;
1811
1812	reset_len = fadt->reset_reg.access_size;
1813	if (reset_len == 0)
1814		reset_len = reset_as;
1815
1816	acpi_gasio(sc, ACPI_IOWRITE,
1817	    fadt->reset_reg.address_space_id,
1818	    fadt->reset_reg.address, reset_as, reset_len, &value);
1819
1820	delay(100000);
1821}
1822
1823void
1824acpi_gpe_task(void *arg0, int gpe)
1825{
1826	struct acpi_softc *sc = acpi_softc;
1827	struct gpe_block *pgpe = &sc->gpe_table[gpe];
1828
1829	dnprintf(10, "handle gpe: %x\n", gpe);
1830	if (pgpe->handler && pgpe->active) {
1831		pgpe->active = 0;
1832		pgpe->handler(sc, gpe, pgpe->arg);
1833	}
1834}
1835
1836void
1837acpi_pbtn_task(void *arg0, int dummy)
1838{
1839	struct acpi_softc *sc = arg0;
1840	uint16_t en;
1841	int s;
1842
1843	dnprintf(1,"power button pressed\n");
1844
1845	/* Reset the latch and re-enable the GPE */
1846	s = spltty();
1847	en = acpi_read_pmreg(sc, ACPIREG_PM1_EN, 0);
1848	acpi_write_pmreg(sc, ACPIREG_PM1_EN,  0,
1849	    en | ACPI_PM1_PWRBTN_EN);
1850	splx(s);
1851
1852	acpi_addtask(sc, acpi_powerdown_task, sc, 0);
1853}
1854
1855void
1856acpi_sbtn_task(void *arg0, int dummy)
1857{
1858	struct acpi_softc *sc = arg0;
1859	uint16_t en;
1860	int s;
1861
1862	dnprintf(1,"sleep button pressed\n");
1863	aml_notify_dev(ACPI_DEV_SBD, 0x80);
1864
1865	/* Reset the latch and re-enable the GPE */
1866	s = spltty();
1867	en = acpi_read_pmreg(sc, ACPIREG_PM1_EN, 0);
1868	acpi_write_pmreg(sc, ACPIREG_PM1_EN,  0,
1869	    en | ACPI_PM1_SLPBTN_EN);
1870	splx(s);
1871}
1872
1873void
1874acpi_powerdown_task(void *arg0, int dummy)
1875{
1876	extern int allowpowerdown;
1877
1878	if (allowpowerdown == 1) {
1879		allowpowerdown = 0;
1880		prsignal(initprocess, SIGUSR2);
1881	}
1882}
1883
1884int
1885acpi_interrupt(void *arg)
1886{
1887	struct acpi_softc *sc = (struct acpi_softc *)arg;
1888	u_int32_t processed = 0, idx, jdx;
1889	u_int16_t sts, en;
1890
1891	dnprintf(40, "ACPI Interrupt\n");
1892	for (idx = 0; idx < sc->sc_lastgpe; idx += 8) {
1893		sts = acpi_read_pmreg(sc, ACPIREG_GPE_STS, idx>>3);
1894		en  = acpi_read_pmreg(sc, ACPIREG_GPE_EN,  idx>>3);
1895		if (en & sts) {
1896			dnprintf(10, "GPE block: %.2x %.2x %.2x\n", idx, sts,
1897			    en);
1898			/* Mask the GPE until it is serviced */
1899			acpi_write_pmreg(sc, ACPIREG_GPE_EN, idx>>3, en & ~sts);
1900			for (jdx = 0; jdx < 8; jdx++) {
1901				if (en & sts & (1L << jdx)) {
1902					/* Signal this GPE */
1903					sc->gpe_table[idx+jdx].active = 1;
1904					dnprintf(10, "queue gpe: %x\n", idx+jdx);
1905					acpi_addtask(sc, acpi_gpe_task, NULL, idx+jdx);
1906
1907					/*
1908					 * Edge interrupts need their STS bits
1909					 * cleared now.  Level interrupts will
1910					 * have their STS bits cleared just
1911					 * before they are re-enabled.
1912					 */
1913					if (sc->gpe_table[idx+jdx].edge)
1914						acpi_write_pmreg(sc,
1915						    ACPIREG_GPE_STS, idx>>3,
1916						    1L << jdx);
1917					processed = 1;
1918				}
1919			}
1920		}
1921	}
1922
1923	sts = acpi_read_pmreg(sc, ACPIREG_PM1_STS, 0);
1924	en  = acpi_read_pmreg(sc, ACPIREG_PM1_EN, 0);
1925	if (sts & en) {
1926		dnprintf(10,"GEN interrupt: %.4x\n", sts & en);
1927		sts &= en;
1928		if (sts & ACPI_PM1_PWRBTN_STS) {
1929			/* Mask and acknowledge */
1930			en &= ~ACPI_PM1_PWRBTN_EN;
1931			acpi_write_pmreg(sc, ACPIREG_PM1_EN, 0, en);
1932			acpi_write_pmreg(sc, ACPIREG_PM1_STS, 0,
1933			    ACPI_PM1_PWRBTN_STS);
1934			sts &= ~ACPI_PM1_PWRBTN_STS;
1935
1936			acpi_addtask(sc, acpi_pbtn_task, sc, 0);
1937		}
1938		if (sts & ACPI_PM1_SLPBTN_STS) {
1939			/* Mask and acknowledge */
1940			en &= ~ACPI_PM1_SLPBTN_EN;
1941			acpi_write_pmreg(sc, ACPIREG_PM1_EN, 0, en);
1942			acpi_write_pmreg(sc, ACPIREG_PM1_STS, 0,
1943			    ACPI_PM1_SLPBTN_STS);
1944			sts &= ~ACPI_PM1_SLPBTN_STS;
1945
1946			acpi_addtask(sc, acpi_sbtn_task, sc, 0);
1947		}
1948		if (sts) {
1949			printf("%s: PM1 stuck (en 0x%x st 0x%x), clearing\n",
1950			    sc->sc_dev.dv_xname, en, sts);
1951			acpi_write_pmreg(sc, ACPIREG_PM1_EN, 0, en & ~sts);
1952			acpi_write_pmreg(sc, ACPIREG_PM1_STS, 0, sts);
1953		}
1954		processed = 1;
1955	}
1956
1957	if (processed) {
1958		acpi_wakeup(sc);
1959	}
1960
1961	return (processed);
1962}
1963
1964int
1965acpi_add_device(struct aml_node *node, void *arg)
1966{
1967	static int nacpicpus = 0;
1968	struct device *self = arg;
1969	struct acpi_softc *sc = arg;
1970	struct acpi_attach_args aaa;
1971	struct aml_value res;
1972	CPU_INFO_ITERATOR cii;
1973	struct cpu_info *ci;
1974	int proc_id = -1;
1975
1976	memset(&aaa, 0, sizeof(aaa));
1977	aaa.aaa_node = node;
1978	aaa.aaa_iot = sc->sc_iot;
1979	aaa.aaa_memt = sc->sc_memt;
1980	if (node == NULL || node->value == NULL)
1981		return 0;
1982
1983	switch (node->value->type) {
1984	case AML_OBJTYPE_PROCESSOR:
1985		if (nacpicpus >= ncpus)
1986			return 0;
1987		if (aml_evalnode(sc, aaa.aaa_node, 0, NULL, &res) == 0) {
1988			if (res.type == AML_OBJTYPE_PROCESSOR)
1989				proc_id = res.v_processor.proc_id;
1990			aml_freevalue(&res);
1991		}
1992		CPU_INFO_FOREACH(cii, ci) {
1993			if (ci->ci_acpi_proc_id == proc_id)
1994				break;
1995		}
1996		if (ci == NULL)
1997			return 0;
1998		nacpicpus++;
1999
2000		aaa.aaa_name = "acpicpu";
2001		break;
2002	case AML_OBJTYPE_THERMZONE:
2003		aaa.aaa_name = "acpitz";
2004		break;
2005	case AML_OBJTYPE_POWERRSRC:
2006		aaa.aaa_name = "acpipwrres";
2007		break;
2008	default:
2009		return 0;
2010	}
2011	config_found(self, &aaa, acpi_print);
2012	return 0;
2013}
2014
2015void
2016acpi_enable_onegpe(struct acpi_softc *sc, int gpe)
2017{
2018	uint8_t mask, en;
2019
2020	/* Read enabled register */
2021	mask = (1L << (gpe & 7));
2022	en = acpi_read_pmreg(sc, ACPIREG_GPE_EN, gpe>>3);
2023	dnprintf(50, "enabling GPE %.2x (current: %sabled) %.2x\n",
2024	    gpe, (en & mask) ? "en" : "dis", en);
2025	acpi_write_pmreg(sc, ACPIREG_GPE_EN, gpe>>3, en | mask);
2026}
2027
2028/* Clear all GPEs */
2029void
2030acpi_disable_allgpes(struct acpi_softc *sc)
2031{
2032	int idx;
2033
2034	for (idx = 0; idx < sc->sc_lastgpe; idx += 8) {
2035		acpi_write_pmreg(sc, ACPIREG_GPE_EN, idx >> 3, 0);
2036		acpi_write_pmreg(sc, ACPIREG_GPE_STS, idx >> 3, -1);
2037	}
2038}
2039
2040/* Enable runtime GPEs */
2041void
2042acpi_enable_rungpes(struct acpi_softc *sc)
2043{
2044	int idx;
2045
2046	for (idx = 0; idx < sc->sc_lastgpe; idx++)
2047		if (sc->gpe_table[idx].handler)
2048			acpi_enable_onegpe(sc, idx);
2049}
2050
2051/* Enable wakeup GPEs */
2052void
2053acpi_enable_wakegpes(struct acpi_softc *sc, int state)
2054{
2055	struct acpi_wakeq *wentry;
2056
2057	SIMPLEQ_FOREACH(wentry, &sc->sc_wakedevs, q_next) {
2058		dnprintf(10, "%.4s(S%d) gpe %.2x\n", wentry->q_node->name,
2059		    wentry->q_state,
2060		    wentry->q_gpe);
2061		if (state <= wentry->q_state)
2062			acpi_enable_onegpe(sc, wentry->q_gpe);
2063	}
2064}
2065
2066int
2067acpi_set_gpehandler(struct acpi_softc *sc, int gpe, int (*handler)
2068    (struct acpi_softc *, int, void *), void *arg, int edge)
2069{
2070	struct gpe_block *ptbl;
2071
2072	ptbl = acpi_find_gpe(sc, gpe);
2073	if (ptbl == NULL || handler == NULL)
2074		return -EINVAL;
2075	if (ptbl->handler != NULL) {
2076		dnprintf(10, "error: GPE %.2x already enabled\n", gpe);
2077		return -EBUSY;
2078	}
2079	dnprintf(50, "Adding GPE handler %.2x (%s)\n", gpe, edge ? "edge" : "level");
2080	ptbl->handler = handler;
2081	ptbl->arg = arg;
2082	ptbl->edge = edge;
2083
2084	return (0);
2085}
2086
2087int
2088acpi_gpe(struct acpi_softc *sc, int gpe, void *arg)
2089{
2090	struct aml_node *node = arg;
2091	uint8_t mask, en;
2092
2093	dnprintf(10, "handling GPE %.2x\n", gpe);
2094	aml_evalnode(sc, node, 0, NULL, NULL);
2095
2096	mask = (1L << (gpe & 7));
2097	if (!sc->gpe_table[gpe].edge)
2098		acpi_write_pmreg(sc, ACPIREG_GPE_STS, gpe>>3, mask);
2099	en = acpi_read_pmreg(sc, ACPIREG_GPE_EN,  gpe>>3);
2100	acpi_write_pmreg(sc, ACPIREG_GPE_EN,  gpe>>3, en | mask);
2101	return (0);
2102}
2103
2104/* Discover Devices that can wakeup the system
2105 * _PRW returns a package
2106 *  pkg[0] = integer (FADT gpe bit) or package (gpe block,gpe bit)
2107 *  pkg[1] = lowest sleep state
2108 *  pkg[2+] = power resource devices (optional)
2109 *
2110 * To enable wakeup devices:
2111 *    Evaluate _ON method in each power resource device
2112 *    Evaluate _PSW method
2113 */
2114int
2115acpi_foundprw(struct aml_node *node, void *arg)
2116{
2117	struct acpi_softc *sc = arg;
2118	struct acpi_wakeq *wq;
2119	int64_t sta;
2120
2121	if (aml_evalinteger(sc, node->parent, "_STA", 0, NULL, &sta))
2122		sta = STA_PRESENT | STA_ENABLED | STA_DEV_OK | 0x1000;
2123
2124	if ((sta & STA_PRESENT) == 0)
2125		return 0;
2126
2127	wq = malloc(sizeof(struct acpi_wakeq), M_DEVBUF, M_NOWAIT | M_ZERO);
2128	if (wq == NULL)
2129		return 0;
2130
2131	wq->q_wakepkg = malloc(sizeof(struct aml_value), M_DEVBUF,
2132	    M_NOWAIT | M_ZERO);
2133	if (wq->q_wakepkg == NULL) {
2134		free(wq, M_DEVBUF, sizeof(*wq));
2135		return 0;
2136	}
2137	dnprintf(10, "Found _PRW (%s)\n", node->parent->name);
2138	aml_evalnode(sc, node, 0, NULL, wq->q_wakepkg);
2139	wq->q_node = node->parent;
2140	wq->q_gpe = -1;
2141
2142	/* Get GPE of wakeup device, and lowest sleep level */
2143	if (wq->q_wakepkg->type == AML_OBJTYPE_PACKAGE &&
2144	    wq->q_wakepkg->length >= 2) {
2145		if (wq->q_wakepkg->v_package[0]->type == AML_OBJTYPE_INTEGER)
2146			wq->q_gpe = wq->q_wakepkg->v_package[0]->v_integer;
2147		if (wq->q_wakepkg->v_package[1]->type == AML_OBJTYPE_INTEGER)
2148			wq->q_state = wq->q_wakepkg->v_package[1]->v_integer;
2149	}
2150	SIMPLEQ_INSERT_TAIL(&sc->sc_wakedevs, wq, q_next);
2151	return 0;
2152}
2153
2154struct gpe_block *
2155acpi_find_gpe(struct acpi_softc *sc, int gpe)
2156{
2157	if (gpe >= sc->sc_lastgpe)
2158		return NULL;
2159	return &sc->gpe_table[gpe];
2160}
2161
2162void
2163acpi_init_gpes(struct acpi_softc *sc)
2164{
2165	struct aml_node *gpe;
2166	char name[12];
2167	int  idx, ngpe;
2168
2169	sc->sc_lastgpe = sc->sc_fadt->gpe0_blk_len << 2;
2170	if (sc->sc_fadt->gpe1_blk_len) {
2171	}
2172	dnprintf(50, "Last GPE: %.2x\n", sc->sc_lastgpe);
2173
2174	/* Allocate GPE table */
2175	sc->gpe_table = mallocarray(sc->sc_lastgpe, sizeof(struct gpe_block),
2176	    M_DEVBUF, M_WAITOK | M_ZERO);
2177
2178	ngpe = 0;
2179
2180	/* Clear GPE status */
2181	acpi_disable_allgpes(sc);
2182	for (idx = 0; idx < sc->sc_lastgpe; idx++) {
2183		/* Search Level-sensitive GPES */
2184		snprintf(name, sizeof(name), "\\_GPE._L%.2X", idx);
2185		gpe = aml_searchname(&aml_root, name);
2186		if (gpe != NULL)
2187			acpi_set_gpehandler(sc, idx, acpi_gpe, gpe, 0);
2188		if (gpe == NULL) {
2189			/* Search Edge-sensitive GPES */
2190			snprintf(name, sizeof(name), "\\_GPE._E%.2X", idx);
2191			gpe = aml_searchname(&aml_root, name);
2192			if (gpe != NULL)
2193				acpi_set_gpehandler(sc, idx, acpi_gpe, gpe, 1);
2194		}
2195	}
2196	aml_find_node(&aml_root, "_PRW", acpi_foundprw, sc);
2197	sc->sc_maxgpe = ngpe;
2198}
2199
2200void
2201acpi_init_pm(struct acpi_softc *sc)
2202{
2203	sc->sc_tts = aml_searchname(&aml_root, "_TTS");
2204	sc->sc_pts = aml_searchname(&aml_root, "_PTS");
2205	sc->sc_wak = aml_searchname(&aml_root, "_WAK");
2206	sc->sc_bfs = aml_searchname(&aml_root, "_BFS");
2207	sc->sc_gts = aml_searchname(&aml_root, "_GTS");
2208	sc->sc_sst = aml_searchname(&aml_root, "_SI_._SST");
2209}
2210
2211#ifndef SMALL_KERNEL
2212
2213void
2214acpi_init_states(struct acpi_softc *sc)
2215{
2216	struct aml_value res;
2217	char name[8];
2218	int i;
2219
2220	printf("\n%s: sleep states", DEVNAME(sc));
2221	for (i = ACPI_STATE_S0; i <= ACPI_STATE_S5; i++) {
2222		snprintf(name, sizeof(name), "_S%d_", i);
2223		sc->sc_sleeptype[i].slp_typa = -1;
2224		sc->sc_sleeptype[i].slp_typb = -1;
2225		if (aml_evalname(sc, &aml_root, name, 0, NULL, &res) == 0) {
2226			if (res.type == AML_OBJTYPE_PACKAGE) {
2227				sc->sc_sleeptype[i].slp_typa = aml_val2int(res.v_package[0]);
2228				sc->sc_sleeptype[i].slp_typb = aml_val2int(res.v_package[1]);
2229				printf(" S%d", i);
2230			}
2231			aml_freevalue(&res);
2232		}
2233	}
2234}
2235
2236void
2237acpi_sleep_pm(struct acpi_softc *sc, int state)
2238{
2239	uint16_t rega, regb, regra, regrb;
2240	int retry = 0;
2241
2242	disable_intr();
2243
2244	/* Clear WAK_STS bit */
2245	acpi_write_pmreg(sc, ACPIREG_PM1_STS, 0, ACPI_PM1_WAK_STS);
2246
2247	/* Disable BM arbitration at deep sleep and beyond */
2248	if (state >= ACPI_STATE_S3 &&
2249	    sc->sc_fadt->pm2_cnt_blk && sc->sc_fadt->pm2_cnt_len)
2250		acpi_write_pmreg(sc, ACPIREG_PM2_CNT, 0, ACPI_PM2_ARB_DIS);
2251
2252	/* Write SLP_TYPx values */
2253	rega = acpi_read_pmreg(sc, ACPIREG_PM1A_CNT, 0);
2254	regb = acpi_read_pmreg(sc, ACPIREG_PM1B_CNT, 0);
2255	rega &= ~(ACPI_PM1_SLP_TYPX_MASK | ACPI_PM1_SLP_EN);
2256	regb &= ~(ACPI_PM1_SLP_TYPX_MASK | ACPI_PM1_SLP_EN);
2257	rega |= ACPI_PM1_SLP_TYPX(sc->sc_sleeptype[state].slp_typa);
2258	regb |= ACPI_PM1_SLP_TYPX(sc->sc_sleeptype[state].slp_typb);
2259	acpi_write_pmreg(sc, ACPIREG_PM1A_CNT, 0, rega);
2260	acpi_write_pmreg(sc, ACPIREG_PM1B_CNT, 0, regb);
2261
2262	/* Loop on WAK_STS, setting the SLP_EN bits once in a while */
2263	rega |= ACPI_PM1_SLP_EN;
2264	regb |= ACPI_PM1_SLP_EN;
2265	while (1) {
2266		if (retry == 0) {
2267			acpi_write_pmreg(sc, ACPIREG_PM1A_CNT, 0, rega);
2268			acpi_write_pmreg(sc, ACPIREG_PM1B_CNT, 0, regb);
2269		}
2270		retry = (retry + 1) % 100000;
2271
2272		regra = acpi_read_pmreg(sc, ACPIREG_PM1A_STS, 0);
2273		regrb = acpi_read_pmreg(sc, ACPIREG_PM1B_STS, 0);
2274		if ((regra & ACPI_PM1_WAK_STS) ||
2275		    (regrb & ACPI_PM1_WAK_STS))
2276			break;
2277	}
2278}
2279
2280u_int32_t acpi_force_bm;
2281
2282void
2283acpi_resume_pm(struct acpi_softc *sc, int fromstate)
2284{
2285	uint16_t rega, regb, en;
2286
2287	/* Write SLP_TYPx values */
2288	rega = acpi_read_pmreg(sc, ACPIREG_PM1A_CNT, 0);
2289	regb = acpi_read_pmreg(sc, ACPIREG_PM1B_CNT, 0);
2290	rega &= ~(ACPI_PM1_SLP_TYPX_MASK | ACPI_PM1_SLP_EN);
2291	regb &= ~(ACPI_PM1_SLP_TYPX_MASK | ACPI_PM1_SLP_EN);
2292	rega |= ACPI_PM1_SLP_TYPX(sc->sc_sleeptype[ACPI_STATE_S0].slp_typa);
2293	regb |= ACPI_PM1_SLP_TYPX(sc->sc_sleeptype[ACPI_STATE_S0].slp_typb);
2294	acpi_write_pmreg(sc, ACPIREG_PM1A_CNT, 0, rega);
2295	acpi_write_pmreg(sc, ACPIREG_PM1B_CNT, 0, regb);
2296
2297	/* Force SCI_EN on resume to fix horribly broken machines */
2298	acpi_write_pmreg(sc, ACPIREG_PM1_CNT, 0,
2299	    ACPI_PM1_SCI_EN | acpi_force_bm);
2300
2301	/* Clear fixed event status */
2302	acpi_write_pmreg(sc, ACPIREG_PM1_STS, 0, ACPI_PM1_ALL_STS);
2303
2304	/* acpica-reference.pdf page 148 says do not call _BFS */
2305	/* 1st resume AML step: _BFS(fromstate) */
2306	aml_node_setval(sc, sc->sc_bfs, fromstate);
2307
2308	/* Enable runtime GPEs */
2309	acpi_disable_allgpes(sc);
2310	acpi_enable_rungpes(sc);
2311
2312	acpi_indicator(sc, ACPI_SST_WAKING);
2313
2314	/* 2nd resume AML step: _WAK(fromstate) */
2315	aml_node_setval(sc, sc->sc_wak, fromstate);
2316
2317	/* Clear WAK_STS bit */
2318	acpi_write_pmreg(sc, ACPIREG_PM1_STS, 0, ACPI_PM1_WAK_STS);
2319
2320	en = acpi_read_pmreg(sc, ACPIREG_PM1_EN, 0);
2321	if (!(sc->sc_fadt->flags & FADT_PWR_BUTTON))
2322		en |= ACPI_PM1_PWRBTN_EN;
2323	if (!(sc->sc_fadt->flags & FADT_SLP_BUTTON))
2324		en |= ACPI_PM1_SLPBTN_EN;
2325	acpi_write_pmreg(sc, ACPIREG_PM1_EN, 0, en);
2326
2327	/*
2328	 * If PM2 exists, re-enable BM arbitration (reportedly some
2329	 * BIOS forget to)
2330	 */
2331	if (sc->sc_fadt->pm2_cnt_blk && sc->sc_fadt->pm2_cnt_len) {
2332		rega = acpi_read_pmreg(sc, ACPIREG_PM2_CNT, 0);
2333		rega &= ~ACPI_PM2_ARB_DIS;
2334		acpi_write_pmreg(sc, ACPIREG_PM2_CNT, 0, rega);
2335	}
2336}
2337
2338/* Set the indicator light to some state */
2339void
2340acpi_indicator(struct acpi_softc *sc, int led_state)
2341{
2342	static int save_led_state = -1;
2343
2344	if (save_led_state != led_state) {
2345		aml_node_setval(sc, sc->sc_sst, led_state);
2346		save_led_state = led_state;
2347	}
2348}
2349
2350
2351int
2352acpi_sleep_state(struct acpi_softc *sc, int sleepmode)
2353{
2354	extern int perflevel;
2355	extern int lid_action;
2356	int error = ENXIO;
2357	size_t rndbuflen = 0;
2358	char *rndbuf = NULL;
2359	int state, s;
2360
2361	switch (sleepmode) {
2362	case ACPI_SLEEP_SUSPEND:
2363		state = ACPI_STATE_S3;
2364		break;
2365	case ACPI_SLEEP_HIBERNATE:
2366		state = ACPI_STATE_S4;
2367		break;
2368	default:
2369		return (EOPNOTSUPP);
2370	}
2371
2372	if (sc->sc_sleeptype[state].slp_typa == -1 ||
2373	    sc->sc_sleeptype[state].slp_typb == -1) {
2374		printf("%s: state S%d unavailable\n",
2375		    sc->sc_dev.dv_xname, state);
2376		return (EOPNOTSUPP);
2377	}
2378
2379	/* 1st suspend AML step: _TTS(tostate) */
2380	if (aml_node_setval(sc, sc->sc_tts, state) != 0)
2381		goto fail_tts;
2382	acpi_indicator(sc, ACPI_SST_WAKING);	/* blink */
2383
2384#if NWSDISPLAY > 0
2385	/*
2386	 * Temporarily release the lock to prevent the X server from
2387	 * blocking on setting the display brightness.
2388	 */
2389	rw_exit_write(&sc->sc_lck);
2390	wsdisplay_suspend();
2391	rw_enter_write(&sc->sc_lck);
2392#endif /* NWSDISPLAY > 0 */
2393
2394	stop_periodic_resettodr();
2395
2396#ifdef HIBERNATE
2397	if (sleepmode == ACPI_SLEEP_HIBERNATE) {
2398		uvmpd_hibernate();
2399		hibernate_suspend_bufcache();
2400		if (hibernate_alloc()) {
2401			printf("%s: failed to allocate hibernate memory\n",
2402			    sc->sc_dev.dv_xname);
2403			goto fail_alloc;
2404		}
2405	}
2406#endif /* HIBERNATE */
2407
2408	sensor_quiesce();
2409	if (config_suspend_all(DVACT_QUIESCE))
2410		goto fail_quiesce;
2411
2412	bufq_quiesce();
2413
2414#ifdef MULTIPROCESSOR
2415	acpi_sleep_mp();
2416#endif
2417
2418	resettodr();
2419
2420	s = splhigh();
2421	disable_intr();	/* PSL_I for resume; PIC/APIC broken until repair */
2422	cold = 2;	/* Force other code to delay() instead of tsleep() */
2423
2424	if (config_suspend_all(DVACT_SUSPEND) != 0)
2425		goto fail_suspend;
2426	acpi_sleep_clocks(sc, state);
2427
2428	suspend_randomness();
2429
2430	/* 2nd suspend AML step: _PTS(tostate) */
2431	if (aml_node_setval(sc, sc->sc_pts, state) != 0)
2432		goto fail_pts;
2433
2434	acpibtn_enable_psw();	/* enable _LID for wakeup */
2435	acpi_indicator(sc, ACPI_SST_SLEEPING);
2436
2437	/* 3rd suspend AML step: _GTS(tostate) */
2438	aml_node_setval(sc, sc->sc_gts, state);
2439
2440	/* Clear fixed event status */
2441	acpi_write_pmreg(sc, ACPIREG_PM1_STS, 0, ACPI_PM1_ALL_STS);
2442
2443	/* Enable wake GPEs */
2444	acpi_disable_allgpes(sc);
2445	acpi_enable_wakegpes(sc, state);
2446
2447	/* Sleep */
2448	sc->sc_state = state;
2449	error = acpi_sleep_cpu(sc, state);
2450	sc->sc_state = ACPI_STATE_S0;
2451	/* Resume */
2452
2453#ifdef HIBERNATE
2454	if (sleepmode == ACPI_SLEEP_HIBERNATE) {
2455		uvm_pmr_dirty_everything();
2456		hib_getentropy(&rndbuf, &rndbuflen);
2457	}
2458#endif /* HIBERNATE */
2459
2460	acpi_resume_clocks(sc);		/* AML may need clocks */
2461	acpi_resume_pm(sc, state);
2462	acpi_resume_cpu(sc);
2463
2464fail_pts:
2465	config_suspend_all(DVACT_RESUME);
2466
2467fail_suspend:
2468	cold = 0;
2469	enable_intr();
2470	splx(s);
2471
2472	acpibtn_disable_psw();		/* disable _LID for wakeup */
2473	inittodr(time_second);
2474
2475	/* 3rd resume AML step: _TTS(runstate) */
2476	aml_node_setval(sc, sc->sc_tts, sc->sc_state);
2477
2478	resume_randomness(rndbuf, rndbuflen);	/* force RNG upper level reseed */
2479
2480#ifdef MULTIPROCESSOR
2481	acpi_resume_mp();
2482#endif
2483
2484	bufq_restart();
2485
2486fail_quiesce:
2487	config_suspend_all(DVACT_WAKEUP);
2488	sensor_restart();
2489
2490#ifdef HIBERNATE
2491	if (sleepmode == ACPI_SLEEP_HIBERNATE) {
2492		hibernate_free();
2493fail_alloc:
2494		hibernate_resume_bufcache();
2495	}
2496#endif /* HIBERNATE */
2497
2498	start_periodic_resettodr();
2499
2500#if NWSDISPLAY > 0
2501	rw_exit_write(&sc->sc_lck);
2502	wsdisplay_resume();
2503	rw_enter_write(&sc->sc_lck);
2504#endif /* NWSDISPLAY > 0 */
2505
2506	/* Restore hw.setperf */
2507	if (cpu_setperf != NULL)
2508		cpu_setperf(perflevel);
2509
2510	acpi_record_event(sc, APM_NORMAL_RESUME);
2511	acpi_indicator(sc, ACPI_SST_WORKING);
2512
2513	/* If we woke up but all the lids are closed, go back to sleep */
2514	if (acpibtn_numopenlids() == 0 && lid_action != 0)
2515		acpi_addtask(sc, acpi_sleep_task, sc, sleepmode);
2516
2517fail_tts:
2518	return (error);
2519}
2520
2521/* XXX
2522 * We are going to do AML execution but are not in the acpi thread.
2523 * We do not know if the acpi thread is sleeping on acpiec in some
2524 * intermediate context.  Wish us luck.
2525 */
2526void
2527acpi_powerdown(void)
2528{
2529	int state = ACPI_STATE_S5, s;
2530	struct acpi_softc *sc = acpi_softc;
2531
2532	if (acpi_enabled == 0)
2533		return;
2534
2535	s = splhigh();
2536	disable_intr();
2537	cold = 1;
2538
2539	/* 1st powerdown AML step: _PTS(tostate) */
2540	aml_node_setval(sc, sc->sc_pts, state);
2541
2542	acpi_disable_allgpes(sc);
2543	acpi_enable_wakegpes(sc, state);
2544
2545	/* 2nd powerdown AML step: _GTS(tostate) */
2546	aml_node_setval(sc, sc->sc_gts, state);
2547
2548	acpi_sleep_pm(sc, state);
2549	panic("acpi S5 transition did not happen");
2550	while (1)
2551		;
2552}
2553
2554int
2555acpi_map_address(struct acpi_softc *sc, struct acpi_gas *gas, bus_addr_t base,
2556    bus_size_t size, bus_space_handle_t *pioh, bus_space_tag_t *piot)
2557{
2558	int iospace = GAS_SYSTEM_IOSPACE;
2559
2560	/* No GAS structure, default to I/O space */
2561	if (gas != NULL) {
2562		base += gas->address;
2563		iospace = gas->address_space_id;
2564	}
2565	switch (iospace) {
2566	case GAS_SYSTEM_MEMORY:
2567		*piot = sc->sc_memt;
2568		break;
2569	case GAS_SYSTEM_IOSPACE:
2570		*piot = sc->sc_iot;
2571		break;
2572	default:
2573		return -1;
2574	}
2575	if (bus_space_map(*piot, base, size, 0, pioh))
2576		return -1;
2577
2578	return 0;
2579}
2580
2581#endif /* SMALL_KERNEL */
2582
2583void
2584acpi_wakeup(void *arg)
2585{
2586	struct acpi_softc  *sc = (struct acpi_softc *)arg;
2587
2588	sc->sc_threadwaiting = 0;
2589	wakeup(sc);
2590}
2591
2592
2593void
2594acpi_thread(void *arg)
2595{
2596	struct acpi_thread *thread = arg;
2597	struct acpi_softc  *sc = thread->sc;
2598	extern int aml_busy;
2599	int s;
2600
2601	/* AML/SMI cannot be trusted -- only run on the BSP */
2602	sched_peg_curproc(&cpu_info_primary);
2603
2604	rw_enter_write(&sc->sc_lck);
2605
2606	/*
2607	 * If we have an interrupt handler, we can get notification
2608	 * when certain status bits changes in the ACPI registers,
2609	 * so let us enable some events we can forward to userland
2610	 */
2611	if (sc->sc_interrupt) {
2612		int16_t en;
2613
2614		dnprintf(1,"slpbtn:%c  pwrbtn:%c\n",
2615		    sc->sc_fadt->flags & FADT_SLP_BUTTON ? 'n' : 'y',
2616		    sc->sc_fadt->flags & FADT_PWR_BUTTON ? 'n' : 'y');
2617		dnprintf(10, "Enabling acpi interrupts...\n");
2618		sc->sc_threadwaiting = 1;
2619
2620		/* Enable Sleep/Power buttons if they exist */
2621		s = spltty();
2622		en = acpi_read_pmreg(sc, ACPIREG_PM1_EN, 0);
2623		if (!(sc->sc_fadt->flags & FADT_PWR_BUTTON))
2624			en |= ACPI_PM1_PWRBTN_EN;
2625		if (!(sc->sc_fadt->flags & FADT_SLP_BUTTON))
2626			en |= ACPI_PM1_SLPBTN_EN;
2627		acpi_write_pmreg(sc, ACPIREG_PM1_EN, 0, en);
2628
2629		/* Enable handled GPEs here */
2630		acpi_enable_rungpes(sc);
2631		splx(s);
2632	}
2633
2634	while (thread->running) {
2635		s = spltty();
2636		while (sc->sc_threadwaiting) {
2637			dnprintf(10, "acpi thread going to sleep...\n");
2638			rw_exit_write(&sc->sc_lck);
2639			tsleep(sc, PWAIT, "acpi0", 0);
2640			rw_enter_write(&sc->sc_lck);
2641		}
2642		sc->sc_threadwaiting = 1;
2643		splx(s);
2644		if (aml_busy) {
2645			panic("thread woke up to find aml was busy");
2646			continue;
2647		}
2648
2649		/* Run ACPI taskqueue */
2650		while(acpi_dotask(acpi_softc))
2651			;
2652	}
2653	free(thread, M_DEVBUF, sizeof(*thread));
2654
2655	kthread_exit(0);
2656}
2657
2658void
2659acpi_create_thread(void *arg)
2660{
2661	struct acpi_softc *sc = arg;
2662
2663	if (kthread_create(acpi_thread, sc->sc_thread, NULL, DEVNAME(sc))
2664	    != 0)
2665		printf("%s: unable to create isr thread, GPEs disabled\n",
2666		    DEVNAME(sc));
2667}
2668
2669int
2670acpi_foundec(struct aml_node *node, void *arg)
2671{
2672	struct acpi_softc	*sc = (struct acpi_softc *)arg;
2673	struct device		*self = (struct device *)arg;
2674	const char		*dev;
2675	struct aml_value	 res;
2676	struct acpi_attach_args	aaa;
2677
2678	if (aml_evalnode(sc, node, 0, NULL, &res) != 0)
2679		return 0;
2680
2681	switch (res.type) {
2682	case AML_OBJTYPE_STRING:
2683		dev = res.v_string;
2684		break;
2685	case AML_OBJTYPE_INTEGER:
2686		dev = aml_eisaid(aml_val2int(&res));
2687		break;
2688	default:
2689		dev = "unknown";
2690		break;
2691	}
2692
2693	if (strcmp(dev, ACPI_DEV_ECD))
2694		return 0;
2695
2696	/* Check if we're already attached */
2697	if (sc->sc_ec && sc->sc_ec->sc_devnode == node->parent)
2698		return 0;
2699
2700	memset(&aaa, 0, sizeof(aaa));
2701	aaa.aaa_iot = sc->sc_iot;
2702	aaa.aaa_memt = sc->sc_memt;
2703	aaa.aaa_node = node->parent;
2704	aaa.aaa_dev = dev;
2705	aaa.aaa_name = "acpiec";
2706	config_found(self, &aaa, acpi_print);
2707	aml_freevalue(&res);
2708
2709	return 0;
2710}
2711
2712int
2713acpi_foundsony(struct aml_node *node, void *arg)
2714{
2715	struct acpi_softc *sc = (struct acpi_softc *)arg;
2716	struct device *self = (struct device *)arg;
2717	struct acpi_attach_args aaa;
2718
2719	memset(&aaa, 0, sizeof(aaa));
2720	aaa.aaa_iot = sc->sc_iot;
2721	aaa.aaa_memt = sc->sc_memt;
2722	aaa.aaa_node = node->parent;
2723	aaa.aaa_name = "acpisony";
2724
2725	config_found(self, &aaa, acpi_print);
2726
2727	return 0;
2728}
2729
2730int
2731acpi_parsehid(struct aml_node *node, void *arg, char *outcdev, char *outdev,
2732    size_t devlen)
2733{
2734	struct acpi_softc	*sc = (struct acpi_softc *)arg;
2735	struct aml_value	 res;
2736	const char		*dev;
2737
2738	/* NB aml_eisaid returns a static buffer, this must come first */
2739	if (aml_evalname(acpi_softc, node->parent, "_CID", 0, NULL, &res) == 0) {
2740		switch (res.type) {
2741		case AML_OBJTYPE_STRING:
2742			dev = res.v_string;
2743			break;
2744		case AML_OBJTYPE_INTEGER:
2745			dev = aml_eisaid(aml_val2int(&res));
2746			break;
2747		default:
2748			dev = "unknown";
2749			break;
2750		}
2751		strlcpy(outcdev, dev, devlen);
2752		aml_freevalue(&res);
2753
2754		dnprintf(10, "compatible with device: %s\n", outcdev);
2755	} else {
2756		outcdev[0] = '\0';
2757	}
2758
2759	dnprintf(10, "found hid device: %s ", node->parent->name);
2760	if (aml_evalnode(sc, node, 0, NULL, &res) != 0)
2761		return (1);
2762
2763	switch (res.type) {
2764	case AML_OBJTYPE_STRING:
2765		dev = res.v_string;
2766		break;
2767	case AML_OBJTYPE_INTEGER:
2768		dev = aml_eisaid(aml_val2int(&res));
2769		break;
2770	default:
2771		dev = "unknown";
2772		break;
2773	}
2774	dnprintf(10, "	device: %s\n", dev);
2775
2776	strlcpy(outdev, dev, devlen);
2777
2778	aml_freevalue(&res);
2779
2780	return (0);
2781}
2782
2783/* Devices for which we don't want to attach a driver */
2784const char *acpi_skip_hids[] = {
2785	"INT0800",	/* Intel 82802Firmware Hub Device */
2786	"PNP0000",	/* 8259-compatible Programmable Interrupt Controller */
2787	"PNP0100",	/* PC-class System Timer */
2788	"PNP0103",	/* HPET System Timer */
2789	"PNP0200",	/* PC-class DMA Controller */
2790	"PNP0800",	/* Microsoft Sound System Compatible Device */
2791	"PNP0A03",	/* PCI Bus */
2792	"PNP0A08",	/* PCI Express Bus */
2793	"PNP0B00",	/* AT Real-Time Clock */
2794	"PNP0C01",	/* System Board */
2795	"PNP0C02",	/* PNP Motherboard Resources */
2796	"PNP0C04",	/* x87-compatible Floating Point Processing Unit */
2797	"PNP0C09",	/* Embedded Controller Device */
2798	"PNP0C0F",	/* PCI Interrupt Link Device */
2799	NULL
2800};
2801
2802/* ISA devices for which we attach a driver later */
2803const char *acpi_isa_hids[] = {
2804	"PNP0303",	/* 8042 PS/2 Controller */
2805	"PNP0501",	/* 16550A-compatible COM Serial Port */
2806	NULL
2807};
2808
2809void
2810acpi_attach_deps(struct acpi_softc *sc, struct aml_node *node)
2811{
2812	struct aml_value res;
2813	struct aml_node *dep;
2814	int i;
2815
2816	if (aml_evalname(sc, node, "_DEP", 0, NULL, &res))
2817		return;
2818
2819	if (res.type != AML_OBJTYPE_PACKAGE)
2820		return;
2821
2822	for (i = 0; i < res.length; i++) {
2823		if (res.v_package[i]->type != AML_OBJTYPE_STRING)
2824			continue;
2825		dep = aml_searchrel(node, res.v_package[i]->v_string);
2826		if (dep == NULL || dep->attached)
2827			continue;
2828		dep = aml_searchname(dep, "_HID");
2829		if (dep)
2830			acpi_foundhid(dep, sc);
2831	}
2832
2833	aml_freevalue(&res);
2834}
2835
2836int
2837acpi_foundhid(struct aml_node *node, void *arg)
2838{
2839	struct acpi_softc	*sc = (struct acpi_softc *)arg;
2840	struct device		*self = (struct device *)arg;
2841	char		 	 cdev[32];
2842	char		 	 dev[32];
2843	struct acpi_attach_args	 aaa;
2844	int64_t			 sta;
2845#ifndef SMALL_KERNEL
2846	int			 i;
2847#endif
2848
2849	if (acpi_parsehid(node, arg, cdev, dev, sizeof(dev)) != 0)
2850		return (0);
2851
2852	if (aml_evalinteger(sc, node->parent, "_STA", 0, NULL, &sta))
2853		sta = STA_PRESENT | STA_ENABLED | STA_DEV_OK | 0x1000;
2854
2855	if ((sta & STA_PRESENT) == 0)
2856		return (0);
2857
2858	acpi_attach_deps(sc, node->parent);
2859
2860	memset(&aaa, 0, sizeof(aaa));
2861	aaa.aaa_iot = sc->sc_iot;
2862	aaa.aaa_memt = sc->sc_memt;
2863	aaa.aaa_node = node->parent;
2864	aaa.aaa_dev = dev;
2865
2866	if (acpi_matchhids(&aaa, acpi_skip_hids, "none") ||
2867	    acpi_matchhids(&aaa, acpi_isa_hids, "none"))
2868		return (0);
2869
2870#ifndef SMALL_KERNEL
2871	if (!strcmp(cdev, ACPI_DEV_MOUSE)) {
2872		for (i = 0; i < nitems(sbtn_pnp); i++) {
2873			if (!strcmp(dev, sbtn_pnp[i])) {
2874				mouse_has_softbtn = 1;
2875				break;
2876			}
2877		}
2878	}
2879#endif
2880
2881	if (!node->parent->attached) {
2882		config_found(self, &aaa, acpi_print);
2883		node->parent->attached = 1;
2884	}
2885
2886	return (0);
2887}
2888
2889#ifndef SMALL_KERNEL
2890int
2891acpi_founddock(struct aml_node *node, void *arg)
2892{
2893	struct acpi_softc	*sc = (struct acpi_softc *)arg;
2894	struct device		*self = (struct device *)arg;
2895	struct acpi_attach_args	aaa;
2896
2897	dnprintf(10, "found dock entry: %s\n", node->parent->name);
2898
2899	memset(&aaa, 0, sizeof(aaa));
2900	aaa.aaa_iot = sc->sc_iot;
2901	aaa.aaa_memt = sc->sc_memt;
2902	aaa.aaa_node = node->parent;
2903	aaa.aaa_name = "acpidock";
2904
2905	config_found(self, &aaa, acpi_print);
2906
2907	return 0;
2908}
2909
2910int
2911acpi_foundvideo(struct aml_node *node, void *arg)
2912{
2913	struct acpi_softc *sc = (struct acpi_softc *)arg;
2914	struct device *self = (struct device *)arg;
2915	struct acpi_attach_args	aaa;
2916
2917	memset(&aaa, 0, sizeof(aaa));
2918	aaa.aaa_iot = sc->sc_iot;
2919	aaa.aaa_memt = sc->sc_memt;
2920	aaa.aaa_node = node->parent;
2921	aaa.aaa_name = "acpivideo";
2922
2923	config_found(self, &aaa, acpi_print);
2924
2925	return (0);
2926}
2927
2928int
2929acpi_foundsbs(struct aml_node *node, void *arg)
2930{
2931	struct acpi_softc	*sc = (struct acpi_softc *)arg;
2932	struct device		*self = (struct device *)arg;
2933	char		 	 cdev[32], dev[32];
2934	struct acpi_attach_args	 aaa;
2935	int64_t			 sta;
2936
2937	if (acpi_parsehid(node, arg, cdev, dev, sizeof(dev)) != 0)
2938		return (0);
2939
2940	if (aml_evalinteger(sc, node->parent, "_STA", 0, NULL, &sta))
2941		sta = STA_PRESENT | STA_ENABLED | STA_DEV_OK | 0x1000;
2942
2943	if ((sta & STA_PRESENT) == 0)
2944		return (0);
2945
2946	acpi_attach_deps(sc, node->parent);
2947
2948	if (strcmp(dev, ACPI_DEV_SBS) != 0)
2949		return (0);
2950
2951	if (node->parent->attached)
2952		return (0);
2953
2954	memset(&aaa, 0, sizeof(aaa));
2955	aaa.aaa_iot = sc->sc_iot;
2956	aaa.aaa_memt = sc->sc_memt;
2957	aaa.aaa_node = node->parent;
2958	aaa.aaa_dev = dev;
2959
2960	config_found(self, &aaa, acpi_print);
2961	node->parent->attached = 1;
2962
2963	return (0);
2964}
2965
2966int
2967acpiopen(dev_t dev, int flag, int mode, struct proc *p)
2968{
2969	int error = 0;
2970	struct acpi_softc *sc;
2971	int s;
2972
2973	if (!acpi_cd.cd_ndevs || APMUNIT(dev) != 0 ||
2974	    !(sc = acpi_cd.cd_devs[APMUNIT(dev)]))
2975		return (ENXIO);
2976
2977	s = spltty();
2978	switch (APMDEV(dev)) {
2979	case APMDEV_CTL:
2980		if (!(flag & FWRITE)) {
2981			error = EINVAL;
2982			break;
2983		}
2984		if (sc->sc_flags & SCFLAG_OWRITE) {
2985			error = EBUSY;
2986			break;
2987		}
2988		sc->sc_flags |= SCFLAG_OWRITE;
2989		break;
2990	case APMDEV_NORMAL:
2991		if (!(flag & FREAD) || (flag & FWRITE)) {
2992			error = EINVAL;
2993			break;
2994		}
2995		sc->sc_flags |= SCFLAG_OREAD;
2996		break;
2997	default:
2998		error = ENXIO;
2999		break;
3000	}
3001	splx(s);
3002	return (error);
3003}
3004
3005int
3006acpiclose(dev_t dev, int flag, int mode, struct proc *p)
3007{
3008	int error = 0;
3009	struct acpi_softc *sc;
3010	int s;
3011
3012	if (!acpi_cd.cd_ndevs || APMUNIT(dev) != 0 ||
3013	    !(sc = acpi_cd.cd_devs[APMUNIT(dev)]))
3014		return (ENXIO);
3015
3016	s = spltty();
3017	switch (APMDEV(dev)) {
3018	case APMDEV_CTL:
3019		sc->sc_flags &= ~SCFLAG_OWRITE;
3020		break;
3021	case APMDEV_NORMAL:
3022		sc->sc_flags &= ~SCFLAG_OREAD;
3023		break;
3024	default:
3025		error = ENXIO;
3026		break;
3027	}
3028	splx(s);
3029	return (error);
3030}
3031
3032int
3033acpiioctl(dev_t dev, u_long cmd, caddr_t data, int flag, struct proc *p)
3034{
3035	int error = 0;
3036	struct acpi_softc *sc;
3037	struct acpi_ac *ac;
3038	struct acpi_bat *bat;
3039	struct acpi_sbs *sbs;
3040	struct apm_power_info *pi = (struct apm_power_info *)data;
3041	int bats;
3042	unsigned int remaining, rem, minutes, rate;
3043	int s;
3044
3045	if (!acpi_cd.cd_ndevs || APMUNIT(dev) != 0 ||
3046	    !(sc = acpi_cd.cd_devs[APMUNIT(dev)]))
3047		return (ENXIO);
3048
3049	s = spltty();
3050	/* fake APM */
3051	switch (cmd) {
3052	case APM_IOC_SUSPEND:
3053	case APM_IOC_STANDBY:
3054		if ((flag & FWRITE) == 0) {
3055			error = EBADF;
3056			break;
3057		}
3058		acpi_addtask(sc, acpi_sleep_task, sc, ACPI_SLEEP_SUSPEND);
3059		acpi_wakeup(sc);
3060		break;
3061#ifdef HIBERNATE
3062	case APM_IOC_HIBERNATE:
3063		if ((error = suser(p, 0)) != 0)
3064			break;
3065		if ((flag & FWRITE) == 0) {
3066			error = EBADF;
3067			break;
3068		}
3069		if (get_hibernate_io_function(swdevt[0].sw_dev) == NULL) {
3070			error = EOPNOTSUPP;
3071			break;
3072		}
3073		acpi_addtask(sc, acpi_sleep_task, sc, ACPI_SLEEP_HIBERNATE);
3074		acpi_wakeup(sc);
3075		break;
3076#endif
3077	case APM_IOC_GETPOWER:
3078		/* A/C */
3079		pi->ac_state = APM_AC_UNKNOWN;
3080		SLIST_FOREACH(ac, &sc->sc_ac, aac_link) {
3081			if (ac->aac_softc->sc_ac_stat == PSR_ONLINE)
3082				pi->ac_state = APM_AC_ON;
3083			else if (ac->aac_softc->sc_ac_stat == PSR_OFFLINE)
3084				if (pi->ac_state == APM_AC_UNKNOWN)
3085					pi->ac_state = APM_AC_OFF;
3086		}
3087
3088		/* battery */
3089		pi->battery_state = APM_BATT_UNKNOWN;
3090		pi->battery_life = 0;
3091		pi->minutes_left = 0;
3092		bats = 0;
3093		remaining = rem = 0;
3094		minutes = 0;
3095		rate = 0;
3096		SLIST_FOREACH(bat, &sc->sc_bat, aba_link) {
3097			if (bat->aba_softc->sc_bat_present == 0)
3098				continue;
3099
3100			if (bat->aba_softc->sc_bix.bix_last_capacity == 0)
3101				continue;
3102
3103			bats++;
3104			rem = (bat->aba_softc->sc_bst.bst_capacity * 100) /
3105			    bat->aba_softc->sc_bix.bix_last_capacity;
3106			if (rem > 100)
3107				rem = 100;
3108			remaining += rem;
3109
3110			if (bat->aba_softc->sc_bst.bst_rate == BST_UNKNOWN)
3111				continue;
3112			else if (bat->aba_softc->sc_bst.bst_rate > 1)
3113				rate = bat->aba_softc->sc_bst.bst_rate;
3114
3115			minutes += bat->aba_softc->sc_bst.bst_capacity;
3116		}
3117
3118		SLIST_FOREACH(sbs, &sc->sc_sbs, asbs_link) {
3119			if (sbs->asbs_softc->sc_batteries_present == 0)
3120				continue;
3121
3122			if (sbs->asbs_softc->sc_battery.rel_charge == 0)
3123				continue;
3124
3125			bats++;
3126			rem = sbs->asbs_softc->sc_battery.rel_charge;
3127			if (rem > 100)
3128				rem = 100;
3129			remaining += rem;
3130
3131			if (sbs->asbs_softc->sc_battery.run_time ==
3132			    ACPISBS_VALUE_UNKNOWN)
3133				continue;
3134
3135			rate = 60; /* XXX */
3136			minutes += sbs->asbs_softc->sc_battery.run_time;
3137		}
3138
3139		if (bats == 0) {
3140			pi->battery_state = APM_BATTERY_ABSENT;
3141			pi->battery_life = 0;
3142			pi->minutes_left = (unsigned int)-1;
3143			break;
3144		}
3145
3146		if (pi->ac_state == APM_AC_ON || rate == 0)
3147			pi->minutes_left = (unsigned int)-1;
3148		else
3149			pi->minutes_left = 60 * minutes / rate;
3150
3151		/* running on battery */
3152		pi->battery_life = remaining / bats;
3153		if (pi->battery_life > 50)
3154			pi->battery_state = APM_BATT_HIGH;
3155		else if (pi->battery_life > 25)
3156			pi->battery_state = APM_BATT_LOW;
3157		else
3158			pi->battery_state = APM_BATT_CRITICAL;
3159
3160		break;
3161
3162	default:
3163		error = ENOTTY;
3164	}
3165
3166	splx(s);
3167	return (error);
3168}
3169
3170void	acpi_filtdetach(struct knote *);
3171int	acpi_filtread(struct knote *, long);
3172
3173struct filterops acpiread_filtops = {
3174	1, NULL, acpi_filtdetach, acpi_filtread
3175};
3176
3177int acpi_evindex;
3178
3179int
3180acpi_record_event(struct acpi_softc *sc, u_int type)
3181{
3182	if ((sc->sc_flags & SCFLAG_OPEN) == 0)
3183		return (1);
3184
3185	acpi_evindex++;
3186	KNOTE(sc->sc_note, APM_EVENT_COMPOSE(type, acpi_evindex));
3187	return (0);
3188}
3189
3190void
3191acpi_filtdetach(struct knote *kn)
3192{
3193	struct acpi_softc *sc = kn->kn_hook;
3194	int s;
3195
3196	s = spltty();
3197	SLIST_REMOVE(sc->sc_note, kn, knote, kn_selnext);
3198	splx(s);
3199}
3200
3201int
3202acpi_filtread(struct knote *kn, long hint)
3203{
3204	/* XXX weird kqueue_scan() semantics */
3205	if (hint && !kn->kn_data)
3206		kn->kn_data = hint;
3207	return (1);
3208}
3209
3210int
3211acpikqfilter(dev_t dev, struct knote *kn)
3212{
3213	struct acpi_softc *sc;
3214	int s;
3215
3216	if (!acpi_cd.cd_ndevs || APMUNIT(dev) != 0 ||
3217	    !(sc = acpi_cd.cd_devs[APMUNIT(dev)]))
3218		return (ENXIO);
3219
3220	switch (kn->kn_filter) {
3221	case EVFILT_READ:
3222		kn->kn_fop = &acpiread_filtops;
3223		break;
3224	default:
3225		return (EINVAL);
3226	}
3227
3228	kn->kn_hook = sc;
3229
3230	s = spltty();
3231	SLIST_INSERT_HEAD(sc->sc_note, kn, kn_selnext);
3232	splx(s);
3233
3234	return (0);
3235}
3236
3237#else /* SMALL_KERNEL */
3238
3239int
3240acpiopen(dev_t dev, int flag, int mode, struct proc *p)
3241{
3242	return (ENXIO);
3243}
3244
3245int
3246acpiclose(dev_t dev, int flag, int mode, struct proc *p)
3247{
3248	return (ENXIO);
3249}
3250
3251int
3252acpiioctl(dev_t dev, u_long cmd, caddr_t data, int flag, struct proc *p)
3253{
3254	return (ENXIO);
3255}
3256
3257int
3258acpikqfilter(dev_t dev, struct knote *kn)
3259{
3260	return (ENXIO);
3261}
3262#endif /* SMALL_KERNEL */
3263