162306a36Sopenharmony_ci// SPDX-License-Identifier: GPL-2.0-or-later
262306a36Sopenharmony_ci/*
362306a36Sopenharmony_ci * Support for PCI bridges found on Power Macintoshes.
462306a36Sopenharmony_ci *
562306a36Sopenharmony_ci * Copyright (C) 2003-2005 Benjamin Herrenschmuidt (benh@kernel.crashing.org)
662306a36Sopenharmony_ci * Copyright (C) 1997 Paul Mackerras (paulus@samba.org)
762306a36Sopenharmony_ci */
862306a36Sopenharmony_ci
962306a36Sopenharmony_ci#include <linux/kernel.h>
1062306a36Sopenharmony_ci#include <linux/pci.h>
1162306a36Sopenharmony_ci#include <linux/delay.h>
1262306a36Sopenharmony_ci#include <linux/string.h>
1362306a36Sopenharmony_ci#include <linux/init.h>
1462306a36Sopenharmony_ci#include <linux/irq.h>
1562306a36Sopenharmony_ci#include <linux/of_address.h>
1662306a36Sopenharmony_ci#include <linux/of_irq.h>
1762306a36Sopenharmony_ci#include <linux/of_pci.h>
1862306a36Sopenharmony_ci
1962306a36Sopenharmony_ci#include <asm/sections.h>
2062306a36Sopenharmony_ci#include <asm/io.h>
2162306a36Sopenharmony_ci#include <asm/pci-bridge.h>
2262306a36Sopenharmony_ci#include <asm/machdep.h>
2362306a36Sopenharmony_ci#include <asm/pmac_feature.h>
2462306a36Sopenharmony_ci#include <asm/grackle.h>
2562306a36Sopenharmony_ci#include <asm/ppc-pci.h>
2662306a36Sopenharmony_ci
2762306a36Sopenharmony_ci#include "pmac.h"
2862306a36Sopenharmony_ci
2962306a36Sopenharmony_ci#undef DEBUG
3062306a36Sopenharmony_ci
3162306a36Sopenharmony_ci#ifdef DEBUG
3262306a36Sopenharmony_ci#define DBG(x...) printk(x)
3362306a36Sopenharmony_ci#else
3462306a36Sopenharmony_ci#define DBG(x...)
3562306a36Sopenharmony_ci#endif
3662306a36Sopenharmony_ci
3762306a36Sopenharmony_ci/* XXX Could be per-controller, but I don't think we risk anything by
3862306a36Sopenharmony_ci * assuming we won't have both UniNorth and Bandit */
3962306a36Sopenharmony_cistatic int has_uninorth;
4062306a36Sopenharmony_ci#ifdef CONFIG_PPC64
4162306a36Sopenharmony_cistatic struct pci_controller *u3_agp;
4262306a36Sopenharmony_ci#else
4362306a36Sopenharmony_cistatic int has_second_ohare;
4462306a36Sopenharmony_ci#endif /* CONFIG_PPC64 */
4562306a36Sopenharmony_ci
4662306a36Sopenharmony_ciextern int pcibios_assign_bus_offset;
4762306a36Sopenharmony_ci
4862306a36Sopenharmony_cistruct device_node *k2_skiplist[2];
4962306a36Sopenharmony_ci
5062306a36Sopenharmony_ci/*
5162306a36Sopenharmony_ci * Magic constants for enabling cache coherency in the bandit/PSX bridge.
5262306a36Sopenharmony_ci */
5362306a36Sopenharmony_ci#define BANDIT_DEVID_2	8
5462306a36Sopenharmony_ci#define BANDIT_REVID	3
5562306a36Sopenharmony_ci
5662306a36Sopenharmony_ci#define BANDIT_DEVNUM	11
5762306a36Sopenharmony_ci#define BANDIT_MAGIC	0x50
5862306a36Sopenharmony_ci#define BANDIT_COHERENT	0x40
5962306a36Sopenharmony_ci
6062306a36Sopenharmony_cistatic int __init fixup_one_level_bus_range(struct device_node *node, int higher)
6162306a36Sopenharmony_ci{
6262306a36Sopenharmony_ci	for (; node; node = node->sibling) {
6362306a36Sopenharmony_ci		const int * bus_range;
6462306a36Sopenharmony_ci		const unsigned int *class_code;
6562306a36Sopenharmony_ci		int len;
6662306a36Sopenharmony_ci
6762306a36Sopenharmony_ci		/* For PCI<->PCI bridges or CardBus bridges, we go down */
6862306a36Sopenharmony_ci		class_code = of_get_property(node, "class-code", NULL);
6962306a36Sopenharmony_ci		if (!class_code || ((*class_code >> 8) != PCI_CLASS_BRIDGE_PCI &&
7062306a36Sopenharmony_ci			(*class_code >> 8) != PCI_CLASS_BRIDGE_CARDBUS))
7162306a36Sopenharmony_ci			continue;
7262306a36Sopenharmony_ci		bus_range = of_get_property(node, "bus-range", &len);
7362306a36Sopenharmony_ci		if (bus_range != NULL && len > 2 * sizeof(int)) {
7462306a36Sopenharmony_ci			if (bus_range[1] > higher)
7562306a36Sopenharmony_ci				higher = bus_range[1];
7662306a36Sopenharmony_ci		}
7762306a36Sopenharmony_ci		higher = fixup_one_level_bus_range(node->child, higher);
7862306a36Sopenharmony_ci	}
7962306a36Sopenharmony_ci	return higher;
8062306a36Sopenharmony_ci}
8162306a36Sopenharmony_ci
8262306a36Sopenharmony_ci/* This routine fixes the "bus-range" property of all bridges in the
8362306a36Sopenharmony_ci * system since they tend to have their "last" member wrong on macs
8462306a36Sopenharmony_ci *
8562306a36Sopenharmony_ci * Note that the bus numbers manipulated here are OF bus numbers, they
8662306a36Sopenharmony_ci * are not Linux bus numbers.
8762306a36Sopenharmony_ci */
8862306a36Sopenharmony_cistatic void __init fixup_bus_range(struct device_node *bridge)
8962306a36Sopenharmony_ci{
9062306a36Sopenharmony_ci	int *bus_range, len;
9162306a36Sopenharmony_ci	struct property *prop;
9262306a36Sopenharmony_ci
9362306a36Sopenharmony_ci	/* Lookup the "bus-range" property for the hose */
9462306a36Sopenharmony_ci	prop = of_find_property(bridge, "bus-range", &len);
9562306a36Sopenharmony_ci	if (prop == NULL || prop->length < 2 * sizeof(int))
9662306a36Sopenharmony_ci		return;
9762306a36Sopenharmony_ci
9862306a36Sopenharmony_ci	bus_range = prop->value;
9962306a36Sopenharmony_ci	bus_range[1] = fixup_one_level_bus_range(bridge->child, bus_range[1]);
10062306a36Sopenharmony_ci}
10162306a36Sopenharmony_ci
10262306a36Sopenharmony_ci/*
10362306a36Sopenharmony_ci * Apple MacRISC (U3, UniNorth, Bandit, Chaos) PCI controllers.
10462306a36Sopenharmony_ci *
10562306a36Sopenharmony_ci * The "Bandit" version is present in all early PCI PowerMacs,
10662306a36Sopenharmony_ci * and up to the first ones using Grackle. Some machines may
10762306a36Sopenharmony_ci * have 2 bandit controllers (2 PCI busses).
10862306a36Sopenharmony_ci *
10962306a36Sopenharmony_ci * "Chaos" is used in some "Bandit"-type machines as a bridge
11062306a36Sopenharmony_ci * for the separate display bus. It is accessed the same
11162306a36Sopenharmony_ci * way as bandit, but cannot be probed for devices. It therefore
11262306a36Sopenharmony_ci * has its own config access functions.
11362306a36Sopenharmony_ci *
11462306a36Sopenharmony_ci * The "UniNorth" version is present in all Core99 machines
11562306a36Sopenharmony_ci * (iBook, G4, new IMacs, and all the recent Apple machines).
11662306a36Sopenharmony_ci * It contains 3 controllers in one ASIC.
11762306a36Sopenharmony_ci *
11862306a36Sopenharmony_ci * The U3 is the bridge used on G5 machines. It contains an
11962306a36Sopenharmony_ci * AGP bus which is dealt with the old UniNorth access routines
12062306a36Sopenharmony_ci * and a HyperTransport bus which uses its own set of access
12162306a36Sopenharmony_ci * functions.
12262306a36Sopenharmony_ci */
12362306a36Sopenharmony_ci
12462306a36Sopenharmony_ci#define MACRISC_CFA0(devfn, off)	\
12562306a36Sopenharmony_ci	((1 << (unsigned int)PCI_SLOT(dev_fn)) \
12662306a36Sopenharmony_ci	| (((unsigned int)PCI_FUNC(dev_fn)) << 8) \
12762306a36Sopenharmony_ci	| (((unsigned int)(off)) & 0xFCUL))
12862306a36Sopenharmony_ci
12962306a36Sopenharmony_ci#define MACRISC_CFA1(bus, devfn, off)	\
13062306a36Sopenharmony_ci	((((unsigned int)(bus)) << 16) \
13162306a36Sopenharmony_ci	|(((unsigned int)(devfn)) << 8) \
13262306a36Sopenharmony_ci	|(((unsigned int)(off)) & 0xFCUL) \
13362306a36Sopenharmony_ci	|1UL)
13462306a36Sopenharmony_ci
13562306a36Sopenharmony_cistatic void __iomem *macrisc_cfg_map_bus(struct pci_bus *bus,
13662306a36Sopenharmony_ci					 unsigned int dev_fn,
13762306a36Sopenharmony_ci					 int offset)
13862306a36Sopenharmony_ci{
13962306a36Sopenharmony_ci	unsigned int caddr;
14062306a36Sopenharmony_ci	struct pci_controller *hose;
14162306a36Sopenharmony_ci
14262306a36Sopenharmony_ci	hose = pci_bus_to_host(bus);
14362306a36Sopenharmony_ci	if (hose == NULL)
14462306a36Sopenharmony_ci		return NULL;
14562306a36Sopenharmony_ci
14662306a36Sopenharmony_ci	if (bus->number == hose->first_busno) {
14762306a36Sopenharmony_ci		if (dev_fn < (11 << 3))
14862306a36Sopenharmony_ci			return NULL;
14962306a36Sopenharmony_ci		caddr = MACRISC_CFA0(dev_fn, offset);
15062306a36Sopenharmony_ci	} else
15162306a36Sopenharmony_ci		caddr = MACRISC_CFA1(bus->number, dev_fn, offset);
15262306a36Sopenharmony_ci
15362306a36Sopenharmony_ci	/* Uninorth will return garbage if we don't read back the value ! */
15462306a36Sopenharmony_ci	do {
15562306a36Sopenharmony_ci		out_le32(hose->cfg_addr, caddr);
15662306a36Sopenharmony_ci	} while (in_le32(hose->cfg_addr) != caddr);
15762306a36Sopenharmony_ci
15862306a36Sopenharmony_ci	offset &= has_uninorth ? 0x07 : 0x03;
15962306a36Sopenharmony_ci	return hose->cfg_data + offset;
16062306a36Sopenharmony_ci}
16162306a36Sopenharmony_ci
16262306a36Sopenharmony_cistatic struct pci_ops macrisc_pci_ops =
16362306a36Sopenharmony_ci{
16462306a36Sopenharmony_ci	.map_bus = macrisc_cfg_map_bus,
16562306a36Sopenharmony_ci	.read = pci_generic_config_read,
16662306a36Sopenharmony_ci	.write = pci_generic_config_write,
16762306a36Sopenharmony_ci};
16862306a36Sopenharmony_ci
16962306a36Sopenharmony_ci#ifdef CONFIG_PPC32
17062306a36Sopenharmony_ci/*
17162306a36Sopenharmony_ci * Verify that a specific (bus, dev_fn) exists on chaos
17262306a36Sopenharmony_ci */
17362306a36Sopenharmony_cistatic void __iomem *chaos_map_bus(struct pci_bus *bus, unsigned int devfn,
17462306a36Sopenharmony_ci				   int offset)
17562306a36Sopenharmony_ci{
17662306a36Sopenharmony_ci	struct device_node *np;
17762306a36Sopenharmony_ci	const u32 *vendor, *device;
17862306a36Sopenharmony_ci
17962306a36Sopenharmony_ci	if (offset >= 0x100)
18062306a36Sopenharmony_ci		return NULL;
18162306a36Sopenharmony_ci	np = of_pci_find_child_device(bus->dev.of_node, devfn);
18262306a36Sopenharmony_ci	if (np == NULL)
18362306a36Sopenharmony_ci		return NULL;
18462306a36Sopenharmony_ci
18562306a36Sopenharmony_ci	vendor = of_get_property(np, "vendor-id", NULL);
18662306a36Sopenharmony_ci	device = of_get_property(np, "device-id", NULL);
18762306a36Sopenharmony_ci	if (vendor == NULL || device == NULL)
18862306a36Sopenharmony_ci		return NULL;
18962306a36Sopenharmony_ci
19062306a36Sopenharmony_ci	if ((*vendor == 0x106b) && (*device == 3) && (offset >= 0x10)
19162306a36Sopenharmony_ci	    && (offset != 0x14) && (offset != 0x18) && (offset <= 0x24))
19262306a36Sopenharmony_ci		return NULL;
19362306a36Sopenharmony_ci
19462306a36Sopenharmony_ci	return macrisc_cfg_map_bus(bus, devfn, offset);
19562306a36Sopenharmony_ci}
19662306a36Sopenharmony_ci
19762306a36Sopenharmony_cistatic struct pci_ops chaos_pci_ops =
19862306a36Sopenharmony_ci{
19962306a36Sopenharmony_ci	.map_bus = chaos_map_bus,
20062306a36Sopenharmony_ci	.read = pci_generic_config_read,
20162306a36Sopenharmony_ci	.write = pci_generic_config_write,
20262306a36Sopenharmony_ci};
20362306a36Sopenharmony_ci
20462306a36Sopenharmony_cistatic void __init setup_chaos(struct pci_controller *hose,
20562306a36Sopenharmony_ci			       struct resource *addr)
20662306a36Sopenharmony_ci{
20762306a36Sopenharmony_ci	/* assume a `chaos' bridge */
20862306a36Sopenharmony_ci	hose->ops = &chaos_pci_ops;
20962306a36Sopenharmony_ci	hose->cfg_addr = ioremap(addr->start + 0x800000, 0x1000);
21062306a36Sopenharmony_ci	hose->cfg_data = ioremap(addr->start + 0xc00000, 0x1000);
21162306a36Sopenharmony_ci}
21262306a36Sopenharmony_ci#endif /* CONFIG_PPC32 */
21362306a36Sopenharmony_ci
21462306a36Sopenharmony_ci#ifdef CONFIG_PPC64
21562306a36Sopenharmony_ci/*
21662306a36Sopenharmony_ci * These versions of U3 HyperTransport config space access ops do not
21762306a36Sopenharmony_ci * implement self-view of the HT host yet
21862306a36Sopenharmony_ci */
21962306a36Sopenharmony_ci
22062306a36Sopenharmony_ci/*
22162306a36Sopenharmony_ci * This function deals with some "special cases" devices.
22262306a36Sopenharmony_ci *
22362306a36Sopenharmony_ci *  0 -> No special case
22462306a36Sopenharmony_ci *  1 -> Skip the device but act as if the access was successful
22562306a36Sopenharmony_ci *       (return 0xff's on reads, eventually, cache config space
22662306a36Sopenharmony_ci *       accesses in a later version)
22762306a36Sopenharmony_ci * -1 -> Hide the device (unsuccessful access)
22862306a36Sopenharmony_ci */
22962306a36Sopenharmony_cistatic int u3_ht_skip_device(struct pci_controller *hose,
23062306a36Sopenharmony_ci			     struct pci_bus *bus, unsigned int devfn)
23162306a36Sopenharmony_ci{
23262306a36Sopenharmony_ci	struct device_node *busdn, *dn;
23362306a36Sopenharmony_ci	int i;
23462306a36Sopenharmony_ci
23562306a36Sopenharmony_ci	/* We only allow config cycles to devices that are in OF device-tree
23662306a36Sopenharmony_ci	 * as we are apparently having some weird things going on with some
23762306a36Sopenharmony_ci	 * revs of K2 on recent G5s, except for the host bridge itself, which
23862306a36Sopenharmony_ci	 * is missing from the tree but we know we can probe.
23962306a36Sopenharmony_ci	 */
24062306a36Sopenharmony_ci	if (bus->self)
24162306a36Sopenharmony_ci		busdn = pci_device_to_OF_node(bus->self);
24262306a36Sopenharmony_ci	else if (devfn == 0)
24362306a36Sopenharmony_ci		return 0;
24462306a36Sopenharmony_ci	else
24562306a36Sopenharmony_ci		busdn = hose->dn;
24662306a36Sopenharmony_ci	for (dn = busdn->child; dn; dn = dn->sibling)
24762306a36Sopenharmony_ci		if (PCI_DN(dn) && PCI_DN(dn)->devfn == devfn)
24862306a36Sopenharmony_ci			break;
24962306a36Sopenharmony_ci	if (dn == NULL)
25062306a36Sopenharmony_ci		return -1;
25162306a36Sopenharmony_ci
25262306a36Sopenharmony_ci	/*
25362306a36Sopenharmony_ci	 * When a device in K2 is powered down, we die on config
25462306a36Sopenharmony_ci	 * cycle accesses. Fix that here.
25562306a36Sopenharmony_ci	 */
25662306a36Sopenharmony_ci	for (i=0; i<2; i++)
25762306a36Sopenharmony_ci		if (k2_skiplist[i] == dn)
25862306a36Sopenharmony_ci			return 1;
25962306a36Sopenharmony_ci
26062306a36Sopenharmony_ci	return 0;
26162306a36Sopenharmony_ci}
26262306a36Sopenharmony_ci
26362306a36Sopenharmony_ci#define U3_HT_CFA0(devfn, off)		\
26462306a36Sopenharmony_ci		((((unsigned int)devfn) << 8) | offset)
26562306a36Sopenharmony_ci#define U3_HT_CFA1(bus, devfn, off)	\
26662306a36Sopenharmony_ci		(U3_HT_CFA0(devfn, off) \
26762306a36Sopenharmony_ci		+ (((unsigned int)bus) << 16) \
26862306a36Sopenharmony_ci		+ 0x01000000UL)
26962306a36Sopenharmony_ci
27062306a36Sopenharmony_cistatic void __iomem *u3_ht_cfg_access(struct pci_controller *hose, u8 bus,
27162306a36Sopenharmony_ci				      u8 devfn, u8 offset, int *swap)
27262306a36Sopenharmony_ci{
27362306a36Sopenharmony_ci	*swap = 1;
27462306a36Sopenharmony_ci	if (bus == hose->first_busno) {
27562306a36Sopenharmony_ci		if (devfn != 0)
27662306a36Sopenharmony_ci			return hose->cfg_data + U3_HT_CFA0(devfn, offset);
27762306a36Sopenharmony_ci		*swap = 0;
27862306a36Sopenharmony_ci		return ((void __iomem *)hose->cfg_addr) + (offset << 2);
27962306a36Sopenharmony_ci	} else
28062306a36Sopenharmony_ci		return hose->cfg_data + U3_HT_CFA1(bus, devfn, offset);
28162306a36Sopenharmony_ci}
28262306a36Sopenharmony_ci
28362306a36Sopenharmony_cistatic int u3_ht_read_config(struct pci_bus *bus, unsigned int devfn,
28462306a36Sopenharmony_ci				    int offset, int len, u32 *val)
28562306a36Sopenharmony_ci{
28662306a36Sopenharmony_ci	struct pci_controller *hose;
28762306a36Sopenharmony_ci	void __iomem *addr;
28862306a36Sopenharmony_ci	int swap;
28962306a36Sopenharmony_ci
29062306a36Sopenharmony_ci	hose = pci_bus_to_host(bus);
29162306a36Sopenharmony_ci	if (hose == NULL)
29262306a36Sopenharmony_ci		return PCIBIOS_DEVICE_NOT_FOUND;
29362306a36Sopenharmony_ci	if (offset >= 0x100)
29462306a36Sopenharmony_ci		return  PCIBIOS_BAD_REGISTER_NUMBER;
29562306a36Sopenharmony_ci	addr = u3_ht_cfg_access(hose, bus->number, devfn, offset, &swap);
29662306a36Sopenharmony_ci	if (!addr)
29762306a36Sopenharmony_ci		return PCIBIOS_DEVICE_NOT_FOUND;
29862306a36Sopenharmony_ci
29962306a36Sopenharmony_ci	switch (u3_ht_skip_device(hose, bus, devfn)) {
30062306a36Sopenharmony_ci	case 0:
30162306a36Sopenharmony_ci		break;
30262306a36Sopenharmony_ci	case 1:
30362306a36Sopenharmony_ci		switch (len) {
30462306a36Sopenharmony_ci		case 1:
30562306a36Sopenharmony_ci			*val = 0xff; break;
30662306a36Sopenharmony_ci		case 2:
30762306a36Sopenharmony_ci			*val = 0xffff; break;
30862306a36Sopenharmony_ci		default:
30962306a36Sopenharmony_ci			*val = 0xfffffffful; break;
31062306a36Sopenharmony_ci		}
31162306a36Sopenharmony_ci		return PCIBIOS_SUCCESSFUL;
31262306a36Sopenharmony_ci	default:
31362306a36Sopenharmony_ci		return PCIBIOS_DEVICE_NOT_FOUND;
31462306a36Sopenharmony_ci	}
31562306a36Sopenharmony_ci
31662306a36Sopenharmony_ci	/*
31762306a36Sopenharmony_ci	 * Note: the caller has already checked that offset is
31862306a36Sopenharmony_ci	 * suitably aligned and that len is 1, 2 or 4.
31962306a36Sopenharmony_ci	 */
32062306a36Sopenharmony_ci	switch (len) {
32162306a36Sopenharmony_ci	case 1:
32262306a36Sopenharmony_ci		*val = in_8(addr);
32362306a36Sopenharmony_ci		break;
32462306a36Sopenharmony_ci	case 2:
32562306a36Sopenharmony_ci		*val = swap ? in_le16(addr) : in_be16(addr);
32662306a36Sopenharmony_ci		break;
32762306a36Sopenharmony_ci	default:
32862306a36Sopenharmony_ci		*val = swap ? in_le32(addr) : in_be32(addr);
32962306a36Sopenharmony_ci		break;
33062306a36Sopenharmony_ci	}
33162306a36Sopenharmony_ci	return PCIBIOS_SUCCESSFUL;
33262306a36Sopenharmony_ci}
33362306a36Sopenharmony_ci
33462306a36Sopenharmony_cistatic int u3_ht_write_config(struct pci_bus *bus, unsigned int devfn,
33562306a36Sopenharmony_ci				     int offset, int len, u32 val)
33662306a36Sopenharmony_ci{
33762306a36Sopenharmony_ci	struct pci_controller *hose;
33862306a36Sopenharmony_ci	void __iomem *addr;
33962306a36Sopenharmony_ci	int swap;
34062306a36Sopenharmony_ci
34162306a36Sopenharmony_ci	hose = pci_bus_to_host(bus);
34262306a36Sopenharmony_ci	if (hose == NULL)
34362306a36Sopenharmony_ci		return PCIBIOS_DEVICE_NOT_FOUND;
34462306a36Sopenharmony_ci	if (offset >= 0x100)
34562306a36Sopenharmony_ci		return  PCIBIOS_BAD_REGISTER_NUMBER;
34662306a36Sopenharmony_ci	addr = u3_ht_cfg_access(hose, bus->number, devfn, offset, &swap);
34762306a36Sopenharmony_ci	if (!addr)
34862306a36Sopenharmony_ci		return PCIBIOS_DEVICE_NOT_FOUND;
34962306a36Sopenharmony_ci
35062306a36Sopenharmony_ci	switch (u3_ht_skip_device(hose, bus, devfn)) {
35162306a36Sopenharmony_ci	case 0:
35262306a36Sopenharmony_ci		break;
35362306a36Sopenharmony_ci	case 1:
35462306a36Sopenharmony_ci		return PCIBIOS_SUCCESSFUL;
35562306a36Sopenharmony_ci	default:
35662306a36Sopenharmony_ci		return PCIBIOS_DEVICE_NOT_FOUND;
35762306a36Sopenharmony_ci	}
35862306a36Sopenharmony_ci
35962306a36Sopenharmony_ci	/*
36062306a36Sopenharmony_ci	 * Note: the caller has already checked that offset is
36162306a36Sopenharmony_ci	 * suitably aligned and that len is 1, 2 or 4.
36262306a36Sopenharmony_ci	 */
36362306a36Sopenharmony_ci	switch (len) {
36462306a36Sopenharmony_ci	case 1:
36562306a36Sopenharmony_ci		out_8(addr, val);
36662306a36Sopenharmony_ci		break;
36762306a36Sopenharmony_ci	case 2:
36862306a36Sopenharmony_ci		swap ? out_le16(addr, val) : out_be16(addr, val);
36962306a36Sopenharmony_ci		break;
37062306a36Sopenharmony_ci	default:
37162306a36Sopenharmony_ci		swap ? out_le32(addr, val) : out_be32(addr, val);
37262306a36Sopenharmony_ci		break;
37362306a36Sopenharmony_ci	}
37462306a36Sopenharmony_ci	return PCIBIOS_SUCCESSFUL;
37562306a36Sopenharmony_ci}
37662306a36Sopenharmony_ci
37762306a36Sopenharmony_cistatic struct pci_ops u3_ht_pci_ops =
37862306a36Sopenharmony_ci{
37962306a36Sopenharmony_ci	.read = u3_ht_read_config,
38062306a36Sopenharmony_ci	.write = u3_ht_write_config,
38162306a36Sopenharmony_ci};
38262306a36Sopenharmony_ci
38362306a36Sopenharmony_ci#define U4_PCIE_CFA0(devfn, off)	\
38462306a36Sopenharmony_ci	((1 << ((unsigned int)PCI_SLOT(dev_fn)))	\
38562306a36Sopenharmony_ci	 | (((unsigned int)PCI_FUNC(dev_fn)) << 8)	\
38662306a36Sopenharmony_ci	 | ((((unsigned int)(off)) >> 8) << 28) \
38762306a36Sopenharmony_ci	 | (((unsigned int)(off)) & 0xfcU))
38862306a36Sopenharmony_ci
38962306a36Sopenharmony_ci#define U4_PCIE_CFA1(bus, devfn, off)	\
39062306a36Sopenharmony_ci	((((unsigned int)(bus)) << 16) \
39162306a36Sopenharmony_ci	 |(((unsigned int)(devfn)) << 8)	\
39262306a36Sopenharmony_ci	 | ((((unsigned int)(off)) >> 8) << 28) \
39362306a36Sopenharmony_ci	 |(((unsigned int)(off)) & 0xfcU)	\
39462306a36Sopenharmony_ci	 |1UL)
39562306a36Sopenharmony_ci
39662306a36Sopenharmony_cistatic void __iomem *u4_pcie_cfg_map_bus(struct pci_bus *bus,
39762306a36Sopenharmony_ci					 unsigned int dev_fn,
39862306a36Sopenharmony_ci					 int offset)
39962306a36Sopenharmony_ci{
40062306a36Sopenharmony_ci	struct pci_controller *hose;
40162306a36Sopenharmony_ci	unsigned int caddr;
40262306a36Sopenharmony_ci
40362306a36Sopenharmony_ci	if (offset >= 0x1000)
40462306a36Sopenharmony_ci		return NULL;
40562306a36Sopenharmony_ci
40662306a36Sopenharmony_ci	hose = pci_bus_to_host(bus);
40762306a36Sopenharmony_ci	if (!hose)
40862306a36Sopenharmony_ci		return NULL;
40962306a36Sopenharmony_ci
41062306a36Sopenharmony_ci	if (bus->number == hose->first_busno) {
41162306a36Sopenharmony_ci		caddr = U4_PCIE_CFA0(dev_fn, offset);
41262306a36Sopenharmony_ci	} else
41362306a36Sopenharmony_ci		caddr = U4_PCIE_CFA1(bus->number, dev_fn, offset);
41462306a36Sopenharmony_ci
41562306a36Sopenharmony_ci	/* Uninorth will return garbage if we don't read back the value ! */
41662306a36Sopenharmony_ci	do {
41762306a36Sopenharmony_ci		out_le32(hose->cfg_addr, caddr);
41862306a36Sopenharmony_ci	} while (in_le32(hose->cfg_addr) != caddr);
41962306a36Sopenharmony_ci
42062306a36Sopenharmony_ci	offset &= 0x03;
42162306a36Sopenharmony_ci	return hose->cfg_data + offset;
42262306a36Sopenharmony_ci}
42362306a36Sopenharmony_ci
42462306a36Sopenharmony_cistatic struct pci_ops u4_pcie_pci_ops =
42562306a36Sopenharmony_ci{
42662306a36Sopenharmony_ci	.map_bus = u4_pcie_cfg_map_bus,
42762306a36Sopenharmony_ci	.read = pci_generic_config_read,
42862306a36Sopenharmony_ci	.write = pci_generic_config_write,
42962306a36Sopenharmony_ci};
43062306a36Sopenharmony_ci
43162306a36Sopenharmony_cistatic void pmac_pci_fixup_u4_of_node(struct pci_dev *dev)
43262306a36Sopenharmony_ci{
43362306a36Sopenharmony_ci	/* Apple's device-tree "hides" the root complex virtual P2P bridge
43462306a36Sopenharmony_ci	 * on U4. However, Linux sees it, causing the PCI <-> OF matching
43562306a36Sopenharmony_ci	 * code to fail to properly match devices below it. This works around
43662306a36Sopenharmony_ci	 * it by setting the node of the bridge to point to the PHB node,
43762306a36Sopenharmony_ci	 * which is not entirely correct but fixes the matching code and
43862306a36Sopenharmony_ci	 * doesn't break anything else. It's also the simplest possible fix.
43962306a36Sopenharmony_ci	 */
44062306a36Sopenharmony_ci	if (dev->dev.of_node == NULL)
44162306a36Sopenharmony_ci		dev->dev.of_node = pcibios_get_phb_of_node(dev->bus);
44262306a36Sopenharmony_ci}
44362306a36Sopenharmony_ciDECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_APPLE, 0x5b, pmac_pci_fixup_u4_of_node);
44462306a36Sopenharmony_ci
44562306a36Sopenharmony_ci#endif /* CONFIG_PPC64 */
44662306a36Sopenharmony_ci
44762306a36Sopenharmony_ci#ifdef CONFIG_PPC32
44862306a36Sopenharmony_ci/*
44962306a36Sopenharmony_ci * For a bandit bridge, turn on cache coherency if necessary.
45062306a36Sopenharmony_ci * N.B. we could clean this up using the hose ops directly.
45162306a36Sopenharmony_ci */
45262306a36Sopenharmony_cistatic void __init init_bandit(struct pci_controller *bp)
45362306a36Sopenharmony_ci{
45462306a36Sopenharmony_ci	unsigned int vendev, magic;
45562306a36Sopenharmony_ci	int rev;
45662306a36Sopenharmony_ci
45762306a36Sopenharmony_ci	/* read the word at offset 0 in config space for device 11 */
45862306a36Sopenharmony_ci	out_le32(bp->cfg_addr, (1UL << BANDIT_DEVNUM) + PCI_VENDOR_ID);
45962306a36Sopenharmony_ci	udelay(2);
46062306a36Sopenharmony_ci	vendev = in_le32(bp->cfg_data);
46162306a36Sopenharmony_ci	if (vendev == (PCI_DEVICE_ID_APPLE_BANDIT << 16) +
46262306a36Sopenharmony_ci			PCI_VENDOR_ID_APPLE) {
46362306a36Sopenharmony_ci		/* read the revision id */
46462306a36Sopenharmony_ci		out_le32(bp->cfg_addr,
46562306a36Sopenharmony_ci			 (1UL << BANDIT_DEVNUM) + PCI_REVISION_ID);
46662306a36Sopenharmony_ci		udelay(2);
46762306a36Sopenharmony_ci		rev = in_8(bp->cfg_data);
46862306a36Sopenharmony_ci		if (rev != BANDIT_REVID)
46962306a36Sopenharmony_ci			printk(KERN_WARNING
47062306a36Sopenharmony_ci			       "Unknown revision %d for bandit\n", rev);
47162306a36Sopenharmony_ci	} else if (vendev != (BANDIT_DEVID_2 << 16) + PCI_VENDOR_ID_APPLE) {
47262306a36Sopenharmony_ci		printk(KERN_WARNING "bandit isn't? (%x)\n", vendev);
47362306a36Sopenharmony_ci		return;
47462306a36Sopenharmony_ci	}
47562306a36Sopenharmony_ci
47662306a36Sopenharmony_ci	/* read the word at offset 0x50 */
47762306a36Sopenharmony_ci	out_le32(bp->cfg_addr, (1UL << BANDIT_DEVNUM) + BANDIT_MAGIC);
47862306a36Sopenharmony_ci	udelay(2);
47962306a36Sopenharmony_ci	magic = in_le32(bp->cfg_data);
48062306a36Sopenharmony_ci	if ((magic & BANDIT_COHERENT) != 0)
48162306a36Sopenharmony_ci		return;
48262306a36Sopenharmony_ci	magic |= BANDIT_COHERENT;
48362306a36Sopenharmony_ci	udelay(2);
48462306a36Sopenharmony_ci	out_le32(bp->cfg_data, magic);
48562306a36Sopenharmony_ci	printk(KERN_INFO "Cache coherency enabled for bandit/PSX\n");
48662306a36Sopenharmony_ci}
48762306a36Sopenharmony_ci
48862306a36Sopenharmony_ci/*
48962306a36Sopenharmony_ci * Tweak the PCI-PCI bridge chip on the blue & white G3s.
49062306a36Sopenharmony_ci */
49162306a36Sopenharmony_cistatic void __init init_p2pbridge(void)
49262306a36Sopenharmony_ci{
49362306a36Sopenharmony_ci	struct device_node *p2pbridge;
49462306a36Sopenharmony_ci	struct pci_controller* hose;
49562306a36Sopenharmony_ci	u8 bus, devfn;
49662306a36Sopenharmony_ci	u16 val;
49762306a36Sopenharmony_ci
49862306a36Sopenharmony_ci	/* XXX it would be better here to identify the specific
49962306a36Sopenharmony_ci	   PCI-PCI bridge chip we have. */
50062306a36Sopenharmony_ci	p2pbridge = of_find_node_by_name(NULL, "pci-bridge");
50162306a36Sopenharmony_ci	if (p2pbridge == NULL || !of_node_name_eq(p2pbridge->parent, "pci"))
50262306a36Sopenharmony_ci		goto done;
50362306a36Sopenharmony_ci	if (pci_device_from_OF_node(p2pbridge, &bus, &devfn) < 0) {
50462306a36Sopenharmony_ci		DBG("Can't find PCI infos for PCI<->PCI bridge\n");
50562306a36Sopenharmony_ci		goto done;
50662306a36Sopenharmony_ci	}
50762306a36Sopenharmony_ci	/* Warning: At this point, we have not yet renumbered all busses.
50862306a36Sopenharmony_ci	 * So we must use OF walking to find out hose
50962306a36Sopenharmony_ci	 */
51062306a36Sopenharmony_ci	hose = pci_find_hose_for_OF_device(p2pbridge);
51162306a36Sopenharmony_ci	if (!hose) {
51262306a36Sopenharmony_ci		DBG("Can't find hose for PCI<->PCI bridge\n");
51362306a36Sopenharmony_ci		goto done;
51462306a36Sopenharmony_ci	}
51562306a36Sopenharmony_ci	if (early_read_config_word(hose, bus, devfn,
51662306a36Sopenharmony_ci				   PCI_BRIDGE_CONTROL, &val) < 0) {
51762306a36Sopenharmony_ci		printk(KERN_ERR "init_p2pbridge: couldn't read bridge"
51862306a36Sopenharmony_ci		       " control\n");
51962306a36Sopenharmony_ci		goto done;
52062306a36Sopenharmony_ci	}
52162306a36Sopenharmony_ci	val &= ~PCI_BRIDGE_CTL_MASTER_ABORT;
52262306a36Sopenharmony_ci	early_write_config_word(hose, bus, devfn, PCI_BRIDGE_CONTROL, val);
52362306a36Sopenharmony_cidone:
52462306a36Sopenharmony_ci	of_node_put(p2pbridge);
52562306a36Sopenharmony_ci}
52662306a36Sopenharmony_ci
52762306a36Sopenharmony_cistatic void __init init_second_ohare(void)
52862306a36Sopenharmony_ci{
52962306a36Sopenharmony_ci	struct device_node *np = of_find_node_by_name(NULL, "pci106b,7");
53062306a36Sopenharmony_ci	unsigned char bus, devfn;
53162306a36Sopenharmony_ci	unsigned short cmd;
53262306a36Sopenharmony_ci
53362306a36Sopenharmony_ci	if (np == NULL)
53462306a36Sopenharmony_ci		return;
53562306a36Sopenharmony_ci
53662306a36Sopenharmony_ci	/* This must run before we initialize the PICs since the second
53762306a36Sopenharmony_ci	 * ohare hosts a PIC that will be accessed there.
53862306a36Sopenharmony_ci	 */
53962306a36Sopenharmony_ci	if (pci_device_from_OF_node(np, &bus, &devfn) == 0) {
54062306a36Sopenharmony_ci		struct pci_controller* hose =
54162306a36Sopenharmony_ci			pci_find_hose_for_OF_device(np);
54262306a36Sopenharmony_ci		if (!hose) {
54362306a36Sopenharmony_ci			printk(KERN_ERR "Can't find PCI hose for OHare2 !\n");
54462306a36Sopenharmony_ci			of_node_put(np);
54562306a36Sopenharmony_ci			return;
54662306a36Sopenharmony_ci		}
54762306a36Sopenharmony_ci		early_read_config_word(hose, bus, devfn, PCI_COMMAND, &cmd);
54862306a36Sopenharmony_ci		cmd |= PCI_COMMAND_MEMORY | PCI_COMMAND_MASTER;
54962306a36Sopenharmony_ci		cmd &= ~PCI_COMMAND_IO;
55062306a36Sopenharmony_ci		early_write_config_word(hose, bus, devfn, PCI_COMMAND, cmd);
55162306a36Sopenharmony_ci	}
55262306a36Sopenharmony_ci	has_second_ohare = 1;
55362306a36Sopenharmony_ci	of_node_put(np);
55462306a36Sopenharmony_ci}
55562306a36Sopenharmony_ci
55662306a36Sopenharmony_ci/*
55762306a36Sopenharmony_ci * Some Apple desktop machines have a NEC PD720100A USB2 controller
55862306a36Sopenharmony_ci * on the motherboard. Open Firmware, on these, will disable the
55962306a36Sopenharmony_ci * EHCI part of it so it behaves like a pair of OHCI's. This fixup
56062306a36Sopenharmony_ci * code re-enables it ;)
56162306a36Sopenharmony_ci */
56262306a36Sopenharmony_cistatic void __init fixup_nec_usb2(void)
56362306a36Sopenharmony_ci{
56462306a36Sopenharmony_ci	struct device_node *nec;
56562306a36Sopenharmony_ci
56662306a36Sopenharmony_ci	for_each_node_by_name(nec, "usb") {
56762306a36Sopenharmony_ci		struct pci_controller *hose;
56862306a36Sopenharmony_ci		u32 data;
56962306a36Sopenharmony_ci		const u32 *prop;
57062306a36Sopenharmony_ci		u8 bus, devfn;
57162306a36Sopenharmony_ci
57262306a36Sopenharmony_ci		prop = of_get_property(nec, "vendor-id", NULL);
57362306a36Sopenharmony_ci		if (prop == NULL)
57462306a36Sopenharmony_ci			continue;
57562306a36Sopenharmony_ci		if (0x1033 != *prop)
57662306a36Sopenharmony_ci			continue;
57762306a36Sopenharmony_ci		prop = of_get_property(nec, "device-id", NULL);
57862306a36Sopenharmony_ci		if (prop == NULL)
57962306a36Sopenharmony_ci			continue;
58062306a36Sopenharmony_ci		if (0x0035 != *prop)
58162306a36Sopenharmony_ci			continue;
58262306a36Sopenharmony_ci		prop = of_get_property(nec, "reg", NULL);
58362306a36Sopenharmony_ci		if (prop == NULL)
58462306a36Sopenharmony_ci			continue;
58562306a36Sopenharmony_ci		devfn = (prop[0] >> 8) & 0xff;
58662306a36Sopenharmony_ci		bus = (prop[0] >> 16) & 0xff;
58762306a36Sopenharmony_ci		if (PCI_FUNC(devfn) != 0)
58862306a36Sopenharmony_ci			continue;
58962306a36Sopenharmony_ci		hose = pci_find_hose_for_OF_device(nec);
59062306a36Sopenharmony_ci		if (!hose)
59162306a36Sopenharmony_ci			continue;
59262306a36Sopenharmony_ci		early_read_config_dword(hose, bus, devfn, 0xe4, &data);
59362306a36Sopenharmony_ci		if (data & 1UL) {
59462306a36Sopenharmony_ci			printk("Found NEC PD720100A USB2 chip with disabled"
59562306a36Sopenharmony_ci			       " EHCI, fixing up...\n");
59662306a36Sopenharmony_ci			data &= ~1UL;
59762306a36Sopenharmony_ci			early_write_config_dword(hose, bus, devfn, 0xe4, data);
59862306a36Sopenharmony_ci		}
59962306a36Sopenharmony_ci	}
60062306a36Sopenharmony_ci}
60162306a36Sopenharmony_ci
60262306a36Sopenharmony_cistatic void __init setup_bandit(struct pci_controller *hose,
60362306a36Sopenharmony_ci				struct resource *addr)
60462306a36Sopenharmony_ci{
60562306a36Sopenharmony_ci	hose->ops = &macrisc_pci_ops;
60662306a36Sopenharmony_ci	hose->cfg_addr = ioremap(addr->start + 0x800000, 0x1000);
60762306a36Sopenharmony_ci	hose->cfg_data = ioremap(addr->start + 0xc00000, 0x1000);
60862306a36Sopenharmony_ci	init_bandit(hose);
60962306a36Sopenharmony_ci}
61062306a36Sopenharmony_ci
61162306a36Sopenharmony_cistatic int __init setup_uninorth(struct pci_controller *hose,
61262306a36Sopenharmony_ci				 struct resource *addr)
61362306a36Sopenharmony_ci{
61462306a36Sopenharmony_ci	pci_add_flags(PCI_REASSIGN_ALL_BUS);
61562306a36Sopenharmony_ci	has_uninorth = 1;
61662306a36Sopenharmony_ci	hose->ops = &macrisc_pci_ops;
61762306a36Sopenharmony_ci	hose->cfg_addr = ioremap(addr->start + 0x800000, 0x1000);
61862306a36Sopenharmony_ci	hose->cfg_data = ioremap(addr->start + 0xc00000, 0x1000);
61962306a36Sopenharmony_ci	/* We "know" that the bridge at f2000000 has the PCI slots. */
62062306a36Sopenharmony_ci	return addr->start == 0xf2000000;
62162306a36Sopenharmony_ci}
62262306a36Sopenharmony_ci#endif /* CONFIG_PPC32 */
62362306a36Sopenharmony_ci
62462306a36Sopenharmony_ci#ifdef CONFIG_PPC64
62562306a36Sopenharmony_cistatic void __init setup_u3_agp(struct pci_controller* hose)
62662306a36Sopenharmony_ci{
62762306a36Sopenharmony_ci	/* On G5, we move AGP up to high bus number so we don't need
62862306a36Sopenharmony_ci	 * to reassign bus numbers for HT. If we ever have P2P bridges
62962306a36Sopenharmony_ci	 * on AGP, we'll have to move pci_assign_all_busses to the
63062306a36Sopenharmony_ci	 * pci_controller structure so we enable it for AGP and not for
63162306a36Sopenharmony_ci	 * HT childs.
63262306a36Sopenharmony_ci	 * We hard code the address because of the different size of
63362306a36Sopenharmony_ci	 * the reg address cell, we shall fix that by killing struct
63462306a36Sopenharmony_ci	 * reg_property and using some accessor functions instead
63562306a36Sopenharmony_ci	 */
63662306a36Sopenharmony_ci	hose->first_busno = 0xf0;
63762306a36Sopenharmony_ci	hose->last_busno = 0xff;
63862306a36Sopenharmony_ci	has_uninorth = 1;
63962306a36Sopenharmony_ci	hose->ops = &macrisc_pci_ops;
64062306a36Sopenharmony_ci	hose->cfg_addr = ioremap(0xf0000000 + 0x800000, 0x1000);
64162306a36Sopenharmony_ci	hose->cfg_data = ioremap(0xf0000000 + 0xc00000, 0x1000);
64262306a36Sopenharmony_ci	u3_agp = hose;
64362306a36Sopenharmony_ci}
64462306a36Sopenharmony_ci
64562306a36Sopenharmony_cistatic void __init setup_u4_pcie(struct pci_controller* hose)
64662306a36Sopenharmony_ci{
64762306a36Sopenharmony_ci	/* We currently only implement the "non-atomic" config space, to
64862306a36Sopenharmony_ci	 * be optimised later.
64962306a36Sopenharmony_ci	 */
65062306a36Sopenharmony_ci	hose->ops = &u4_pcie_pci_ops;
65162306a36Sopenharmony_ci	hose->cfg_addr = ioremap(0xf0000000 + 0x800000, 0x1000);
65262306a36Sopenharmony_ci	hose->cfg_data = ioremap(0xf0000000 + 0xc00000, 0x1000);
65362306a36Sopenharmony_ci
65462306a36Sopenharmony_ci	/* The bus contains a bridge from root -> device, we need to
65562306a36Sopenharmony_ci	 * make it visible on bus 0 so that we pick the right type
65662306a36Sopenharmony_ci	 * of config cycles. If we didn't, we would have to force all
65762306a36Sopenharmony_ci	 * config cycles to be type 1. So we override the "bus-range"
65862306a36Sopenharmony_ci	 * property here
65962306a36Sopenharmony_ci	 */
66062306a36Sopenharmony_ci	hose->first_busno = 0x00;
66162306a36Sopenharmony_ci	hose->last_busno = 0xff;
66262306a36Sopenharmony_ci}
66362306a36Sopenharmony_ci
66462306a36Sopenharmony_cistatic void __init parse_region_decode(struct pci_controller *hose,
66562306a36Sopenharmony_ci				       u32 decode)
66662306a36Sopenharmony_ci{
66762306a36Sopenharmony_ci	unsigned long base, end, next = -1;
66862306a36Sopenharmony_ci	int i, cur = -1;
66962306a36Sopenharmony_ci
67062306a36Sopenharmony_ci	/* Iterate through all bits. We ignore the last bit as this region is
67162306a36Sopenharmony_ci	 * reserved for the ROM among other niceties
67262306a36Sopenharmony_ci	 */
67362306a36Sopenharmony_ci	for (i = 0; i < 31; i++) {
67462306a36Sopenharmony_ci		if ((decode & (0x80000000 >> i)) == 0)
67562306a36Sopenharmony_ci			continue;
67662306a36Sopenharmony_ci		if (i < 16) {
67762306a36Sopenharmony_ci			base = 0xf0000000 | (((u32)i) << 24);
67862306a36Sopenharmony_ci			end = base + 0x00ffffff;
67962306a36Sopenharmony_ci		} else {
68062306a36Sopenharmony_ci			base = ((u32)i-16) << 28;
68162306a36Sopenharmony_ci			end = base + 0x0fffffff;
68262306a36Sopenharmony_ci		}
68362306a36Sopenharmony_ci		if (base != next) {
68462306a36Sopenharmony_ci			if (++cur >= 3) {
68562306a36Sopenharmony_ci				printk(KERN_WARNING "PCI: Too many ranges !\n");
68662306a36Sopenharmony_ci				break;
68762306a36Sopenharmony_ci			}
68862306a36Sopenharmony_ci			hose->mem_resources[cur].flags = IORESOURCE_MEM;
68962306a36Sopenharmony_ci			hose->mem_resources[cur].name = hose->dn->full_name;
69062306a36Sopenharmony_ci			hose->mem_resources[cur].start = base;
69162306a36Sopenharmony_ci			hose->mem_resources[cur].end = end;
69262306a36Sopenharmony_ci			hose->mem_offset[cur] = 0;
69362306a36Sopenharmony_ci			DBG("  %d: 0x%08lx-0x%08lx\n", cur, base, end);
69462306a36Sopenharmony_ci		} else {
69562306a36Sopenharmony_ci			DBG("   :           -0x%08lx\n", end);
69662306a36Sopenharmony_ci			hose->mem_resources[cur].end = end;
69762306a36Sopenharmony_ci		}
69862306a36Sopenharmony_ci		next = end + 1;
69962306a36Sopenharmony_ci	}
70062306a36Sopenharmony_ci}
70162306a36Sopenharmony_ci
70262306a36Sopenharmony_cistatic void __init setup_u3_ht(struct pci_controller* hose)
70362306a36Sopenharmony_ci{
70462306a36Sopenharmony_ci	struct device_node *np = hose->dn;
70562306a36Sopenharmony_ci	struct resource cfg_res, self_res;
70662306a36Sopenharmony_ci	u32 decode;
70762306a36Sopenharmony_ci
70862306a36Sopenharmony_ci	hose->ops = &u3_ht_pci_ops;
70962306a36Sopenharmony_ci
71062306a36Sopenharmony_ci	/* Get base addresses from OF tree
71162306a36Sopenharmony_ci	 */
71262306a36Sopenharmony_ci	if (of_address_to_resource(np, 0, &cfg_res) ||
71362306a36Sopenharmony_ci	    of_address_to_resource(np, 1, &self_res)) {
71462306a36Sopenharmony_ci		printk(KERN_ERR "PCI: Failed to get U3/U4 HT resources !\n");
71562306a36Sopenharmony_ci		return;
71662306a36Sopenharmony_ci	}
71762306a36Sopenharmony_ci
71862306a36Sopenharmony_ci	/* Map external cfg space access into cfg_data and self registers
71962306a36Sopenharmony_ci	 * into cfg_addr
72062306a36Sopenharmony_ci	 */
72162306a36Sopenharmony_ci	hose->cfg_data = ioremap(cfg_res.start, 0x02000000);
72262306a36Sopenharmony_ci	hose->cfg_addr = ioremap(self_res.start, resource_size(&self_res));
72362306a36Sopenharmony_ci
72462306a36Sopenharmony_ci	/*
72562306a36Sopenharmony_ci	 * /ht node doesn't expose a "ranges" property, we read the register
72662306a36Sopenharmony_ci	 * that controls the decoding logic and use that for memory regions.
72762306a36Sopenharmony_ci	 * The IO region is hard coded since it is fixed in HW as well.
72862306a36Sopenharmony_ci	 */
72962306a36Sopenharmony_ci	hose->io_base_phys = 0xf4000000;
73062306a36Sopenharmony_ci	hose->pci_io_size = 0x00400000;
73162306a36Sopenharmony_ci	hose->io_resource.name = np->full_name;
73262306a36Sopenharmony_ci	hose->io_resource.start = 0;
73362306a36Sopenharmony_ci	hose->io_resource.end = 0x003fffff;
73462306a36Sopenharmony_ci	hose->io_resource.flags = IORESOURCE_IO;
73562306a36Sopenharmony_ci	hose->first_busno = 0;
73662306a36Sopenharmony_ci	hose->last_busno = 0xef;
73762306a36Sopenharmony_ci
73862306a36Sopenharmony_ci	/* Note: fix offset when cfg_addr becomes a void * */
73962306a36Sopenharmony_ci	decode = in_be32(hose->cfg_addr + 0x80);
74062306a36Sopenharmony_ci
74162306a36Sopenharmony_ci	DBG("PCI: Apple HT bridge decode register: 0x%08x\n", decode);
74262306a36Sopenharmony_ci
74362306a36Sopenharmony_ci	/* NOTE: The decode register setup is a bit weird... region
74462306a36Sopenharmony_ci	 * 0xf8000000 for example is marked as enabled in there while it's
74562306a36Sopenharmony_ci	 & actually the memory controller registers.
74662306a36Sopenharmony_ci	 * That means that we are incorrectly attributing it to HT.
74762306a36Sopenharmony_ci	 *
74862306a36Sopenharmony_ci	 * In a similar vein, region 0xf4000000 is actually the HT IO space but
74962306a36Sopenharmony_ci	 * also marked as enabled in here and 0xf9000000 is used by some other
75062306a36Sopenharmony_ci	 * internal bits of the northbridge.
75162306a36Sopenharmony_ci	 *
75262306a36Sopenharmony_ci	 * Unfortunately, we can't just mask out those bit as we would end
75362306a36Sopenharmony_ci	 * up with more regions than we can cope (linux can only cope with
75462306a36Sopenharmony_ci	 * 3 memory regions for a PHB at this stage).
75562306a36Sopenharmony_ci	 *
75662306a36Sopenharmony_ci	 * So for now, we just do a little hack. We happen to -know- that
75762306a36Sopenharmony_ci	 * Apple firmware doesn't assign things below 0xfa000000 for that
75862306a36Sopenharmony_ci	 * bridge anyway so we mask out all bits we don't want.
75962306a36Sopenharmony_ci	 */
76062306a36Sopenharmony_ci	decode &= 0x003fffff;
76162306a36Sopenharmony_ci
76262306a36Sopenharmony_ci	/* Now parse the resulting bits and build resources */
76362306a36Sopenharmony_ci	parse_region_decode(hose, decode);
76462306a36Sopenharmony_ci}
76562306a36Sopenharmony_ci#endif /* CONFIG_PPC64 */
76662306a36Sopenharmony_ci
76762306a36Sopenharmony_ci/*
76862306a36Sopenharmony_ci * We assume that if we have a G3 powermac, we have one bridge called
76962306a36Sopenharmony_ci * "pci" (a MPC106) and no bandit or chaos bridges, and contrariwise,
77062306a36Sopenharmony_ci * if we have one or more bandit or chaos bridges, we don't have a MPC106.
77162306a36Sopenharmony_ci */
77262306a36Sopenharmony_cistatic int __init pmac_add_bridge(struct device_node *dev)
77362306a36Sopenharmony_ci{
77462306a36Sopenharmony_ci	int len;
77562306a36Sopenharmony_ci	struct pci_controller *hose;
77662306a36Sopenharmony_ci	struct resource rsrc;
77762306a36Sopenharmony_ci	char *disp_name;
77862306a36Sopenharmony_ci	const int *bus_range;
77962306a36Sopenharmony_ci	int primary = 1;
78062306a36Sopenharmony_ci
78162306a36Sopenharmony_ci	DBG("Adding PCI host bridge %pOF\n", dev);
78262306a36Sopenharmony_ci
78362306a36Sopenharmony_ci	/* Fetch host bridge registers address */
78462306a36Sopenharmony_ci	of_address_to_resource(dev, 0, &rsrc);
78562306a36Sopenharmony_ci
78662306a36Sopenharmony_ci	/* Get bus range if any */
78762306a36Sopenharmony_ci	bus_range = of_get_property(dev, "bus-range", &len);
78862306a36Sopenharmony_ci	if (bus_range == NULL || len < 2 * sizeof(int)) {
78962306a36Sopenharmony_ci		printk(KERN_WARNING "Can't get bus-range for %pOF, assume"
79062306a36Sopenharmony_ci		       " bus 0\n", dev);
79162306a36Sopenharmony_ci	}
79262306a36Sopenharmony_ci
79362306a36Sopenharmony_ci	hose = pcibios_alloc_controller(dev);
79462306a36Sopenharmony_ci	if (!hose)
79562306a36Sopenharmony_ci		return -ENOMEM;
79662306a36Sopenharmony_ci	hose->first_busno = bus_range ? bus_range[0] : 0;
79762306a36Sopenharmony_ci	hose->last_busno = bus_range ? bus_range[1] : 0xff;
79862306a36Sopenharmony_ci	hose->controller_ops = pmac_pci_controller_ops;
79962306a36Sopenharmony_ci
80062306a36Sopenharmony_ci	disp_name = NULL;
80162306a36Sopenharmony_ci
80262306a36Sopenharmony_ci	/* 64 bits only bridges */
80362306a36Sopenharmony_ci#ifdef CONFIG_PPC64
80462306a36Sopenharmony_ci	if (of_device_is_compatible(dev, "u3-agp")) {
80562306a36Sopenharmony_ci		setup_u3_agp(hose);
80662306a36Sopenharmony_ci		disp_name = "U3-AGP";
80762306a36Sopenharmony_ci		primary = 0;
80862306a36Sopenharmony_ci	} else if (of_device_is_compatible(dev, "u3-ht")) {
80962306a36Sopenharmony_ci		setup_u3_ht(hose);
81062306a36Sopenharmony_ci		disp_name = "U3-HT";
81162306a36Sopenharmony_ci		primary = 1;
81262306a36Sopenharmony_ci	} else if (of_device_is_compatible(dev, "u4-pcie")) {
81362306a36Sopenharmony_ci		setup_u4_pcie(hose);
81462306a36Sopenharmony_ci		disp_name = "U4-PCIE";
81562306a36Sopenharmony_ci		primary = 0;
81662306a36Sopenharmony_ci	}
81762306a36Sopenharmony_ci	printk(KERN_INFO "Found %s PCI host bridge.  Firmware bus number:"
81862306a36Sopenharmony_ci	       " %d->%d\n", disp_name, hose->first_busno, hose->last_busno);
81962306a36Sopenharmony_ci#endif /* CONFIG_PPC64 */
82062306a36Sopenharmony_ci
82162306a36Sopenharmony_ci	/* 32 bits only bridges */
82262306a36Sopenharmony_ci#ifdef CONFIG_PPC32
82362306a36Sopenharmony_ci	if (of_device_is_compatible(dev, "uni-north")) {
82462306a36Sopenharmony_ci		primary = setup_uninorth(hose, &rsrc);
82562306a36Sopenharmony_ci		disp_name = "UniNorth";
82662306a36Sopenharmony_ci	} else if (of_node_name_eq(dev, "pci")) {
82762306a36Sopenharmony_ci		/* XXX assume this is a mpc106 (grackle) */
82862306a36Sopenharmony_ci		setup_grackle(hose);
82962306a36Sopenharmony_ci		disp_name = "Grackle (MPC106)";
83062306a36Sopenharmony_ci	} else if (of_node_name_eq(dev, "bandit")) {
83162306a36Sopenharmony_ci		setup_bandit(hose, &rsrc);
83262306a36Sopenharmony_ci		disp_name = "Bandit";
83362306a36Sopenharmony_ci	} else if (of_node_name_eq(dev, "chaos")) {
83462306a36Sopenharmony_ci		setup_chaos(hose, &rsrc);
83562306a36Sopenharmony_ci		disp_name = "Chaos";
83662306a36Sopenharmony_ci		primary = 0;
83762306a36Sopenharmony_ci	}
83862306a36Sopenharmony_ci	printk(KERN_INFO "Found %s PCI host bridge at 0x%016llx. "
83962306a36Sopenharmony_ci	       "Firmware bus number: %d->%d\n",
84062306a36Sopenharmony_ci		disp_name, (unsigned long long)rsrc.start, hose->first_busno,
84162306a36Sopenharmony_ci		hose->last_busno);
84262306a36Sopenharmony_ci#endif /* CONFIG_PPC32 */
84362306a36Sopenharmony_ci
84462306a36Sopenharmony_ci	DBG(" ->Hose at 0x%p, cfg_addr=0x%p,cfg_data=0x%p\n",
84562306a36Sopenharmony_ci		hose, hose->cfg_addr, hose->cfg_data);
84662306a36Sopenharmony_ci
84762306a36Sopenharmony_ci	/* Interpret the "ranges" property */
84862306a36Sopenharmony_ci	/* This also maps the I/O region and sets isa_io/mem_base */
84962306a36Sopenharmony_ci	pci_process_bridge_OF_ranges(hose, dev, primary);
85062306a36Sopenharmony_ci
85162306a36Sopenharmony_ci	/* Fixup "bus-range" OF property */
85262306a36Sopenharmony_ci	fixup_bus_range(dev);
85362306a36Sopenharmony_ci
85462306a36Sopenharmony_ci	/* create pci_dn's for DT nodes under this PHB */
85562306a36Sopenharmony_ci	if (IS_ENABLED(CONFIG_PPC64))
85662306a36Sopenharmony_ci		pci_devs_phb_init_dynamic(hose);
85762306a36Sopenharmony_ci
85862306a36Sopenharmony_ci	return 0;
85962306a36Sopenharmony_ci}
86062306a36Sopenharmony_ci
86162306a36Sopenharmony_civoid pmac_pci_irq_fixup(struct pci_dev *dev)
86262306a36Sopenharmony_ci{
86362306a36Sopenharmony_ci#ifdef CONFIG_PPC32
86462306a36Sopenharmony_ci	/* Fixup interrupt for the modem/ethernet combo controller.
86562306a36Sopenharmony_ci	 * on machines with a second ohare chip.
86662306a36Sopenharmony_ci	 * The number in the device tree (27) is bogus (correct for
86762306a36Sopenharmony_ci	 * the ethernet-only board but not the combo ethernet/modem
86862306a36Sopenharmony_ci	 * board). The real interrupt is 28 on the second controller
86962306a36Sopenharmony_ci	 * -> 28+32 = 60.
87062306a36Sopenharmony_ci	 */
87162306a36Sopenharmony_ci	if (has_second_ohare &&
87262306a36Sopenharmony_ci	    dev->vendor == PCI_VENDOR_ID_DEC &&
87362306a36Sopenharmony_ci	    dev->device == PCI_DEVICE_ID_DEC_TULIP_PLUS) {
87462306a36Sopenharmony_ci		dev->irq = irq_create_mapping(NULL, 60);
87562306a36Sopenharmony_ci		irq_set_irq_type(dev->irq, IRQ_TYPE_LEVEL_LOW);
87662306a36Sopenharmony_ci	}
87762306a36Sopenharmony_ci#endif /* CONFIG_PPC32 */
87862306a36Sopenharmony_ci}
87962306a36Sopenharmony_ci
88062306a36Sopenharmony_ci#ifdef CONFIG_PPC64
88162306a36Sopenharmony_cistatic int pmac_pci_root_bridge_prepare(struct pci_host_bridge *bridge)
88262306a36Sopenharmony_ci{
88362306a36Sopenharmony_ci	struct pci_controller *hose = pci_bus_to_host(bridge->bus);
88462306a36Sopenharmony_ci	struct device_node *np, *child;
88562306a36Sopenharmony_ci
88662306a36Sopenharmony_ci	if (hose != u3_agp)
88762306a36Sopenharmony_ci		return 0;
88862306a36Sopenharmony_ci
88962306a36Sopenharmony_ci	/* Fixup the PCI<->OF mapping for U3 AGP due to bus renumbering. We
89062306a36Sopenharmony_ci	 * assume there is no P2P bridge on the AGP bus, which should be a
89162306a36Sopenharmony_ci	 * safe assumptions for now. We should do something better in the
89262306a36Sopenharmony_ci	 * future though
89362306a36Sopenharmony_ci	 */
89462306a36Sopenharmony_ci	np = hose->dn;
89562306a36Sopenharmony_ci	PCI_DN(np)->busno = 0xf0;
89662306a36Sopenharmony_ci	for_each_child_of_node(np, child)
89762306a36Sopenharmony_ci		PCI_DN(child)->busno = 0xf0;
89862306a36Sopenharmony_ci
89962306a36Sopenharmony_ci	return 0;
90062306a36Sopenharmony_ci}
90162306a36Sopenharmony_ci#endif /* CONFIG_PPC64 */
90262306a36Sopenharmony_ci
90362306a36Sopenharmony_civoid __init pmac_pci_init(void)
90462306a36Sopenharmony_ci{
90562306a36Sopenharmony_ci	struct device_node *np, *root;
90662306a36Sopenharmony_ci	struct device_node *ht __maybe_unused = NULL;
90762306a36Sopenharmony_ci
90862306a36Sopenharmony_ci	pci_set_flags(PCI_CAN_SKIP_ISA_ALIGN);
90962306a36Sopenharmony_ci
91062306a36Sopenharmony_ci	root = of_find_node_by_path("/");
91162306a36Sopenharmony_ci	if (root == NULL) {
91262306a36Sopenharmony_ci		printk(KERN_CRIT "pmac_pci_init: can't find root "
91362306a36Sopenharmony_ci		       "of device tree\n");
91462306a36Sopenharmony_ci		return;
91562306a36Sopenharmony_ci	}
91662306a36Sopenharmony_ci	for_each_child_of_node(root, np) {
91762306a36Sopenharmony_ci		if (of_node_name_eq(np, "bandit")
91862306a36Sopenharmony_ci		    || of_node_name_eq(np, "chaos")
91962306a36Sopenharmony_ci		    || of_node_name_eq(np, "pci")) {
92062306a36Sopenharmony_ci			if (pmac_add_bridge(np) == 0)
92162306a36Sopenharmony_ci				of_node_get(np);
92262306a36Sopenharmony_ci		}
92362306a36Sopenharmony_ci		if (of_node_name_eq(np, "ht")) {
92462306a36Sopenharmony_ci			of_node_get(np);
92562306a36Sopenharmony_ci			ht = np;
92662306a36Sopenharmony_ci		}
92762306a36Sopenharmony_ci	}
92862306a36Sopenharmony_ci	of_node_put(root);
92962306a36Sopenharmony_ci
93062306a36Sopenharmony_ci#ifdef CONFIG_PPC64
93162306a36Sopenharmony_ci	/* Probe HT last as it relies on the agp resources to be already
93262306a36Sopenharmony_ci	 * setup
93362306a36Sopenharmony_ci	 */
93462306a36Sopenharmony_ci	if (ht && pmac_add_bridge(ht) != 0)
93562306a36Sopenharmony_ci		of_node_put(ht);
93662306a36Sopenharmony_ci
93762306a36Sopenharmony_ci	ppc_md.pcibios_root_bridge_prepare = pmac_pci_root_bridge_prepare;
93862306a36Sopenharmony_ci	/* pmac_check_ht_link(); */
93962306a36Sopenharmony_ci
94062306a36Sopenharmony_ci#else /* CONFIG_PPC64 */
94162306a36Sopenharmony_ci	init_p2pbridge();
94262306a36Sopenharmony_ci	init_second_ohare();
94362306a36Sopenharmony_ci	fixup_nec_usb2();
94462306a36Sopenharmony_ci
94562306a36Sopenharmony_ci	/* We are still having some issues with the Xserve G4, enabling
94662306a36Sopenharmony_ci	 * some offset between bus number and domains for now when we
94762306a36Sopenharmony_ci	 * assign all busses should help for now
94862306a36Sopenharmony_ci	 */
94962306a36Sopenharmony_ci	if (pci_has_flag(PCI_REASSIGN_ALL_BUS))
95062306a36Sopenharmony_ci		pcibios_assign_bus_offset = 0x10;
95162306a36Sopenharmony_ci#endif
95262306a36Sopenharmony_ci}
95362306a36Sopenharmony_ci
95462306a36Sopenharmony_ci#ifdef CONFIG_PPC32
95562306a36Sopenharmony_cistatic bool pmac_pci_enable_device_hook(struct pci_dev *dev)
95662306a36Sopenharmony_ci{
95762306a36Sopenharmony_ci	struct device_node* node;
95862306a36Sopenharmony_ci	int updatecfg = 0;
95962306a36Sopenharmony_ci	int uninorth_child;
96062306a36Sopenharmony_ci
96162306a36Sopenharmony_ci	node = pci_device_to_OF_node(dev);
96262306a36Sopenharmony_ci
96362306a36Sopenharmony_ci	/* We don't want to enable USB controllers absent from the OF tree
96462306a36Sopenharmony_ci	 * (iBook second controller)
96562306a36Sopenharmony_ci	 */
96662306a36Sopenharmony_ci	if (dev->vendor == PCI_VENDOR_ID_APPLE
96762306a36Sopenharmony_ci	    && dev->class == PCI_CLASS_SERIAL_USB_OHCI
96862306a36Sopenharmony_ci	    && !node) {
96962306a36Sopenharmony_ci		printk(KERN_INFO "Apple USB OHCI %s disabled by firmware\n",
97062306a36Sopenharmony_ci		       pci_name(dev));
97162306a36Sopenharmony_ci		return false;
97262306a36Sopenharmony_ci	}
97362306a36Sopenharmony_ci
97462306a36Sopenharmony_ci	if (!node)
97562306a36Sopenharmony_ci		return true;
97662306a36Sopenharmony_ci
97762306a36Sopenharmony_ci	uninorth_child = node->parent &&
97862306a36Sopenharmony_ci		of_device_is_compatible(node->parent, "uni-north");
97962306a36Sopenharmony_ci
98062306a36Sopenharmony_ci	/* Firewire & GMAC were disabled after PCI probe, the driver is
98162306a36Sopenharmony_ci	 * claiming them, we must re-enable them now.
98262306a36Sopenharmony_ci	 */
98362306a36Sopenharmony_ci	if (uninorth_child && of_node_name_eq(node, "firewire") &&
98462306a36Sopenharmony_ci	    (of_device_is_compatible(node, "pci106b,18") ||
98562306a36Sopenharmony_ci	     of_device_is_compatible(node, "pci106b,30") ||
98662306a36Sopenharmony_ci	     of_device_is_compatible(node, "pci11c1,5811"))) {
98762306a36Sopenharmony_ci		pmac_call_feature(PMAC_FTR_1394_CABLE_POWER, node, 0, 1);
98862306a36Sopenharmony_ci		pmac_call_feature(PMAC_FTR_1394_ENABLE, node, 0, 1);
98962306a36Sopenharmony_ci		updatecfg = 1;
99062306a36Sopenharmony_ci	}
99162306a36Sopenharmony_ci	if (uninorth_child && of_node_name_eq(node, "ethernet") &&
99262306a36Sopenharmony_ci	    of_device_is_compatible(node, "gmac")) {
99362306a36Sopenharmony_ci		pmac_call_feature(PMAC_FTR_GMAC_ENABLE, node, 0, 1);
99462306a36Sopenharmony_ci		updatecfg = 1;
99562306a36Sopenharmony_ci	}
99662306a36Sopenharmony_ci
99762306a36Sopenharmony_ci	/*
99862306a36Sopenharmony_ci	 * Fixup various header fields on 32 bits. We don't do that on
99962306a36Sopenharmony_ci	 * 64 bits as some of these have strange values behind the HT
100062306a36Sopenharmony_ci	 * bridge and we must not, for example, enable MWI or set the
100162306a36Sopenharmony_ci	 * cache line size on them.
100262306a36Sopenharmony_ci	 */
100362306a36Sopenharmony_ci	if (updatecfg) {
100462306a36Sopenharmony_ci		u16 cmd;
100562306a36Sopenharmony_ci
100662306a36Sopenharmony_ci		pci_read_config_word(dev, PCI_COMMAND, &cmd);
100762306a36Sopenharmony_ci		cmd |= PCI_COMMAND_MEMORY | PCI_COMMAND_MASTER
100862306a36Sopenharmony_ci			| PCI_COMMAND_INVALIDATE;
100962306a36Sopenharmony_ci		pci_write_config_word(dev, PCI_COMMAND, cmd);
101062306a36Sopenharmony_ci		pci_write_config_byte(dev, PCI_LATENCY_TIMER, 16);
101162306a36Sopenharmony_ci
101262306a36Sopenharmony_ci		pci_write_config_byte(dev, PCI_CACHE_LINE_SIZE,
101362306a36Sopenharmony_ci				      L1_CACHE_BYTES >> 2);
101462306a36Sopenharmony_ci	}
101562306a36Sopenharmony_ci
101662306a36Sopenharmony_ci	return true;
101762306a36Sopenharmony_ci}
101862306a36Sopenharmony_ci
101962306a36Sopenharmony_cistatic void pmac_pci_fixup_ohci(struct pci_dev *dev)
102062306a36Sopenharmony_ci{
102162306a36Sopenharmony_ci	struct device_node *node = pci_device_to_OF_node(dev);
102262306a36Sopenharmony_ci
102362306a36Sopenharmony_ci	/* We don't want to assign resources to USB controllers
102462306a36Sopenharmony_ci	 * absent from the OF tree (iBook second controller)
102562306a36Sopenharmony_ci	 */
102662306a36Sopenharmony_ci	if (dev->class == PCI_CLASS_SERIAL_USB_OHCI && !node)
102762306a36Sopenharmony_ci		dev->resource[0].flags = 0;
102862306a36Sopenharmony_ci}
102962306a36Sopenharmony_ciDECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_APPLE, PCI_ANY_ID, pmac_pci_fixup_ohci);
103062306a36Sopenharmony_ci
103162306a36Sopenharmony_ci/* We power down some devices after they have been probed. They'll
103262306a36Sopenharmony_ci * be powered back on later on
103362306a36Sopenharmony_ci */
103462306a36Sopenharmony_civoid __init pmac_pcibios_after_init(void)
103562306a36Sopenharmony_ci{
103662306a36Sopenharmony_ci	struct device_node* nd;
103762306a36Sopenharmony_ci
103862306a36Sopenharmony_ci	for_each_node_by_name(nd, "firewire") {
103962306a36Sopenharmony_ci		if (nd->parent && (of_device_is_compatible(nd, "pci106b,18") ||
104062306a36Sopenharmony_ci				   of_device_is_compatible(nd, "pci106b,30") ||
104162306a36Sopenharmony_ci				   of_device_is_compatible(nd, "pci11c1,5811"))
104262306a36Sopenharmony_ci		    && of_device_is_compatible(nd->parent, "uni-north")) {
104362306a36Sopenharmony_ci			pmac_call_feature(PMAC_FTR_1394_ENABLE, nd, 0, 0);
104462306a36Sopenharmony_ci			pmac_call_feature(PMAC_FTR_1394_CABLE_POWER, nd, 0, 0);
104562306a36Sopenharmony_ci		}
104662306a36Sopenharmony_ci	}
104762306a36Sopenharmony_ci	for_each_node_by_name(nd, "ethernet") {
104862306a36Sopenharmony_ci		if (nd->parent && of_device_is_compatible(nd, "gmac")
104962306a36Sopenharmony_ci		    && of_device_is_compatible(nd->parent, "uni-north"))
105062306a36Sopenharmony_ci			pmac_call_feature(PMAC_FTR_GMAC_ENABLE, nd, 0, 0);
105162306a36Sopenharmony_ci	}
105262306a36Sopenharmony_ci}
105362306a36Sopenharmony_ci
105462306a36Sopenharmony_cistatic void pmac_pci_fixup_cardbus(struct pci_dev *dev)
105562306a36Sopenharmony_ci{
105662306a36Sopenharmony_ci	if (!machine_is(powermac))
105762306a36Sopenharmony_ci		return;
105862306a36Sopenharmony_ci	/*
105962306a36Sopenharmony_ci	 * Fix the interrupt routing on the various cardbus bridges
106062306a36Sopenharmony_ci	 * used on powerbooks
106162306a36Sopenharmony_ci	 */
106262306a36Sopenharmony_ci	if (dev->vendor != PCI_VENDOR_ID_TI)
106362306a36Sopenharmony_ci		return;
106462306a36Sopenharmony_ci	if (dev->device == PCI_DEVICE_ID_TI_1130 ||
106562306a36Sopenharmony_ci	    dev->device == PCI_DEVICE_ID_TI_1131) {
106662306a36Sopenharmony_ci		u8 val;
106762306a36Sopenharmony_ci		/* Enable PCI interrupt */
106862306a36Sopenharmony_ci		if (pci_read_config_byte(dev, 0x91, &val) == 0)
106962306a36Sopenharmony_ci			pci_write_config_byte(dev, 0x91, val | 0x30);
107062306a36Sopenharmony_ci		/* Disable ISA interrupt mode */
107162306a36Sopenharmony_ci		if (pci_read_config_byte(dev, 0x92, &val) == 0)
107262306a36Sopenharmony_ci			pci_write_config_byte(dev, 0x92, val & ~0x06);
107362306a36Sopenharmony_ci	}
107462306a36Sopenharmony_ci	if (dev->device == PCI_DEVICE_ID_TI_1210 ||
107562306a36Sopenharmony_ci	    dev->device == PCI_DEVICE_ID_TI_1211 ||
107662306a36Sopenharmony_ci	    dev->device == PCI_DEVICE_ID_TI_1410 ||
107762306a36Sopenharmony_ci	    dev->device == PCI_DEVICE_ID_TI_1510) {
107862306a36Sopenharmony_ci		u8 val;
107962306a36Sopenharmony_ci		/* 0x8c == TI122X_IRQMUX, 2 says to route the INTA
108062306a36Sopenharmony_ci		   signal out the MFUNC0 pin */
108162306a36Sopenharmony_ci		if (pci_read_config_byte(dev, 0x8c, &val) == 0)
108262306a36Sopenharmony_ci			pci_write_config_byte(dev, 0x8c, (val & ~0x0f) | 2);
108362306a36Sopenharmony_ci		/* Disable ISA interrupt mode */
108462306a36Sopenharmony_ci		if (pci_read_config_byte(dev, 0x92, &val) == 0)
108562306a36Sopenharmony_ci			pci_write_config_byte(dev, 0x92, val & ~0x06);
108662306a36Sopenharmony_ci	}
108762306a36Sopenharmony_ci}
108862306a36Sopenharmony_ci
108962306a36Sopenharmony_ciDECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_TI, PCI_ANY_ID, pmac_pci_fixup_cardbus);
109062306a36Sopenharmony_ci
109162306a36Sopenharmony_cistatic void pmac_pci_fixup_pciata(struct pci_dev *dev)
109262306a36Sopenharmony_ci{
109362306a36Sopenharmony_ci       u8 progif = 0;
109462306a36Sopenharmony_ci
109562306a36Sopenharmony_ci       /*
109662306a36Sopenharmony_ci        * On PowerMacs, we try to switch any PCI ATA controller to
109762306a36Sopenharmony_ci	* fully native mode
109862306a36Sopenharmony_ci        */
109962306a36Sopenharmony_ci	if (!machine_is(powermac))
110062306a36Sopenharmony_ci		return;
110162306a36Sopenharmony_ci
110262306a36Sopenharmony_ci	/* Some controllers don't have the class IDE */
110362306a36Sopenharmony_ci	if (dev->vendor == PCI_VENDOR_ID_PROMISE)
110462306a36Sopenharmony_ci		switch(dev->device) {
110562306a36Sopenharmony_ci		case PCI_DEVICE_ID_PROMISE_20246:
110662306a36Sopenharmony_ci		case PCI_DEVICE_ID_PROMISE_20262:
110762306a36Sopenharmony_ci		case PCI_DEVICE_ID_PROMISE_20263:
110862306a36Sopenharmony_ci		case PCI_DEVICE_ID_PROMISE_20265:
110962306a36Sopenharmony_ci		case PCI_DEVICE_ID_PROMISE_20267:
111062306a36Sopenharmony_ci		case PCI_DEVICE_ID_PROMISE_20268:
111162306a36Sopenharmony_ci		case PCI_DEVICE_ID_PROMISE_20269:
111262306a36Sopenharmony_ci		case PCI_DEVICE_ID_PROMISE_20270:
111362306a36Sopenharmony_ci		case PCI_DEVICE_ID_PROMISE_20271:
111462306a36Sopenharmony_ci		case PCI_DEVICE_ID_PROMISE_20275:
111562306a36Sopenharmony_ci		case PCI_DEVICE_ID_PROMISE_20276:
111662306a36Sopenharmony_ci		case PCI_DEVICE_ID_PROMISE_20277:
111762306a36Sopenharmony_ci			goto good;
111862306a36Sopenharmony_ci		}
111962306a36Sopenharmony_ci	/* Others, check PCI class */
112062306a36Sopenharmony_ci	if ((dev->class >> 8) != PCI_CLASS_STORAGE_IDE)
112162306a36Sopenharmony_ci		return;
112262306a36Sopenharmony_ci good:
112362306a36Sopenharmony_ci	pci_read_config_byte(dev, PCI_CLASS_PROG, &progif);
112462306a36Sopenharmony_ci	if ((progif & 5) != 5) {
112562306a36Sopenharmony_ci		printk(KERN_INFO "PCI: %s Forcing PCI IDE into native mode\n",
112662306a36Sopenharmony_ci		       pci_name(dev));
112762306a36Sopenharmony_ci		(void) pci_write_config_byte(dev, PCI_CLASS_PROG, progif|5);
112862306a36Sopenharmony_ci		if (pci_read_config_byte(dev, PCI_CLASS_PROG, &progif) ||
112962306a36Sopenharmony_ci		    (progif & 5) != 5)
113062306a36Sopenharmony_ci			printk(KERN_ERR "Rewrite of PROGIF failed !\n");
113162306a36Sopenharmony_ci		else {
113262306a36Sopenharmony_ci			/* Clear IO BARs, they will be reassigned */
113362306a36Sopenharmony_ci			pci_write_config_dword(dev, PCI_BASE_ADDRESS_0, 0);
113462306a36Sopenharmony_ci			pci_write_config_dword(dev, PCI_BASE_ADDRESS_1, 0);
113562306a36Sopenharmony_ci			pci_write_config_dword(dev, PCI_BASE_ADDRESS_2, 0);
113662306a36Sopenharmony_ci			pci_write_config_dword(dev, PCI_BASE_ADDRESS_3, 0);
113762306a36Sopenharmony_ci		}
113862306a36Sopenharmony_ci	}
113962306a36Sopenharmony_ci}
114062306a36Sopenharmony_ciDECLARE_PCI_FIXUP_EARLY(PCI_ANY_ID, PCI_ANY_ID, pmac_pci_fixup_pciata);
114162306a36Sopenharmony_ci#endif /* CONFIG_PPC32 */
114262306a36Sopenharmony_ci
114362306a36Sopenharmony_ci/*
114462306a36Sopenharmony_ci * Disable second function on K2-SATA, it's broken
114562306a36Sopenharmony_ci * and disable IO BARs on first one
114662306a36Sopenharmony_ci */
114762306a36Sopenharmony_cistatic void fixup_k2_sata(struct pci_dev* dev)
114862306a36Sopenharmony_ci{
114962306a36Sopenharmony_ci	int i;
115062306a36Sopenharmony_ci	u16 cmd;
115162306a36Sopenharmony_ci
115262306a36Sopenharmony_ci	if (PCI_FUNC(dev->devfn) > 0) {
115362306a36Sopenharmony_ci		pci_read_config_word(dev, PCI_COMMAND, &cmd);
115462306a36Sopenharmony_ci		cmd &= ~(PCI_COMMAND_IO | PCI_COMMAND_MEMORY);
115562306a36Sopenharmony_ci		pci_write_config_word(dev, PCI_COMMAND, cmd);
115662306a36Sopenharmony_ci		for (i = 0; i < 6; i++) {
115762306a36Sopenharmony_ci			dev->resource[i].start = dev->resource[i].end = 0;
115862306a36Sopenharmony_ci			dev->resource[i].flags = 0;
115962306a36Sopenharmony_ci			pci_write_config_dword(dev, PCI_BASE_ADDRESS_0 + 4 * i,
116062306a36Sopenharmony_ci					       0);
116162306a36Sopenharmony_ci		}
116262306a36Sopenharmony_ci	} else {
116362306a36Sopenharmony_ci		pci_read_config_word(dev, PCI_COMMAND, &cmd);
116462306a36Sopenharmony_ci		cmd &= ~PCI_COMMAND_IO;
116562306a36Sopenharmony_ci		pci_write_config_word(dev, PCI_COMMAND, cmd);
116662306a36Sopenharmony_ci		for (i = 0; i < 5; i++) {
116762306a36Sopenharmony_ci			dev->resource[i].start = dev->resource[i].end = 0;
116862306a36Sopenharmony_ci			dev->resource[i].flags = 0;
116962306a36Sopenharmony_ci			pci_write_config_dword(dev, PCI_BASE_ADDRESS_0 + 4 * i,
117062306a36Sopenharmony_ci					       0);
117162306a36Sopenharmony_ci		}
117262306a36Sopenharmony_ci	}
117362306a36Sopenharmony_ci}
117462306a36Sopenharmony_ciDECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_SERVERWORKS, 0x0240, fixup_k2_sata);
117562306a36Sopenharmony_ci
117662306a36Sopenharmony_ci/*
117762306a36Sopenharmony_ci * On U4 (aka CPC945) the PCIe root complex "P2P" bridge resource ranges aren't
117862306a36Sopenharmony_ci * configured by the firmware. The bridge itself seems to ignore them but it
117962306a36Sopenharmony_ci * causes problems with Linux which then re-assigns devices below the bridge,
118062306a36Sopenharmony_ci * thus changing addresses of those devices from what was in the device-tree,
118162306a36Sopenharmony_ci * which sucks when those are video cards using offb
118262306a36Sopenharmony_ci *
118362306a36Sopenharmony_ci * We could just mark it transparent but I prefer fixing up the resources to
118462306a36Sopenharmony_ci * properly show what's going on here, as I have some doubts about having them
118562306a36Sopenharmony_ci * badly configured potentially being an issue for DMA.
118662306a36Sopenharmony_ci *
118762306a36Sopenharmony_ci * We leave PIO alone, it seems to be fine
118862306a36Sopenharmony_ci *
118962306a36Sopenharmony_ci * Oh and there's another funny bug. The OF properties advertize the region
119062306a36Sopenharmony_ci * 0xf1000000..0xf1ffffff as being forwarded as memory space. But that's
119162306a36Sopenharmony_ci * actually not true, this region is the memory mapped config space. So we
119262306a36Sopenharmony_ci * also need to filter it out or we'll map things in the wrong place.
119362306a36Sopenharmony_ci */
119462306a36Sopenharmony_cistatic void fixup_u4_pcie(struct pci_dev* dev)
119562306a36Sopenharmony_ci{
119662306a36Sopenharmony_ci	struct pci_controller *host = pci_bus_to_host(dev->bus);
119762306a36Sopenharmony_ci	struct resource *region = NULL;
119862306a36Sopenharmony_ci	u32 reg;
119962306a36Sopenharmony_ci	int i;
120062306a36Sopenharmony_ci
120162306a36Sopenharmony_ci	/* Only do that on PowerMac */
120262306a36Sopenharmony_ci	if (!machine_is(powermac))
120362306a36Sopenharmony_ci		return;
120462306a36Sopenharmony_ci
120562306a36Sopenharmony_ci	/* Find the largest MMIO region */
120662306a36Sopenharmony_ci	for (i = 0; i < 3; i++) {
120762306a36Sopenharmony_ci		struct resource *r = &host->mem_resources[i];
120862306a36Sopenharmony_ci		if (!(r->flags & IORESOURCE_MEM))
120962306a36Sopenharmony_ci			continue;
121062306a36Sopenharmony_ci		/* Skip the 0xf0xxxxxx..f2xxxxxx regions, we know they
121162306a36Sopenharmony_ci		 * are reserved by HW for other things
121262306a36Sopenharmony_ci		 */
121362306a36Sopenharmony_ci		if (r->start >= 0xf0000000 && r->start < 0xf3000000)
121462306a36Sopenharmony_ci			continue;
121562306a36Sopenharmony_ci		if (!region || resource_size(r) > resource_size(region))
121662306a36Sopenharmony_ci			region = r;
121762306a36Sopenharmony_ci	}
121862306a36Sopenharmony_ci	/* Nothing found, bail */
121962306a36Sopenharmony_ci	if (!region)
122062306a36Sopenharmony_ci		return;
122162306a36Sopenharmony_ci
122262306a36Sopenharmony_ci	/* Print things out */
122362306a36Sopenharmony_ci	printk(KERN_INFO "PCI: Fixup U4 PCIe bridge range: %pR\n", region);
122462306a36Sopenharmony_ci
122562306a36Sopenharmony_ci	/* Fixup bridge config space. We know it's a Mac, resource aren't
122662306a36Sopenharmony_ci	 * offset so let's just blast them as-is. We also know that they
122762306a36Sopenharmony_ci	 * fit in 32 bits
122862306a36Sopenharmony_ci	 */
122962306a36Sopenharmony_ci	reg = ((region->start >> 16) & 0xfff0) | (region->end & 0xfff00000);
123062306a36Sopenharmony_ci	pci_write_config_dword(dev, PCI_MEMORY_BASE, reg);
123162306a36Sopenharmony_ci	pci_write_config_dword(dev, PCI_PREF_BASE_UPPER32, 0);
123262306a36Sopenharmony_ci	pci_write_config_dword(dev, PCI_PREF_LIMIT_UPPER32, 0);
123362306a36Sopenharmony_ci	pci_write_config_dword(dev, PCI_PREF_MEMORY_BASE, 0);
123462306a36Sopenharmony_ci}
123562306a36Sopenharmony_ciDECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_APPLE, PCI_DEVICE_ID_APPLE_U4_PCIE, fixup_u4_pcie);
123662306a36Sopenharmony_ci
123762306a36Sopenharmony_ci#ifdef CONFIG_PPC64
123862306a36Sopenharmony_cistatic int pmac_pci_probe_mode(struct pci_bus *bus)
123962306a36Sopenharmony_ci{
124062306a36Sopenharmony_ci	struct device_node *node = pci_bus_to_OF_node(bus);
124162306a36Sopenharmony_ci
124262306a36Sopenharmony_ci	/* We need to use normal PCI probing for the AGP bus,
124362306a36Sopenharmony_ci	 * since the device for the AGP bridge isn't in the tree.
124462306a36Sopenharmony_ci	 * Same for the PCIe host on U4 and the HT host bridge.
124562306a36Sopenharmony_ci	 */
124662306a36Sopenharmony_ci	if (bus->self == NULL && (of_device_is_compatible(node, "u3-agp") ||
124762306a36Sopenharmony_ci				  of_device_is_compatible(node, "u4-pcie") ||
124862306a36Sopenharmony_ci				  of_device_is_compatible(node, "u3-ht")))
124962306a36Sopenharmony_ci		return PCI_PROBE_NORMAL;
125062306a36Sopenharmony_ci	return PCI_PROBE_DEVTREE;
125162306a36Sopenharmony_ci}
125262306a36Sopenharmony_ci#endif /* CONFIG_PPC64 */
125362306a36Sopenharmony_ci
125462306a36Sopenharmony_cistruct pci_controller_ops pmac_pci_controller_ops = {
125562306a36Sopenharmony_ci#ifdef CONFIG_PPC64
125662306a36Sopenharmony_ci	.probe_mode		= pmac_pci_probe_mode,
125762306a36Sopenharmony_ci#endif
125862306a36Sopenharmony_ci#ifdef CONFIG_PPC32
125962306a36Sopenharmony_ci	.enable_device_hook	= pmac_pci_enable_device_hook,
126062306a36Sopenharmony_ci#endif
126162306a36Sopenharmony_ci};
1262