pci.c revision 34990
1/*
2 * Copyright (c) 1997, Stefan Esser <se@freebsd.org>
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 * 1. Redistributions of source code must retain the above copyright
9 *    notice unmodified, this list of conditions, and the following
10 *    disclaimer.
11 * 2. Redistributions in binary form must reproduce the above copyright
12 *    notice, this list of conditions and the following disclaimer in the
13 *    documentation and/or other materials provided with the distribution.
14 *
15 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
16 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
17 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
18 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
19 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
20 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
21 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
22 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
23 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
24 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
25 *
26 * $Id: pci.c,v 1.81 1998/01/24 02:54:47 eivind Exp $
27 *
28 */
29
30#include "pci.h"
31#if NPCI > 0
32
33#include "opt_devfs.h"
34
35#include <sys/param.h>
36#include <sys/systm.h>
37#include <sys/malloc.h>
38#include <sys/fcntl.h>
39#include <sys/conf.h>
40#include <sys/kernel.h>
41#ifdef DEVFS
42#include <sys/devfsext.h>
43#endif /* DEVFS */
44
45#include <vm/vm.h>
46#include <vm/pmap.h>
47
48#include <pci/pcireg.h>
49#include <pci/pcivar.h>
50#include <pci/pci_ioctl.h>
51
52#ifdef APIC_IO
53#include <machine/smp.h>
54#endif /* APIC_IO */
55
56/* return highest PCI bus number known to be used, or -1 if none */
57
58static int
59pci_bushigh(void)
60{
61	if (pci_cfgopen() == 0)
62		return (-1);
63	return (0);
64}
65
66/* return base address of memory or port map */
67
68static int
69pci_mapbase(unsigned mapreg)
70{
71	int mask = 0x03;
72	if ((mapreg & 0x01) == 0)
73		mask = 0x0f;
74	return (mapreg & ~mask);
75}
76
77/* return map type of memory or port map */
78
79static int
80pci_maptype(unsigned mapreg)
81{
82	static u_int8_t maptype[0x10] = {
83		PCI_MAPMEM,		PCI_MAPPORT,
84		PCI_MAPMEM,		0,
85		PCI_MAPMEM,		PCI_MAPPORT,
86		0,			0,
87		PCI_MAPMEM|PCI_MAPMEMP,	PCI_MAPPORT,
88		PCI_MAPMEM|PCI_MAPMEMP, 0,
89		PCI_MAPMEM|PCI_MAPMEMP,	PCI_MAPPORT,
90		0,			0,
91	};
92
93	return maptype[mapreg & 0x0f];
94}
95
96/* return log2 of map size decoded for memory or port map */
97
98static int
99pci_mapsize(unsigned testval)
100{
101	int ln2size;
102
103	testval = pci_mapbase(testval);
104	ln2size = 0;
105	if (testval != 0) {
106		while ((testval & 1) == 0)
107		{
108			ln2size++;
109			testval >>= 1;
110		}
111	}
112	return (ln2size);
113}
114
115/* return log2 of address range supported by map register */
116
117static int
118pci_maprange(unsigned mapreg)
119{
120	int ln2range = 0;
121	switch (mapreg & 0x07) {
122	case 0x00:
123	case 0x01:
124	case 0x05:
125		ln2range = 32;
126		break;
127	case 0x02:
128		ln2range = 20;
129		break;
130	case 0x04:
131		ln2range = 64;
132		break;
133	}
134	return (ln2range);
135}
136
137/* extract map parameters into newly allocated array of pcimap structures */
138
139static pcimap *
140pci_readmaps(pcicfgregs *cfg, int maxmaps)
141{
142	int i;
143	pcimap *map;
144	int map64 = 0;
145
146	for (i = 0; i < maxmaps; i++) {
147		int reg = PCIR_MAPS + i*4;
148		u_int32_t base;
149		u_int32_t ln2range;
150
151		base = pci_cfgread(cfg, reg, 4);
152		ln2range = pci_maprange(base);
153
154		if (base == 0 || ln2range == 0)
155			maxmaps = i;
156		else if (ln2range > 32)
157			i++;
158	}
159
160	map = malloc(maxmaps * sizeof (pcimap), M_DEVBUF, M_WAITOK);
161	if (map != NULL) {
162		bzero(map, sizeof(pcimap) * maxmaps);
163
164		for (i = 0; i < maxmaps; i++) {
165			int reg = PCIR_MAPS + i*4;
166			u_int32_t base;
167			u_int32_t testval;
168
169			base = pci_cfgread(cfg, reg, 4);
170
171			if (map64 == 0) {
172				pci_cfgwrite(cfg, reg, 0xffffffff, 4);
173				testval = pci_cfgread(cfg, reg, 4);
174				pci_cfgwrite(cfg, reg, base, 4);
175
176				map[i].base     = pci_mapbase(base);
177				map[i].type     = pci_maptype(base);
178				map[i].ln2size  = pci_mapsize(testval);
179				map[i].ln2range = pci_maprange(testval);
180				map64 = map[i].ln2range == 64;
181			} else {
182				/* only fill in base, other fields are 0 */
183				map[i].base     = base;
184				map64 = 0;
185			}
186		}
187		cfg->nummaps = maxmaps;
188	}
189	return (map);
190}
191
192/* adjust some values from PCI 1.0 devices to match 2.0 standards ... */
193
194static void
195pci_fixancient(pcicfgregs *cfg)
196{
197	if (cfg->hdrtype != 0)
198		return;
199
200	/* PCI to PCI bridges use header type 1 */
201	if (cfg->class == PCIC_BRIDGE && cfg->subclass == PCIS_BRIDGE_PCI)
202		cfg->hdrtype = 1;
203}
204
205/* read config data specific to header type 1 device (PCI to PCI bridge) */
206
207static void *
208pci_readppb(pcicfgregs *cfg)
209{
210	pcih1cfgregs *p;
211
212	p = malloc(sizeof (pcih1cfgregs), M_DEVBUF, M_WAITOK);
213	if (p == NULL)
214		return (NULL);
215
216	bzero(p, sizeof *p);
217
218	p->secstat = pci_cfgread(cfg, PCIR_SECSTAT_1, 2);
219	p->bridgectl = pci_cfgread(cfg, PCIR_BRIDGECTL_1, 2);
220
221	p->seclat = pci_cfgread(cfg, PCIR_SECLAT_1, 1);
222
223	p->iobase = PCI_PPBIOBASE (pci_cfgread(cfg, PCIR_IOBASEH_1, 2),
224				   pci_cfgread(cfg, PCIR_IOBASEL_1, 1));
225	p->iolimit = PCI_PPBIOLIMIT (pci_cfgread(cfg, PCIR_IOLIMITH_1, 2),
226				     pci_cfgread(cfg, PCIR_IOLIMITL_1, 1));
227
228	p->membase = PCI_PPBMEMBASE (0,
229				     pci_cfgread(cfg, PCIR_MEMBASE_1, 2));
230	p->memlimit = PCI_PPBMEMLIMIT (0,
231				       pci_cfgread(cfg, PCIR_MEMLIMIT_1, 2));
232
233	p->pmembase = PCI_PPBMEMBASE (
234		(pci_addr_t)pci_cfgread(cfg, PCIR_PMBASEH_1, 4),
235		pci_cfgread(cfg, PCIR_PMBASEL_1, 2));
236
237	p->pmemlimit = PCI_PPBMEMLIMIT (
238		(pci_addr_t)pci_cfgread(cfg, PCIR_PMLIMITH_1, 4),
239		pci_cfgread(cfg, PCIR_PMLIMITL_1, 2));
240	return (p);
241}
242
243/* read config data specific to header type 2 device (PCI to CardBus bridge) */
244
245static void *
246pci_readpcb(pcicfgregs *cfg)
247{
248	pcih2cfgregs *p;
249
250	p = malloc(sizeof (pcih2cfgregs), M_DEVBUF, M_WAITOK);
251	if (p == NULL)
252		return (NULL);
253
254	bzero(p, sizeof *p);
255
256	p->secstat = pci_cfgread(cfg, PCIR_SECSTAT_2, 2);
257	p->bridgectl = pci_cfgread(cfg, PCIR_BRIDGECTL_2, 2);
258
259	p->seclat = pci_cfgread(cfg, PCIR_SECLAT_2, 1);
260
261	p->membase0 = pci_cfgread(cfg, PCIR_MEMBASE0_2, 4);
262	p->memlimit0 = pci_cfgread(cfg, PCIR_MEMLIMIT0_2, 4);
263	p->membase1 = pci_cfgread(cfg, PCIR_MEMBASE1_2, 4);
264	p->memlimit1 = pci_cfgread(cfg, PCIR_MEMLIMIT1_2, 4);
265
266	p->iobase0 = pci_cfgread(cfg, PCIR_IOBASE0_2, 4);
267	p->iolimit0 = pci_cfgread(cfg, PCIR_IOLIMIT0_2, 4);
268	p->iobase1 = pci_cfgread(cfg, PCIR_IOBASE1_2, 4);
269	p->iolimit1 = pci_cfgread(cfg, PCIR_IOLIMIT1_2, 4);
270
271	p->pccardif = pci_cfgread(cfg, PCIR_PCCARDIF_2, 4);
272	return p;
273}
274
275/* extract header type specific config data */
276
277static void
278pci_hdrtypedata(pcicfgregs *cfg)
279{
280	switch (cfg->hdrtype) {
281	case 0:
282		cfg->subvendor      = pci_cfgread(cfg, PCIR_SUBVEND_0, 2);
283		cfg->subdevice      = pci_cfgread(cfg, PCIR_SUBDEV_0, 2);
284		cfg->map            = pci_readmaps(cfg, PCI_MAXMAPS_0);
285		break;
286	case 1:
287		cfg->subvendor      = pci_cfgread(cfg, PCIR_SUBVEND_1, 2);
288		cfg->subdevice      = pci_cfgread(cfg, PCIR_SUBDEV_1, 2);
289		cfg->secondarybus   = pci_cfgread(cfg, PCIR_SECBUS_1, 1);
290		cfg->subordinatebus = pci_cfgread(cfg, PCIR_SUBBUS_1, 1);
291		cfg->map            = pci_readmaps(cfg, PCI_MAXMAPS_1);
292		cfg->hdrspec        = pci_readppb(cfg);
293		break;
294	case 2:
295		cfg->subvendor      = pci_cfgread(cfg, PCIR_SUBVEND_2, 2);
296		cfg->subdevice      = pci_cfgread(cfg, PCIR_SUBDEV_2, 2);
297		cfg->secondarybus   = pci_cfgread(cfg, PCIR_SECBUS_2, 1);
298		cfg->subordinatebus = pci_cfgread(cfg, PCIR_SUBBUS_2, 1);
299		cfg->map            = pci_readmaps(cfg, PCI_MAXMAPS_2);
300		cfg->hdrspec        = pci_readpcb(cfg);
301		break;
302	}
303}
304
305/* read configuration header into pcicfgrect structure */
306
307static pcicfgregs *
308pci_readcfg(pcicfgregs *probe)
309{
310	pcicfgregs *cfg = NULL;
311
312	if (pci_cfgread(probe, PCIR_DEVVENDOR, 4) != -1) {
313		cfg = malloc(sizeof (pcicfgregs), M_DEVBUF, M_WAITOK);
314		if (cfg == NULL)
315			return (cfg);
316
317		bzero(cfg, sizeof *cfg);
318
319		cfg->bus		= probe->bus;
320		cfg->slot		= probe->slot;
321		cfg->func		= probe->func;
322		cfg->parent		= probe->parent;
323
324		cfg->vendor		= pci_cfgread(cfg, PCIR_VENDOR, 2);
325		cfg->device		= pci_cfgread(cfg, PCIR_DEVICE, 2);
326		cfg->cmdreg		= pci_cfgread(cfg, PCIR_COMMAND, 2);
327		cfg->statreg		= pci_cfgread(cfg, PCIR_STATUS, 2);
328		cfg->class		= pci_cfgread(cfg, PCIR_CLASS, 1);
329		cfg->subclass		= pci_cfgread(cfg, PCIR_SUBCLASS, 1);
330		cfg->progif		= pci_cfgread(cfg, PCIR_PROGIF, 1);
331		cfg->revid		= pci_cfgread(cfg, PCIR_REVID, 1);
332		cfg->hdrtype		= pci_cfgread(cfg, PCIR_HEADERTYPE, 1);
333		cfg->cachelnsz		= pci_cfgread(cfg, PCIR_CACHELNSZ, 1);
334		cfg->lattimer		= pci_cfgread(cfg, PCIR_LATTIMER, 1);
335		cfg->intpin		= pci_cfgread(cfg, PCIR_INTPIN, 1);
336		cfg->intline		= pci_cfgread(cfg, PCIR_INTLINE, 1);
337
338#ifdef APIC_IO
339		if (cfg->intpin != 0) {
340			int airq;
341
342			airq = pci_apic_pin(cfg->bus, cfg->slot, cfg->intpin);
343			if (airq >= 0) {
344				/* PCI specific entry found in MP table */
345				if (airq != cfg->intline) {
346					undirect_pci_irq(cfg->intline);
347					cfg->intline = airq;
348				}
349			} else {
350				/*
351				 * PCI interrupts might be redirected to the
352				 * ISA bus according to some MP tables. Use the
353				 * same methods as used by the ISA devices
354				 * devices to find the proper IOAPIC int pin.
355				 */
356				airq = isa_apic_pin(cfg->intline);
357				if ((airq >= 0) && (airq != cfg->intline)) {
358					/* XXX: undirect_pci_irq() ? */
359					undirect_isa_irq(cfg->intline);
360					cfg->intline = airq;
361				}
362			}
363		}
364#endif /* APIC_IO */
365
366		cfg->mingnt		= pci_cfgread(cfg, PCIR_MINGNT, 1);
367		cfg->maxlat		= pci_cfgread(cfg, PCIR_MAXLAT, 1);
368
369		cfg->mfdev		= (cfg->hdrtype & PCIM_MFDEV) != 0;
370		cfg->hdrtype		&= ~PCIM_MFDEV;
371
372		pci_fixancient(cfg);
373		pci_hdrtypedata(cfg);
374	}
375	return (cfg);
376}
377
378#if 0
379/* free pcicfgregs structure and all depending data structures */
380
381static int
382pci_freecfg(pcicfgregs *cfg)
383{
384	if (cfg->hdrspec != NULL)
385		free(cfg->hdrspec, M_DEVBUF);
386	if (cfg->map != NULL)
387		free(cfg->map, M_DEVBUF);
388	free(cfg, M_DEVBUF);
389	return (0);
390}
391#endif
392
393static void
394pci_addcfg(pcicfgregs *cfg)
395{
396	if (bootverbose) {
397		int i;
398		printf("found->\tvendor=0x%04x, dev=0x%04x, revid=0x%02x\n",
399		       cfg->vendor, cfg->device, cfg->revid);
400		printf("\tclass=%02x-%02x-%02x, hdrtype=0x%02x, mfdev=%d\n",
401		       cfg->class, cfg->subclass, cfg->progif, cfg->hdrtype, cfg->mfdev);
402#ifdef PCI_DEBUG
403		printf("\tcmdreg=0x%04x, statreg=0x%04x, cachelnsz=%d (dwords)\n",
404		       cfg->cmdreg, cfg->statreg, cfg->cachelnsz);
405		printf("\tlattimer=0x%02x (%d ns), mingnt=0x%02x (%d ns), maxlat=0x%02x (%d ns)\n",
406		       cfg->lattimer, cfg->lattimer * 30,
407		       cfg->mingnt, cfg->mingnt * 250, cfg->maxlat, cfg->maxlat * 250);
408#endif /* PCI_DEBUG */
409		if (cfg->intpin > 0)
410			printf("\tintpin=%c, irq=%d\n", cfg->intpin +'a' -1, cfg->intline);
411
412		for (i = 0; i < cfg->nummaps; i++) {
413			pcimap *m = &cfg->map[i];
414			printf("\tmap[%d]: type %x, range %2d, base %08x, size %2d\n",
415			       i, m->type, m->ln2range, m->base, m->ln2size);
416		}
417	}
418	pci_drvattach(cfg); /* XXX currently defined in pci_compat.c */
419}
420
421/* return pointer to device that is a bridge to this bus */
422
423static pcicfgregs *
424pci_bridgeto(int bus)
425{
426	return (NULL); /* XXX not yet implemented */
427}
428
429/* scan one PCI bus for devices */
430
431static int
432pci_probebus(int bus)
433{
434	pcicfgregs probe;
435	int bushigh = bus;
436
437	bzero(&probe, sizeof probe);
438	probe.parent = pci_bridgeto(bus);
439	probe.bus = bus;
440	for (probe.slot = 0; probe.slot <= PCI_SLOTMAX; probe.slot++) {
441		int pcifunchigh = 0;
442		for (probe.func = 0; probe.func <= pcifunchigh; probe.func++) {
443			pcicfgregs *cfg = pci_readcfg(&probe);
444			if (cfg != NULL) {
445				if (cfg->mfdev)
446					pcifunchigh = 7;
447				/*
448				 * XXX: Temporarily move pci_addcfg() up before
449				 * the use of cfg->subordinatebus. This is
450				 * necessary, since pci_addcfg() calls the
451				 * device's probe(), which may read the bus#
452				 * from some device dependent register of
453				 * some host to PCI bridges. The probe will
454				 * eventually be moved to pci_readcfg(), and
455				 * pci_addcfg() will then be moved back down
456				 * below the conditional statement ...
457				 */
458				pci_addcfg(cfg);
459
460				if (bushigh < cfg->subordinatebus)
461					bushigh = cfg->subordinatebus;
462
463				cfg = NULL; /* we don't own this anymore ... */
464			}
465		}
466	}
467	return (bushigh);
468}
469
470/* scan a PCI bus tree reached through one PCI attachment point */
471
472int
473pci_probe(pciattach *parent)
474{
475	int bushigh;
476	int bus = 0;
477
478	bushigh = pci_bushigh();
479	while (bus <= bushigh) {
480		int newbushigh;
481
482		printf("Probing for devices on PCI bus %d:\n", bus);
483		newbushigh = pci_probebus(bus);
484
485		if (bushigh < newbushigh)
486			bushigh = newbushigh;
487		bus++;
488	}
489	return (bushigh);
490}
491
492/*
493 * This is the user interface to PCI configuration space.
494 */
495
496static int
497pci_open(dev_t dev, int oflags, int devtype, struct proc *p)
498{
499	if ((oflags & FWRITE) && securelevel > 0) {
500		return EPERM;
501	}
502	return 0;
503}
504
505static int
506pci_close(dev_t dev, int flag, int devtype, struct proc *p)
507{
508	return 0;
509}
510
511static int
512pci_ioctl(dev_t dev, int cmd, caddr_t data, int flag, struct proc *p)
513{
514	struct pci_io *io;
515	int error;
516
517	if (cmd != PCIOCGETCONF && !(flag & FWRITE))
518		return EPERM;
519
520	switch(cmd) {
521	case PCIOCGETCONF:
522#ifdef NOTYET
523static struct pci_conf *pci_dev_list;
524static unsigned pci_dev_list_count;
525static unsigned pci_dev_list_size;
526
527		cio = (struct pci_conf_io *)data;
528		iolen = min(cio->pci_len,
529			    pci_dev_list_count * sizeof(struct pci_conf));
530		cio->pci_len = pci_dev_list_count * sizeof(struct pci_conf);
531
532		error = copyout(pci_dev_list, cio->pci_buf, iolen);
533#else
534		error = ENODEV;
535#endif
536		break;
537
538	case PCIOCREAD:
539		io = (struct pci_io *)data;
540		switch(io->pi_width) {
541			pcicfgregs probe;
542		case 4:
543		case 2:
544		case 1:
545			probe.bus = io->pi_sel.pc_bus;
546			probe.slot = io->pi_sel.pc_dev;
547			probe.func = io->pi_sel.pc_func;
548			io->pi_data = pci_cfgread(&probe,
549						  io->pi_reg, io->pi_width);
550			error = 0;
551			break;
552		default:
553			error = ENODEV;
554			break;
555		}
556		break;
557
558	case PCIOCWRITE:
559		io = (struct pci_io *)data;
560		switch(io->pi_width) {
561			pcicfgregs probe;
562		case 4:
563		case 2:
564		case 1:
565			probe.bus = io->pi_sel.pc_bus;
566			probe.slot = io->pi_sel.pc_dev;
567			probe.func = io->pi_sel.pc_func;
568			pci_cfgwrite(&probe,
569				    io->pi_reg, io->pi_data, io->pi_width);
570			error = 0;
571			break;
572		default:
573			error = ENODEV;
574			break;
575		}
576		break;
577
578	default:
579		error = ENOTTY;
580		break;
581	}
582
583	return (error);
584}
585
586#define	PCI_CDEV	78
587
588static struct cdevsw pcicdev = {
589	pci_open, pci_close, noread, nowrite, pci_ioctl, nostop, noreset,
590	nodevtotty, seltrue, nommap, nostrategy, "pci", 0, PCI_CDEV
591};
592
593#ifdef DEVFS
594static void *pci_devfs_token;
595#endif
596
597static void
598pci_cdevinit(void *dummy)
599{
600	dev_t dev;
601
602	dev = makedev(PCI_CDEV, 0);
603	cdevsw_add(&dev, &pcicdev, NULL);
604#ifdef	DEVFS
605	pci_devfs_token = devfs_add_devswf(&pcicdev, 0, DV_CHR,
606					   UID_ROOT, GID_WHEEL, 0644, "pci");
607#endif
608}
609
610SYSINIT(pcidev, SI_SUB_DRIVERS, SI_ORDER_MIDDLE+PCI_CDEV, pci_cdevinit, NULL);
611
612#endif /* NPCI > 0 */
613