xref: /freebsd/sys/dev/bhnd/bhndb/bhndb_pci.c (revision a5ff72cb0e51a7675d4e2b5810a2b6dad5b91960)
1 /*-
2  * Copyright (c) 2015 Landon Fuller <landon@landonf.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, this list of conditions and the following disclaimer,
10  *    without modification.
11  * 2. Redistributions in binary form must reproduce at minimum a disclaimer
12  *    similar to the "NO WARRANTY" disclaimer below ("Disclaimer") and any
13  *    redistribution must be conditioned upon including a substantially
14  *    similar Disclaimer requirement for further binary redistribution.
15  *
16  * NO WARRANTY
17  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
18  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
19  * LIMITED TO, THE IMPLIED WARRANTIES OF NONINFRINGEMENT, MERCHANTIBILITY
20  * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
21  * THE COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY,
22  * OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
23  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
24  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
25  * IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
26  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
27  * THE POSSIBILITY OF SUCH DAMAGES.
28  */
29 
30 #include <sys/cdefs.h>
31 __FBSDID("$FreeBSD$");
32 
33 /*
34  * PCI-specific implementation for the BHNDB bridge driver.
35  *
36  * Provides support for bridging from a PCI parent bus to a BHND-compatible
37  * bus (e.g. bcma or siba) via a Broadcom PCI core configured in end-point
38  * mode.
39  *
40  * This driver handles all interactions with the PCI bridge core. On the
41  * bridged bhnd bus, the PCI core device will be claimed by a simple
42  * bhnd_hostb driver.
43  */
44 
45 // Quirk TODO
46 // WARs for the following are not yet implemented:
47 // - BHND_PCI_QUIRK_SBINTVEC
48 // - BHND_PCIE_QUIRK_ASPM_OVR
49 // - BHND_PCIE_QUIRK_SERDES_NOPLLDOWN
50 // Quirks (and WARs) for the following are not yet defined:
51 // - Power savings via MDIO BLK1/PWR_MGMT3 on PCIe hwrev 15-20, 21-22
52 // - WOWL PME enable/disable
53 // - 4360 PCIe SerDes Tx amplitude/deemphasis (vendor Apple, boards
54 //   BCM94360X51P2, BCM94360X51A).
55 // - PCI latency timer (boards CB2_4321_BOARD, CB2_4321_AG_BOARD)
56 // - Max SerDes TX drive strength (vendor Apple, pcie >= rev10,
57 //   board BCM94322X9)
58 // - 700mV SerDes TX drive strength (chipid BCM4331, boards BCM94331X19,
59 //   BCM94331X28, BCM94331X29B, BCM94331X19C)
60 
61 #include <sys/param.h>
62 #include <sys/kernel.h>
63 #include <sys/bus.h>
64 #include <sys/limits.h>
65 #include <sys/malloc.h>
66 #include <sys/module.h>
67 #include <sys/systm.h>
68 
69 #include <dev/pci/pcireg.h>
70 #include <dev/pci/pcivar.h>
71 
72 #include <dev/bhnd/bhnd.h>
73 
74 #include <dev/bhnd/cores/pci/bhnd_pcireg.h>
75 #include <dev/bhnd/cores/pci/mdio_pcievar.h>
76 
77 #include "bhndb_pcireg.h"
78 #include "bhndb_pcivar.h"
79 #include "bhndb_private.h"
80 
81 static int	bhndb_enable_pci_clocks(struct bhndb_pci_softc *sc);
82 static int	bhndb_disable_pci_clocks(struct bhndb_pci_softc *sc);
83 
84 static int	bhndb_pci_compat_setregwin(struct bhndb_pci_softc *,
85 		    const struct bhndb_regwin *, bhnd_addr_t);
86 static int	bhndb_pci_fast_setregwin(struct bhndb_pci_softc *,
87 		    const struct bhndb_regwin *, bhnd_addr_t);
88 
89 static uint32_t	bhndb_pcie_read_proto_reg(struct bhndb_pci_softc *sc,
90 		    uint32_t addr);
91 static void	bhndb_pcie_write_proto_reg(struct bhndb_pci_softc *sc,
92 		    uint32_t addr, uint32_t val);
93 
94 static void	bhndb_init_sromless_pci_config(struct bhndb_pci_softc *sc);
95 
96 static int	bhndb_pci_wars_register_access(struct bhndb_pci_softc *sc);
97 static int	bhndb_pci_wars_early_once(struct bhndb_pci_softc *sc);
98 static int	bhndb_pci_wars_hwup(struct bhndb_pci_softc *sc);
99 static int	bhndb_pci_wars_hwdown(struct bhndb_pci_softc *sc);
100 
101 static uint32_t	bhndb_pci_discover_quirks(struct bhndb_pci_softc *,
102 		    const struct bhndb_pci_id *);
103 
104 static const struct bhndb_pci_id *bhndb_pci_find_core_id(
105 				      struct bhnd_core_info *core);
106 /*
107  * Supported PCI bridge cores.
108  *
109  * This table defines quirks specific to core hwrev ranges; see also
110  * bhndb_pci_discover_quirks() for additional quirk detection.
111  */
112 static const struct bhndb_pci_id bhndb_pci_ids[] = {
113 	/* PCI */
114 	{ BHND_COREID_PCI, BHND_PCI_REGFMT_PCI,
115 		(struct bhnd_device_quirk[]) {
116 			{ BHND_HWREV_GTE	(0),
117 				BHNDB_PCI_QUIRK_EXT_CLOCK_GATING |
118 				BHNDB_PCI_QUIRK_SBTOPCI2_PREF_BURST },
119 
120 			{ BHND_HWREV_RANGE	(0, 5),
121 				BHNDB_PCI_QUIRK_SBINTVEC },
122 
123 			{ BHND_HWREV_GTE	(11),
124 				BHNDB_PCI_QUIRK_SBTOPCI2_READMULTI |
125 				BHNDB_PCI_QUIRK_CLKRUN_DSBL },
126 
127 			BHND_DEVICE_QUIRK_END
128 		}
129 	},
130 
131 	/* PCI Gen 1 */
132 	{ BHND_COREID_PCIE, BHND_PCI_REGFMT_PCIE,
133 		(struct bhnd_device_quirk[]) {
134 			{ BHND_HWREV_EQ		(0),
135 				BHNDB_PCIE_QUIRK_SDR9_L0s_HANG },
136 
137 			{ BHND_HWREV_RANGE	(0, 1),
138 				BHNDB_PCIE_QUIRK_UR_STATUS_FIX },
139 
140 			{ BHND_HWREV_EQ		(1),
141 				BHNDB_PCIE_QUIRK_PCIPM_REQEN },
142 
143 			{ BHND_HWREV_RANGE	(3, 5),
144 				BHNDB_PCIE_QUIRK_ASPM_OVR |
145 				BHNDB_PCIE_QUIRK_SDR9_POLARITY |
146 				BHNDB_PCIE_QUIRK_SDR9_NO_FREQRETRY },
147 
148 			{ BHND_HWREV_LTE	(6),
149 				BHNDB_PCIE_QUIRK_L1_IDLE_THRESH },
150 
151 			{ BHND_HWREV_GTE	(6),
152 				BHNDB_PCIE_QUIRK_SPROM_L23_PCI_RESET },
153 
154 			{ BHND_HWREV_EQ		(7),
155 				BHNDB_PCIE_QUIRK_SERDES_NOPLLDOWN },
156 
157 			{ BHND_HWREV_GTE	(8),
158 				BHNDB_PCIE_QUIRK_L1_TIMER_PERF },
159 
160 			{ BHND_HWREV_GTE	(10),
161 				BHNDB_PCIE_QUIRK_SD_C22_EXTADDR },
162 
163 			BHND_DEVICE_QUIRK_END
164 		}
165 	},
166 
167 	{ BHND_COREID_INVALID, BHND_PCI_REGFMT_PCI }
168 };
169 
170 
171 /* quirk flag convenience macros */
172 #define	BHNDB_PCI_QUIRK(_sc, _name)	\
173     ((_sc)->quirks & BHNDB_PCI_QUIRK_ ## _name)
174 #define	BHNDB_PCIE_QUIRK(_sc, _name)	\
175     ((_sc)->quirks & BHNDB_PCIE_QUIRK_ ## _name)
176 
177 #define	BHNDB_PCI_ASSERT_QUIRK(_sc, name)	\
178     KASSERT(BHNDB_PCI_QUIRK((_sc), name), ("quirk " __STRING(_name) " not set"))
179 #define	BHNDB_PCIE_ASSERT_QUIRK(_sc, name)	\
180     KASSERT(BHNDB_PCIE_QUIRK((_sc), name), ("quirk " __STRING(_name) " not set"))
181 
182 
183 /* bus_(read|write)_* convenience macros */
184 #define	BHNDB_PCI_READ_2(_sc, _reg)		\
185 	bus_read_2((_sc)->mem_res, (_sc)->mem_off + (_reg))
186 #define	BHNDB_PCI_READ_4(_sc, _reg)		\
187 	bus_read_4((_sc)->mem_res, (_sc)->mem_off + (_reg))
188 
189 #define	BHNDB_PCI_WRITE_2(_sc, _reg, _val)	\
190 	bus_write_2((_sc)->mem_res, (_sc)->mem_off +  (_reg), (_val))
191 #define	BHNDB_PCI_WRITE_4(_sc, _reg, _val)	\
192 	bus_write_4((_sc)->mem_res, (_sc)->mem_off +  (_reg), (_val))
193 
194 
195 /* BHNDB_PCI_REG_* convenience macros */
196 #define	BPCI_REG_EXTRACT(_rv, _a)	BHND_PCI_REG_EXTRACT(_rv, BHND_ ## _a)
197 #define	BPCI_REG_INSERT(_rv, _a, _v)	BHND_PCI_REG_INSERT(_rv, BHND_ ## _a, _v)
198 
199 #define	BPCI_COMMON_REG_EXTRACT(_r, _a)	\
200 	BHND_PCI_COMMON_REG_EXTRACT(sc->regfmt, _r, _a)
201 
202 #define	BPCI_COMMON_REG_INSERT(_r, _a, _v)	\
203 	BHND_PCI_COMMON_REG_INSERT(sc->regfmt, _r, _a, _v)
204 
205 #define	BPCI_COMMON_REG(_name)		\
206 	BHND_PCI_COMMON_REG(sc->regfmt, _name)
207 
208 #define	BPCI_COMMON_REG_OFFSET(_base, _offset)	\
209 	(BPCI_COMMON_REG(_base) + BPCI_COMMON_REG(_offset))
210 
211 /**
212  * Default bhndb_pci implementation of device_probe().
213  *
214  * Verifies that the parent is a PCI/PCIe device.
215  */
216 static int
217 bhndb_pci_probe(device_t dev)
218 {
219 	device_t	parent;
220 	devclass_t	parent_bus;
221 	devclass_t	pci;
222 
223 	/* Our parent must be a PCI/PCIe device. */
224 	pci = devclass_find("pci");
225 	parent = device_get_parent(dev);
226 	parent_bus = device_get_devclass(device_get_parent(parent));
227 
228 	if (parent_bus != pci)
229 		return (ENXIO);
230 
231 	device_set_desc(dev, "PCI-BHND bridge");
232 
233 	return (BUS_PROBE_DEFAULT);
234 }
235 
236 static int
237 bhndb_pci_attach(device_t dev)
238 {
239 	struct bhndb_pci_softc	*sc;
240 	int			 error, reg;
241 
242 	sc = device_get_softc(dev);
243 	sc->dev = dev;
244 
245 	/* Enable PCI bus mastering */
246 	pci_enable_busmaster(device_get_parent(dev));
247 
248 	/* Determine our bridge device class */
249 	sc->pci_devclass = BHND_DEVCLASS_PCI;
250 	if (pci_find_cap(device_get_parent(dev), PCIY_EXPRESS, &reg) == 0)
251 		sc->pci_devclass = BHND_DEVCLASS_PCIE;
252 
253 	/* Determine the basic set of applicable quirks. This will be updated
254 	 * in bhndb_pci_init_full_config() once the PCI device core has
255 	 * been enumerated. */
256 	sc->quirks = bhndb_pci_discover_quirks(sc, NULL);
257 
258 	/* Using the discovered quirks, apply any WARs required for basic
259 	 * register access. */
260 	if ((error = bhndb_pci_wars_register_access(sc)))
261 		return (error);
262 
263 	/* Use siba(4)-compatible regwin handling until we know
264 	 * what kind of bus is attached */
265 	sc->set_regwin = bhndb_pci_compat_setregwin;
266 
267 	/* Perform full bridge attach. This should call back into our
268 	 * bhndb_pci_init_full_config() implementation once the bridged
269 	 * bhnd(4) bus has been enumerated, but before any devices have been
270 	 * probed or attached. */
271 	if ((error = bhndb_attach(dev, sc->pci_devclass)))
272 		return (error);
273 
274 	/* If supported, switch to the faster regwin handling */
275 	if (sc->bhndb.chipid.chip_type != BHND_CHIPTYPE_SIBA) {
276 		atomic_store_rel_ptr((volatile void *) &sc->set_regwin,
277 		    (uintptr_t) &bhndb_pci_fast_setregwin);
278 	}
279 
280 	return (0);
281 }
282 
283 /**
284  * Initialize the full bridge configuration.
285  *
286  * This is called during the DEVICE_ATTACH() process by the bridged bhndb(4)
287  * bus, prior to probe/attachment of child cores.
288  *
289  * At this point, we can introspect the enumerated cores, find our host
290  * bridge device, and apply any bridge-level hardware workarounds required
291  * for proper operation of the bridged device cores.
292  */
293 static int
294 bhndb_pci_init_full_config(device_t dev, device_t child,
295     const struct bhndb_hw_priority *prio_table)
296 {
297 	struct bhnd_core_info		 core;
298 	const struct bhndb_pci_id	*id;
299 	struct bhndb_pci_softc		*sc;
300 	struct bhndb_region		*pcir;
301 	bhnd_addr_t			 pcir_addr;
302 	bhnd_size_t			 pcir_size;
303 	int				 error;
304 
305 	sc = device_get_softc(dev);
306 
307 	/* Let bhndb perform full discovery and initialization of the
308 	 * available register windows and bridge resources. */
309 	if ((error = bhndb_generic_init_full_config(dev, child, prio_table)))
310 		return (error);
311 
312 	/*
313 	 * Identify our PCI bridge core, its register family, and any
314 	 * applicable hardware quirks.
315 	 */
316 	KASSERT(sc->bhndb.hostb_dev,
317 	    ("missing hostb device\n"));
318 
319 	core = bhnd_get_core_info(sc->bhndb.hostb_dev);
320 	id = bhndb_pci_find_core_id(&core);
321 	if (id == NULL) {
322 		device_printf(dev, "%s %s hostb core is not recognized\n",
323 		    bhnd_vendor_name(core.vendor), bhnd_core_name(&core));
324 	}
325 
326 	sc->regfmt = id->regfmt;
327 
328 	/* Now that we've identified the PCI bridge core, we can determine the
329 	 * full set of device quirks */
330 	sc->quirks = bhndb_pci_discover_quirks(sc, id);
331 
332 	/*
333 	 * Determine and save a reference to the bhndb resource and offset
334 	 * at which the bridge core's device registers are mapped.
335 	 *
336 	 * All known bhnd(4) hardware provides a fixed static mapping of
337 	 * the PCI core's registers. If this changes in the future -- which
338 	 * is unlikely -- this driver will need to be adjusted to use
339 	 * dynamic register windows.
340 	 */
341 
342 	/* Find base address and size of the PCI core's register block. */
343 	error = bhnd_get_region_addr(sc->bhndb.hostb_dev, BHND_PORT_DEVICE, 0,
344 	    0, &pcir_addr, &pcir_size);
345 	if (error) {
346 		device_printf(dev,
347 		    "failed to locate PCI core registers\n");
348 		return (error);
349 	}
350 
351 	/* Find the bhndb_region that statically maps this block */
352 	pcir = bhndb_find_resource_region(sc->bhndb.bus_res, pcir_addr,
353 	    pcir_size);
354 	if (pcir == NULL || pcir->static_regwin == NULL) {
355 		device_printf(dev,
356 		    "missing static PCI core register window\n");
357 		return (ENXIO);
358 	}
359 
360 	/* Save borrowed reference to the mapped PCI core registers */
361 	sc->mem_off = pcir->static_regwin->win_offset;
362 	sc->mem_res = bhndb_find_regwin_resource(sc->bhndb.bus_res,
363 	    pcir->static_regwin);
364 	if (sc->mem_res == NULL || !(rman_get_flags(sc->mem_res) & RF_ACTIVE)) {
365 		device_printf(dev,
366 		    "no active resource maps the PCI core register window\n");
367 		return (ENXIO);
368 	}
369 
370 	/* Configure a direct bhnd_resource wrapper that we can pass to
371 	 * bhnd_resource APIs */
372 	sc->bhnd_mem_res = (struct bhnd_resource) {
373 		.res = sc->mem_res,
374 		.direct = true
375 	};
376 
377 	/*
378 	 * Attach MMIO device (if this is a PCIe device), which is used for
379 	 * access to the PCIe SerDes required by the quirk workarounds.
380 	 */
381 	if (sc->pci_devclass == BHND_DEVCLASS_PCIE) {
382 		sc->mdio = BUS_ADD_CHILD(dev, 0,
383 		    devclass_get_name(bhnd_mdio_pci_devclass), 0);
384 		if (sc->mdio == NULL)
385 			return (ENXIO);
386 
387 		error = bus_set_resource(sc->mdio, SYS_RES_MEMORY, 0,
388 		    rman_get_start(sc->mem_res) + sc->mem_off +
389 		    BHND_PCIE_MDIO_CTL, sizeof(uint32_t)*2);
390 		if (error) {
391 			device_printf(dev, "failed to set MDIO resource\n");
392 			return (error);
393 		}
394 
395 		if ((error = device_probe_and_attach(sc->mdio))) {
396 			device_printf(dev, "failed to attach MDIO device\n");
397 			return (error);
398 		}
399 	}
400 
401 	/* Apply any early one-time quirk workarounds */
402 	if ((error = bhndb_pci_wars_early_once(sc)))
403 		return (error);
404 
405 	/* Apply attach-time quirk workarounds, required before the bridged
406 	 * bhnd(4) bus itself performs a full attach(). */
407 	if ((error = bhndb_pci_wars_hwup(sc)))
408 		return (error);
409 
410 	return (0);
411 }
412 
413 /**
414  * Apply any hardware workarounds that must be executed prior to attempting
415  * register access on the bridged chipset.
416  *
417  * This must be called very early in attach() or resume(), after the basic
418  * set of applicable device quirks has been determined.
419  */
420 static int
421 bhndb_pci_wars_register_access(struct bhndb_pci_softc *sc)
422 {
423 	int error;
424 
425 	if (BHNDB_PCI_QUIRK(sc, EXT_CLOCK_GATING)) {
426 		if ((error = bhndb_enable_pci_clocks(sc))) {
427 			device_printf(sc->dev, "failed to enable clocks\n");
428 			return (error);
429 		}
430 	}
431 
432 	return (0);
433 }
434 
435 /**
436  * Apply any hardware work-arounds that must be executed exactly once, early in
437  * the attach process.
438  *
439  * This must be called after core enumeration and discovery of all applicable
440  * quirks, but prior to probe/attach of any cores, parsing of
441  * SPROM, etc.
442  */
443 static int
444 bhndb_pci_wars_early_once(struct bhndb_pci_softc *sc)
445 {
446 	/* Determine correct polarity by observing the attach-time PCIe PHY
447 	 * link status. This is used later to reset/force the SerDes
448 	 * polarity */
449 	if (BHNDB_PCIE_QUIRK(sc, SDR9_POLARITY)) {
450 		uint32_t st;
451 		bool inv;
452 
453 
454 		st = bhndb_pcie_read_proto_reg(sc, BHND_PCIE_PLP_STATUSREG);
455 		inv = ((st & BHND_PCIE_PLP_POLARITY_INV) != 0);
456 		sc->sdr9_quirk_polarity.inv = inv;
457 	}
458 
459 	return (0);
460 }
461 
462 /**
463  * Apply any hardware workarounds that are required upon attach or resume
464  * of the bridge device.
465  */
466 static int
467 bhndb_pci_wars_hwup(struct bhndb_pci_softc *sc)
468 {
469 	/* Note that the order here matters; these work-arounds
470 	 * should not be re-ordered without careful review of their
471 	 * interdependencies */
472 
473 	/* Fix up any PoR defaults on SROMless devices */
474 	bhndb_init_sromless_pci_config(sc);
475 
476 	/* Enable PCI prefetch/burst/readmulti flags */
477 	if (BHNDB_PCI_QUIRK(sc, SBTOPCI2_PREF_BURST) ||
478 	    BHNDB_PCI_QUIRK(sc, SBTOPCI2_READMULTI))
479 	{
480 		uint32_t sbp2;
481 		sbp2 = BHNDB_PCI_READ_4(sc, BHND_PCI_SBTOPCI2);
482 
483 		if (BHNDB_PCI_QUIRK(sc, SBTOPCI2_PREF_BURST))
484 			sbp2 |= (BHND_PCI_SBTOPCI_PREF|BHND_PCI_SBTOPCI_BURST);
485 
486 		if (BHNDB_PCI_QUIRK(sc, SBTOPCI2_READMULTI))
487 			sbp2 |= BHND_PCI_SBTOPCI_RC_READMULTI;
488 
489 		BHNDB_PCI_WRITE_4(sc, BHND_PCI_SBTOPCI2, sbp2);
490 	}
491 
492 	/* Disable PCI CLKRUN# */
493 	if (BHNDB_PCI_QUIRK(sc, CLKRUN_DSBL)) {
494 		uint32_t ctl;
495 
496 		ctl = BHNDB_PCI_READ_4(sc, BHND_PCI_CLKRUN_CTL);
497 		ctl |= BHND_PCI_CLKRUN_DSBL;
498 		BHNDB_PCI_WRITE_4(sc, BHND_PCI_CLKRUN_CTL, ctl);
499 	}
500 
501 	/* Enable TLP unmatched address handling work-around */
502 	if (BHNDB_PCIE_QUIRK(sc, UR_STATUS_FIX)) {
503 		uint32_t wrs;
504 		wrs = bhndb_pcie_read_proto_reg(sc, BHND_PCIE_TLP_WORKAROUNDSREG);
505 		wrs |= BHND_PCIE_TLP_WORKAROUND_URBIT;
506 		bhndb_pcie_write_proto_reg(sc, BHND_PCIE_TLP_WORKAROUNDSREG, wrs);
507 	}
508 
509 	/* Adjust SerDes CDR tuning to ensure that CDR is stable before sending
510 	 * data during L0s to L0 exit transitions. */
511 	if (BHNDB_PCIE_QUIRK(sc, SDR9_L0s_HANG)) {
512 		uint16_t sdv;
513 
514 		/* Set RX track/acquire timers to 2.064us/40.96us */
515 		sdv = BPCI_REG_INSERT(0, PCIE_SDR9_RX_TIMER1_LKTRK, (2064/16));
516 		sdv = BPCI_REG_INSERT(sdv, PCIE_SDR9_RX_TIMER1_LKACQ,
517 		    (40960/1024));
518 		MDIO_WRITEREG(sc->mdio, BHND_PCIE_PHY_SDR9_TXRX,
519 		    BHND_PCIE_SDR9_RX_TIMER1, sdv);
520 
521 		/* Apply CDR frequency workaround */
522 		sdv = BHND_PCIE_SDR9_RX_CDR_FREQ_OVR_EN;
523 		sdv = BPCI_REG_INSERT(sdv, PCIE_SDR9_RX_CDR_FREQ_OVR, 0x0);
524 		MDIO_WRITEREG(sc->mdio, BHND_PCIE_PHY_SDR9_TXRX,
525 		    BHND_PCIE_SDR9_RX_CDR, sdv);
526 
527 		/* Apply CDR BW tunings */
528 		sdv = 0;
529 		sdv = BPCI_REG_INSERT(sdv, PCIE_SDR9_RX_CDRBW_INTGTRK, 0x2);
530 		sdv = BPCI_REG_INSERT(sdv, PCIE_SDR9_RX_CDRBW_INTGACQ, 0x4);
531 		sdv = BPCI_REG_INSERT(sdv, PCIE_SDR9_RX_CDRBW_PROPTRK, 0x6);
532 		sdv = BPCI_REG_INSERT(sdv, PCIE_SDR9_RX_CDRBW_PROPACQ, 0x6);
533 		MDIO_WRITEREG(sc->mdio, BHND_PCIE_PHY_SDR9_TXRX,
534 		    BHND_PCIE_SDR9_RX_CDRBW, sdv);
535 	}
536 
537 	/* Force correct SerDes polarity */
538 	if (BHNDB_PCIE_QUIRK(sc, SDR9_POLARITY)) {
539 		uint16_t	rxctl;
540 
541 		rxctl = MDIO_READREG(sc->mdio, BHND_PCIE_PHY_SDR9_TXRX,
542 		    BHND_PCIE_SDR9_RX_CTRL);
543 
544 		rxctl |= BHND_PCIE_SDR9_RX_CTRL_FORCE;
545 		if (sc->sdr9_quirk_polarity.inv)
546 			rxctl |= BHND_PCIE_SDR9_RX_CTRL_POLARITY_INV;
547 		else
548 			rxctl &= ~BHND_PCIE_SDR9_RX_CTRL_POLARITY_INV;
549 
550 		MDIO_WRITEREG(sc->mdio, BHND_PCIE_PHY_SDR9_TXRX,
551 		    BHND_PCIE_SDR9_RX_CTRL, rxctl);
552 	}
553 
554 	/* Disable startup retry on PLL frequency detection failure */
555 	if (BHNDB_PCIE_QUIRK(sc, SDR9_NO_FREQRETRY)) {
556 		uint16_t	pctl;
557 
558 		pctl = MDIO_READREG(sc->mdio, BHND_PCIE_PHY_SDR9_PLL,
559 		    BHND_PCIE_SDR9_PLL_CTRL);
560 
561 		pctl &= ~BHND_PCIE_SDR9_PLL_CTRL_FREQDET_EN;
562 		MDIO_WRITEREG(sc->mdio, BHND_PCIE_PHY_SDR9_PLL,
563 		    BHND_PCIE_SDR9_PLL_CTRL, pctl);
564 	}
565 
566 	/* Explicitly enable PCI-PM */
567 	if (BHNDB_PCIE_QUIRK(sc, PCIPM_REQEN)) {
568 		uint32_t lcreg;
569 		lcreg = bhndb_pcie_read_proto_reg(sc, BHND_PCIE_DLLP_LCREG);
570 		lcreg |= BHND_PCIE_DLLP_LCREG_PCIPM_EN;
571 		bhndb_pcie_write_proto_reg(sc, BHND_PCIE_DLLP_LCREG, lcreg);
572 	}
573 
574 	/* Adjust L1 timer to fix slow L1->L0 transitions */
575 	if (BHNDB_PCIE_QUIRK(sc, L1_IDLE_THRESH)) {
576 		uint32_t pmt;
577 		pmt = bhndb_pcie_read_proto_reg(sc, BHND_PCIE_DLLP_PMTHRESHREG);
578 		pmt = BPCI_REG_INSERT(pmt, PCIE_L1THRESHOLDTIME,
579 		    BHND_PCIE_L1THRESHOLD_WARVAL);
580 		bhndb_pcie_write_proto_reg(sc, BHND_PCIE_DLLP_PMTHRESHREG, pmt);
581 	}
582 
583 	/* Extend L1 timer for better performance.
584 	 * TODO: We could enable/disable this on demand for better power
585 	 * savings if we tie this to HT clock request handling */
586 	if (BHNDB_PCIE_QUIRK(sc, L1_TIMER_PERF)) {
587 		uint32_t pmt;
588 		pmt = bhndb_pcie_read_proto_reg(sc, BHND_PCIE_DLLP_PMTHRESHREG);
589 		pmt |= BHND_PCIE_ASPMTIMER_EXTEND;
590 		bhndb_pcie_write_proto_reg(sc, BHND_PCIE_DLLP_PMTHRESHREG, pmt);
591 	}
592 
593 	/* Enable L23READY_EXIT_NOPRST if not already set in SPROM. */
594 	if (BHNDB_PCIE_QUIRK(sc, SPROM_L23_PCI_RESET)) {
595 		bus_size_t	reg;
596 		uint16_t	cfg;
597 
598 		/* Fetch the misc cfg flags from SPROM */
599 		reg = BHND_PCIE_SPROM_SHADOW + BHND_PCIE_SRSH_PCIE_MISC_CONFIG;
600 		cfg = BHNDB_PCI_READ_2(sc, reg);
601 
602 		/* Write EXIT_NOPRST flag if not already set in SPROM */
603 		if (!(cfg & BHND_PCIE_SRSH_L23READY_EXIT_NOPRST)) {
604 			cfg |= BHND_PCIE_SRSH_L23READY_EXIT_NOPRST;
605 			BHNDB_PCI_WRITE_2(sc, reg, cfg);
606 		}
607 	}
608 
609 	return (0);
610 }
611 
612 /**
613  * Apply any hardware workarounds that are required upon resume of the
614  * bridge device.
615  *
616  * This must be called before any bridged bhnd(4) cores have been resumed.
617  */
618 static int
619 bhndb_pci_wars_hwresume(struct bhndb_pci_softc *sc)
620 {
621 	int error;
622 
623 	/* Nothing is possible without register access */
624 	if ((error = bhndb_pci_wars_register_access(sc)))
625 		return (error);
626 
627 	/* Apply the general hwup workarounds */
628 	return (bhndb_pci_wars_hwup(sc));
629 }
630 
631 /**
632  * Apply any hardware workarounds that are required upon detach or suspend
633  * of the bridge device.
634  */
635 static int
636 bhndb_pci_wars_hwdown(struct bhndb_pci_softc *sc)
637 {
638 	int error;
639 
640 	/* Reduce L1 timer for better power savings.
641 	 * TODO: We could enable/disable this on demand for better power
642 	 * savings if we tie this to HT clock request handling */
643 	if (BHNDB_PCIE_QUIRK(sc, L1_TIMER_PERF)) {
644 		uint32_t pmt;
645 		pmt = bhndb_pcie_read_proto_reg(sc, BHND_PCIE_DLLP_PMTHRESHREG);
646 		pmt &= ~BHND_PCIE_ASPMTIMER_EXTEND;
647 		bhndb_pcie_write_proto_reg(sc, BHND_PCIE_DLLP_PMTHRESHREG, pmt);
648 	}
649 
650 	/* Disable clocks */
651 	if (BHNDB_PCI_QUIRK(sc, EXT_CLOCK_GATING)) {
652 		if ((error = bhndb_disable_pci_clocks(sc))) {
653 			device_printf(sc->dev, "failed to disable clocks\n");
654 			return (error);
655 		}
656 	}
657 
658 	return (0);
659 }
660 
661 /*
662  * On devices without a SROM, the PCI(e) cores will be initialized with
663  * their Power-on-Reset defaults; this can leave the the BAR0 PCI windows
664  * potentially mapped to the wrong core index.
665  *
666  * This function updates the PCI core's BAR0 PCI configuration to point at the
667  * current PCI core.
668  *
669  * Applies to all PCI/PCIe revisions. Must be applied before bus devices
670  * are probed/attached or the SPROM is parsed.
671  */
672 static void
673 bhndb_init_sromless_pci_config(struct bhndb_pci_softc *sc)
674 {
675 	bus_size_t	sprom_addr;
676 	u_int		sprom_core_idx;
677 	u_int		pci_core_idx;
678 	uint16_t	val;
679 
680 	/* Fetch the SPROM's configured core index */
681 	sprom_addr = BPCI_COMMON_REG_OFFSET(SPROM_SHADOW, SRSH_PI_OFFSET);
682 	val = BHNDB_PCI_READ_2(sc, sprom_addr);
683 
684 	/* If it doesn't match host bridge's core index, update the index
685 	 * value */
686 	sprom_core_idx = BPCI_COMMON_REG_EXTRACT(val, SRSH_PI);
687 	pci_core_idx = bhnd_get_core_index(sc->bhndb.hostb_dev);
688 
689 	if (sprom_core_idx != pci_core_idx) {
690 		val = BPCI_COMMON_REG_INSERT(val, SRSH_PI, pci_core_idx);
691 		BHNDB_PCI_WRITE_2(sc, sprom_addr, val);
692 	}
693 }
694 
695 static int
696 bhndb_pci_detach(device_t dev)
697 {
698 	struct bhndb_pci_softc	*sc;
699 	int			 error;
700 
701 	sc = device_get_softc(dev);
702 
703 	if ((error = bhndb_generic_detach(dev)))
704 		return (error);
705 
706 	/* Apply any hardware workarounds. This may disable the clock, and
707 	 * thus must be called *after* any children have been detached. */
708 	if ((error = bhndb_pci_wars_hwdown(sc)))
709 		return (error);
710 
711 	/* Disable PCI bus mastering */
712 	pci_disable_busmaster(device_get_parent(dev));
713 
714 	return (0);
715 }
716 
717 static int
718 bhndb_pci_suspend(device_t dev)
719 {
720 	struct bhndb_pci_softc	*sc;
721 	int			 error;
722 
723 	sc = device_get_softc(dev);
724 
725 	if ((error = bhndb_generic_suspend(dev)))
726 		return (error);
727 
728 	/* Apply any hardware workarounds. This may disable the clock, and
729 	 * thus must be called *after* any children have been suspended. */
730 	if ((error = bhndb_pci_wars_hwdown(sc)))
731 		return (error);
732 
733 	return (0);
734 }
735 
736 static int
737 bhndb_pci_resume(device_t dev)
738 {
739 	struct bhndb_pci_softc	*sc;
740 	int			 error;
741 
742 	sc = device_get_softc(dev);
743 
744 	/* Apply any resume workarounds; these may be required for bridged
745 	 * device access, and thus must be called *before* any children are
746 	 * resumed. */
747 	if ((error = bhndb_pci_wars_hwresume(sc)))
748 		return (error);
749 
750 	if ((error = bhndb_generic_resume(dev)))
751 		return (error);
752 
753 	return (0);
754 }
755 
756 static int
757 bhndb_pci_set_window_addr(device_t dev, const struct bhndb_regwin *rw,
758     bhnd_addr_t addr)
759 {
760 	struct bhndb_pci_softc *sc = device_get_softc(dev);
761 	return (sc->set_regwin(sc, rw, addr));
762 }
763 
764 /**
765  * A siba(4) and bcma(4)-compatible bhndb_set_window_addr implementation.
766  *
767  * On siba(4) devices, it's possible that writing a PCI window register may
768  * not succeed; it's necessary to immediately read the configuration register
769  * and retry if not set to the desired value.
770  *
771  * This is not necessary on bcma(4) devices, but other than the overhead of
772  * validating the register, there's no harm in performing the verification.
773  */
774 static int
775 bhndb_pci_compat_setregwin(struct bhndb_pci_softc *sc,
776     const struct bhndb_regwin *rw, bhnd_addr_t addr)
777 {
778 	device_t	parent;
779 	int		error;
780 
781 	parent = sc->bhndb.parent_dev;
782 
783 	if (rw->win_type != BHNDB_REGWIN_T_DYN)
784 		return (ENODEV);
785 
786 	for (u_int i = 0; i < BHNDB_PCI_BARCTRL_WRITE_RETRY; i++) {
787 		if ((error = bhndb_pci_fast_setregwin(sc, rw, addr)))
788 			return (error);
789 
790 		if (pci_read_config(parent, rw->dyn.cfg_offset, 4) == addr)
791 			return (0);
792 
793 		DELAY(10);
794 	}
795 
796 	/* Unable to set window */
797 	return (ENODEV);
798 }
799 
800 /**
801  * A bcma(4)-only bhndb_set_window_addr implementation.
802  */
803 static int
804 bhndb_pci_fast_setregwin(struct bhndb_pci_softc *sc,
805     const struct bhndb_regwin *rw, bhnd_addr_t addr)
806 {
807 	device_t parent = sc->bhndb.parent_dev;
808 
809 	/* The PCI bridge core only supports 32-bit addressing, regardless
810 	 * of the bus' support for 64-bit addressing */
811 	if (addr > UINT32_MAX)
812 		return (ERANGE);
813 
814 	switch (rw->win_type) {
815 	case BHNDB_REGWIN_T_DYN:
816 		/* Addresses must be page aligned */
817 		if (addr % rw->win_size != 0)
818 			return (EINVAL);
819 
820 		pci_write_config(parent, rw->dyn.cfg_offset, addr, 4);
821 		break;
822 	default:
823 		return (ENODEV);
824 	}
825 
826 	return (0);
827 }
828 
829 
830 /**
831  * Read a 32-bit PCIe TLP/DLLP/PLP protocol register.
832  *
833  * @param sc The bhndb_pci driver state.
834  * @param addr The protocol register offset.
835  */
836 static uint32_t
837 bhndb_pcie_read_proto_reg(struct bhndb_pci_softc *sc, uint32_t addr)
838 {
839 	uint32_t val;
840 
841 	KASSERT(bhnd_get_class(sc->bhndb.hostb_dev) == BHND_DEVCLASS_PCIE,
842 	    ("not a pcie device!"));
843 
844 	BHNDB_LOCK(&sc->bhndb);
845 	BHNDB_PCI_WRITE_4(sc, BHND_PCIE_IND_ADDR, addr);
846 	val = BHNDB_PCI_READ_4(sc, BHND_PCIE_IND_DATA);
847 	BHNDB_UNLOCK(&sc->bhndb);
848 
849 	return (val);
850 }
851 
852 /**
853  * Write a 32-bit PCIe TLP/DLLP/PLP protocol register value.
854  *
855  * @param sc The bhndb_pci driver state.
856  * @param addr The protocol register offset.
857  * @param val The value to write to @p addr.
858  */
859 static void
860 bhndb_pcie_write_proto_reg(struct bhndb_pci_softc *sc, uint32_t addr,
861     uint32_t val)
862 {
863 	KASSERT(bhnd_get_class(sc->bhndb.hostb_dev) == BHND_DEVCLASS_PCIE,
864 	    ("not a pcie device!"));
865 
866 	BHNDB_LOCK(&sc->bhndb);
867 	BHNDB_PCI_WRITE_4(sc, BHND_PCIE_IND_ADDR, addr);
868 	BHNDB_PCI_WRITE_4(sc, BHND_PCIE_IND_DATA, val);
869 	BHNDB_UNLOCK(&sc->bhndb);
870 }
871 
872 
873 /**
874  * Enable externally managed clocks.
875  *
876  * Quirk Required: EXT_CLOCK_GATING
877  *
878  * @param sc Bridge driver state.
879  */
880 static int
881 bhndb_enable_pci_clocks(struct bhndb_pci_softc *sc)
882 {
883 	device_t		pci_parent;
884 	uint32_t		gpio_in, gpio_out, gpio_en;
885 	uint32_t		gpio_flags;
886 	uint16_t		pci_status;
887 
888 	BHNDB_PCI_ASSERT_QUIRK(sc, EXT_CLOCK_GATING);
889 
890 	pci_parent = device_get_parent(sc->dev);
891 
892 	/* Read state of XTAL pin */
893 	gpio_in = pci_read_config(pci_parent, BHNDB_PCI_GPIO_IN, 4);
894 	if (gpio_in & BHNDB_PCI_GPIO_XTAL_ON)
895 		return (0); /* already enabled */
896 
897 	/* Fetch current config */
898 	gpio_out = pci_read_config(pci_parent, BHNDB_PCI_GPIO_OUT, 4);
899 	gpio_en = pci_read_config(pci_parent, BHNDB_PCI_GPIO_OUTEN, 4);
900 
901 	/* Set PLL_OFF/XTAL_ON pins to HIGH and enable both pins */
902 	gpio_flags = (BHNDB_PCI_GPIO_PLL_OFF|BHNDB_PCI_GPIO_XTAL_ON);
903 	gpio_out |= gpio_flags;
904 	gpio_en |= gpio_flags;
905 
906 	pci_write_config(pci_parent, BHNDB_PCI_GPIO_OUT, gpio_out, 4);
907 	pci_write_config(pci_parent, BHNDB_PCI_GPIO_OUTEN, gpio_en, 4);
908 	DELAY(1000);
909 
910 	/* Reset PLL_OFF */
911 	gpio_out &= ~BHNDB_PCI_GPIO_PLL_OFF;
912 	pci_write_config(pci_parent, BHNDB_PCI_GPIO_OUT, gpio_out, 4);
913 	DELAY(5000);
914 
915 	/* Clear any PCI 'sent target-abort' flag. */
916 	pci_status = pci_read_config(pci_parent, PCIR_STATUS, 2);
917 	pci_status &= ~PCIM_STATUS_STABORT;
918 	pci_write_config(pci_parent, PCIR_STATUS, pci_status, 2);
919 
920 	return (0);
921 }
922 
923 /**
924  * Disable externally managed clocks.
925  *
926  * Quirk Required: EXT_CLOCK_GATING
927  *
928  * @param sc Bridge driver state.
929  */
930 static int
931 bhndb_disable_pci_clocks(struct bhndb_pci_softc *sc)
932 {
933 	device_t	parent_dev;
934 	uint32_t	gpio_out, gpio_en;
935 
936 	BHNDB_PCI_ASSERT_QUIRK(sc, EXT_CLOCK_GATING);
937 
938 	parent_dev = device_get_parent(sc->dev);
939 
940 	// TODO: Check board flags for BFL2_XTALBUFOUTEN?
941 	// TODO: Check PCI core revision?
942 	// TODO: Switch to 'slow' clock?
943 
944 	/* Fetch current config */
945 	gpio_out = pci_read_config(parent_dev, BHNDB_PCI_GPIO_OUT, 4);
946 	gpio_en = pci_read_config(parent_dev, BHNDB_PCI_GPIO_OUTEN, 4);
947 
948 	/* Set PLL_OFF to HIGH, XTAL_ON to LOW. */
949 	gpio_out &= ~BHNDB_PCI_GPIO_XTAL_ON;
950 	gpio_out |= BHNDB_PCI_GPIO_PLL_OFF;
951 	pci_write_config(parent_dev, BHNDB_PCI_GPIO_OUT, gpio_out, 4);
952 
953 	/* Enable both output pins */
954 	gpio_en |= (BHNDB_PCI_GPIO_PLL_OFF|BHNDB_PCI_GPIO_XTAL_ON);
955 	pci_write_config(parent_dev, BHNDB_PCI_GPIO_OUTEN, gpio_en, 4);
956 
957 	return (0);
958 }
959 
960 
961 /**
962  * Find the identification table entry for a core descriptor.
963  *
964  * @param sc bhndb PCI driver state.
965  */
966 static const struct bhndb_pci_id *
967 bhndb_pci_find_core_id(struct bhnd_core_info *core)
968 {
969 	const struct bhndb_pci_id *id;
970 
971 	for (id = bhndb_pci_ids; id->device != BHND_COREID_INVALID; id++) {
972 		if (core->vendor == BHND_MFGID_BCM &&
973 		    core->device == id->device)
974 			return (id);
975 	}
976 
977 	return (NULL);
978 }
979 
980 /**
981  * Return all quirks known to be applicable to the host bridge.
982  *
983  * If the PCI bridge core has not yet been identified, no core-specific
984  * quirk flags will be returned. This function may be called again to
985  * rediscover applicable quirks after the host bridge core has been
986  * identified.
987  *
988  * @param sc bhndb PCI driver state.
989  * @param id The host bridge core's identification table entry, or NULL
990  * if the host bridge core has not yet been identified.
991  *
992  * @return Returns the set of quirks applicable to the current hardware.
993  */
994 static uint32_t
995 bhndb_pci_discover_quirks(struct bhndb_pci_softc *sc,
996     const struct bhndb_pci_id *id)
997 {
998 	struct bhnd_device_quirk	*qt;
999 	uint32_t			 quirks;
1000 	uint8_t				 hwrev;
1001 
1002 	quirks = BHNDB_PCI_QUIRK_NONE;
1003 
1004 	/* Determine any device class-specific quirks */
1005 	switch (sc->pci_devclass) {
1006 	case BHND_DEVCLASS_PCI:
1007 		/* All PCI devices require external clock gating */
1008 		sc->quirks |= BHNDB_PCI_QUIRK_EXT_CLOCK_GATING;
1009 		break;
1010 	default:
1011 		break;
1012 	}
1013 
1014 	// TODO: Additional quirk matching
1015 
1016 	/* Determine any PCI core hwrev-specific device quirks */
1017 	if (id != NULL) {
1018 		hwrev = bhnd_get_hwrev(sc->bhndb.hostb_dev);
1019 		for (qt = id->quirks; qt->quirks != 0; qt++) {
1020 			if (bhnd_hwrev_matches(hwrev, &qt->hwrev))
1021 				quirks |= qt->quirks;
1022 		}
1023 	}
1024 
1025 
1026 	return (quirks);
1027 }
1028 
1029 /*
1030  * Support for attaching the PCIe-Gen1 MDIO driver to a parent bhndb PCIe
1031  * bridge device.
1032  */
1033 static int
1034 bhndb_mdio_pcie_probe(device_t dev)
1035 {
1036 	device_quiet(dev);
1037 	return (BUS_PROBE_NOWILDCARD);
1038 }
1039 
1040 static int
1041 bhndb_mdio_pcie_attach(device_t dev)
1042 {
1043 	struct bhndb_pci_softc	*psc;
1044 	psc = device_get_softc(device_get_parent(dev));
1045 	return (bhnd_mdio_pcie_attach(dev,
1046 	    &psc->bhnd_mem_res, -1,
1047 	    psc->mem_off + BHND_PCIE_MDIO_CTL,
1048 	    (psc->quirks & BHNDB_PCIE_QUIRK_SD_C22_EXTADDR) != 0));
1049 }
1050 
1051 static device_method_t bhnd_mdio_pcie_methods[] = {
1052 	/* Device interface */
1053 	DEVMETHOD(device_probe,			bhndb_mdio_pcie_probe),
1054 	DEVMETHOD(device_attach,		bhndb_mdio_pcie_attach),
1055 	DEVMETHOD_END
1056 };
1057 
1058 static device_method_t bhndb_pci_methods[] = {
1059 	/* Device interface */
1060 	DEVMETHOD(device_probe,			bhndb_pci_probe),
1061 	DEVMETHOD(device_attach,		bhndb_pci_attach),
1062 	DEVMETHOD(device_detach,		bhndb_pci_detach),
1063 	DEVMETHOD(device_suspend,		bhndb_pci_suspend),
1064 	DEVMETHOD(device_resume,		bhndb_pci_resume),
1065 
1066 	/* BHNDB interface */
1067 	DEVMETHOD(bhndb_init_full_config,	bhndb_pci_init_full_config),
1068 	DEVMETHOD(bhndb_set_window_addr,	bhndb_pci_set_window_addr),
1069 
1070 	DEVMETHOD_END
1071 };
1072 
1073 DEFINE_CLASS_1(bhndb, bhndb_pci_driver, bhndb_pci_methods,
1074     sizeof(struct bhndb_pci_softc), bhndb_driver);
1075 
1076 DEFINE_CLASS_1(bhnd_mdio_pci, bhndb_mdio_pcie_driver, bhnd_mdio_pcie_methods,
1077     sizeof(struct bhnd_mdio_pcie_softc), bhnd_mdio_pcie_driver);
1078 
1079 DRIVER_MODULE(bhnd_mdio_pcie, bhndb, bhndb_mdio_pcie_driver,
1080     bhnd_mdio_pci_devclass, NULL, NULL);
1081 
1082 MODULE_VERSION(bhndb_pci, 1);
1083 MODULE_DEPEND(bhndb_pci, bhnd_pci, 1, 1, 1);
1084 MODULE_DEPEND(bhndb_pci, pci, 1, 1, 1);
1085 MODULE_DEPEND(bhndb_pci, bhndb, 1, 1, 1);
1086