Deleted Added
full compact
ofw_pcibus.c (178728) ofw_pcibus.c (182020)
1/*-
2 * Copyright (c) 1997, Stefan Esser <se@freebsd.org>
3 * Copyright (c) 2000, Michael Smith <msmith@freebsd.org>
4 * Copyright (c) 2000, BSDi
5 * Copyright (c) 2003, Thomas Moestl <tmm@FreeBSD.org>
6 * All rights reserved.
7 *
8 * Redistribution and use in source and binary forms, with or without

--- 14 unchanged lines hidden (view full) ---

23 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
24 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
25 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
26 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
27 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28 */
29
30#include <sys/cdefs.h>
1/*-
2 * Copyright (c) 1997, Stefan Esser <se@freebsd.org>
3 * Copyright (c) 2000, Michael Smith <msmith@freebsd.org>
4 * Copyright (c) 2000, BSDi
5 * Copyright (c) 2003, Thomas Moestl <tmm@FreeBSD.org>
6 * All rights reserved.
7 *
8 * Redistribution and use in source and binary forms, with or without

--- 14 unchanged lines hidden (view full) ---

23 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
24 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
25 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
26 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
27 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28 */
29
30#include <sys/cdefs.h>
31__FBSDID("$FreeBSD: head/sys/sparc64/pci/ofw_pcibus.c 178728 2008-05-02 17:44:18Z marius $");
31__FBSDID("$FreeBSD: head/sys/sparc64/pci/ofw_pcibus.c 182020 2008-08-22 20:28:19Z marius $");
32
33#include "opt_ofw_pci.h"
34
35#include <sys/param.h>
36#include <sys/bus.h>
37#include <sys/kernel.h>
38#include <sys/libkern.h>
39#include <sys/module.h>

--- 15 unchanged lines hidden (view full) ---

55#include <dev/pci/pcivar.h>
56#include <dev/pci/pci_private.h>
57
58#include <sparc64/pci/ofw_pci.h>
59
60#include "pcib_if.h"
61#include "pci_if.h"
62
32
33#include "opt_ofw_pci.h"
34
35#include <sys/param.h>
36#include <sys/bus.h>
37#include <sys/kernel.h>
38#include <sys/libkern.h>
39#include <sys/module.h>

--- 15 unchanged lines hidden (view full) ---

55#include <dev/pci/pcivar.h>
56#include <dev/pci/pci_private.h>
57
58#include <sparc64/pci/ofw_pci.h>
59
60#include "pcib_if.h"
61#include "pci_if.h"
62
63/* Helper functions. */
63/* Helper functions */
64static void ofw_pcibus_setup_device(device_t, u_int, u_int, u_int);
65
64static void ofw_pcibus_setup_device(device_t, u_int, u_int, u_int);
65
66/* Methods. */
66/* Methods */
67static device_probe_t ofw_pcibus_probe;
68static device_attach_t ofw_pcibus_attach;
69static pci_assign_interrupt_t ofw_pcibus_assign_interrupt;
70static ofw_bus_get_devinfo_t ofw_pcibus_get_devinfo;
71
72static device_method_t ofw_pcibus_methods[] = {
73 /* Device interface */
74 DEVMETHOD(device_probe, ofw_pcibus_probe),

--- 43 unchanged lines hidden (view full) ---

118 * Perform miscellaneous setups the firmware usually does not do for us.
119 */
120static void
121ofw_pcibus_setup_device(device_t bridge, u_int busno, u_int slot, u_int func)
122{
123 uint32_t reg;
124
125 /*
67static device_probe_t ofw_pcibus_probe;
68static device_attach_t ofw_pcibus_attach;
69static pci_assign_interrupt_t ofw_pcibus_assign_interrupt;
70static ofw_bus_get_devinfo_t ofw_pcibus_get_devinfo;
71
72static device_method_t ofw_pcibus_methods[] = {
73 /* Device interface */
74 DEVMETHOD(device_probe, ofw_pcibus_probe),

--- 43 unchanged lines hidden (view full) ---

118 * Perform miscellaneous setups the firmware usually does not do for us.
119 */
120static void
121ofw_pcibus_setup_device(device_t bridge, u_int busno, u_int slot, u_int func)
122{
123 uint32_t reg;
124
125 /*
126 * Initialize the latency timer register for busmaster devices to work
127 * properly. This is another task which the firmware does not always
128 * perform. The Min_Gnt register can be used to compute it's recommended
129 * value: it contains the desired latency in units of 1/4 us. To
130 * calculate the correct latency timer value, the clock frequency of
131 * the bus (defaulting to 33Mhz) should be used and no wait states
126 * Initialize the latency timer register for busmaster devices to
127 * work properly. This is another task which the firmware doesn't
128 * always perform. The Min_Gnt register can be used to compute its
129 * recommended value: it contains the desired latency in units of
130 * 1/4 us. To calculate the correct latency timer value, the clock
131 * frequency of the bus (defaulting to 33MHz) and no wait states
132 * should be assumed.
133 */
134 if (OF_getprop(ofw_bus_get_node(bridge), "clock-frequency", &reg,
135 sizeof(reg)) == -1)
136 reg = 33000000;
137 reg = PCIB_READ_CONFIG(bridge, busno, slot, func, PCIR_MINGNT, 1) *
138 reg / 1000000 / 4;
139 if (reg != 0) {

--- 6 unchanged lines hidden (view full) ---

146 PCIB_WRITE_CONFIG(bridge, busno, slot, func,
147 PCIR_LATTIMER, min(reg, 255), 1);
148 }
149
150#ifndef SUN4V
151 /*
152 * Compute a value to write into the cache line size register.
153 * The role of the streaming cache is unclear in write invalidate
132 * should be assumed.
133 */
134 if (OF_getprop(ofw_bus_get_node(bridge), "clock-frequency", &reg,
135 sizeof(reg)) == -1)
136 reg = 33000000;
137 reg = PCIB_READ_CONFIG(bridge, busno, slot, func, PCIR_MINGNT, 1) *
138 reg / 1000000 / 4;
139 if (reg != 0) {

--- 6 unchanged lines hidden (view full) ---

146 PCIB_WRITE_CONFIG(bridge, busno, slot, func,
147 PCIR_LATTIMER, min(reg, 255), 1);
148 }
149
150#ifndef SUN4V
151 /*
152 * Compute a value to write into the cache line size register.
153 * The role of the streaming cache is unclear in write invalidate
154 * transfers, so it is made sure that it's line size is always reached.
155 * Generally, the cache line size is fixed at 64 bytes by Fireplane/
156 * Safari, JBus and UPA.
154 * transfers, so it is made sure that it's line size is always
155 * reached. Generally, the cache line size is fixed at 64 bytes
156 * by Fireplane/Safari, JBus and UPA.
157 */
158 PCIB_WRITE_CONFIG(bridge, busno, slot, func, PCIR_CACHELNSZ,
159 STRBUF_LINESZ / sizeof(uint32_t), 1);
160#endif
161
162 /*
157 */
158 PCIB_WRITE_CONFIG(bridge, busno, slot, func, PCIR_CACHELNSZ,
159 STRBUF_LINESZ / sizeof(uint32_t), 1);
160#endif
161
162 /*
163 * The preset in the intline register is usually wrong. Reset it to 255,
164 * so that the PCI code will reroute the interrupt if needed.
163 * The preset in the intline register is usually wrong. Reset
164 * it to 255, so that the PCI code will reroute the interrupt if
165 * needed.
165 */
166 PCIB_WRITE_CONFIG(bridge, busno, slot, func, PCIR_INTLINE,
167 PCI_INVALID_IRQ, 1);
168}
169
170static int
171ofw_pcibus_attach(device_t dev)
172{

--- 5 unchanged lines hidden (view full) ---

178
179 pcib = device_get_parent(dev);
180
181 domain = pcib_get_domain(dev);
182 busno = pcib_get_bus(dev);
183 if (bootverbose)
184 device_printf(dev, "domain=%d, physical bus=%d\n",
185 domain, busno);
166 */
167 PCIB_WRITE_CONFIG(bridge, busno, slot, func, PCIR_INTLINE,
168 PCI_INVALID_IRQ, 1);
169}
170
171static int
172ofw_pcibus_attach(device_t dev)
173{

--- 5 unchanged lines hidden (view full) ---

179
180 pcib = device_get_parent(dev);
181
182 domain = pcib_get_domain(dev);
183 busno = pcib_get_bus(dev);
184 if (bootverbose)
185 device_printf(dev, "domain=%d, physical bus=%d\n",
186 domain, busno);
186
187 node = ofw_bus_get_node(dev);
188
189#ifndef SUN4V
190 /* Add the PCI side of the HOST-PCI bridge itself to the bus. */
191 if (strcmp(device_get_name(device_get_parent(pcib)), "nexus") == 0 &&
192 (dinfo = (struct ofw_pcibus_devinfo *)pci_read_device(pcib,
193 domain, busno, 0, 0, sizeof(*dinfo))) != NULL) {
194 if (ofw_bus_gen_setup_devinfo(&dinfo->opd_obdinfo, node) != 0)

--- 37 unchanged lines hidden (view full) ---

232 sizeof(intr));
233 if (isz != sizeof(intr)) {
234 /* No property; our best guess is the intpin. */
235 intr = pci_get_intpin(child);
236#ifndef SUN4V
237 } else if (intr >= 255) {
238 /*
239 * A fully specified interrupt (including IGN), as present on
187 node = ofw_bus_get_node(dev);
188
189#ifndef SUN4V
190 /* Add the PCI side of the HOST-PCI bridge itself to the bus. */
191 if (strcmp(device_get_name(device_get_parent(pcib)), "nexus") == 0 &&
192 (dinfo = (struct ofw_pcibus_devinfo *)pci_read_device(pcib,
193 domain, busno, 0, 0, sizeof(*dinfo))) != NULL) {
194 if (ofw_bus_gen_setup_devinfo(&dinfo->opd_obdinfo, node) != 0)

--- 37 unchanged lines hidden (view full) ---

232 sizeof(intr));
233 if (isz != sizeof(intr)) {
234 /* No property; our best guess is the intpin. */
235 intr = pci_get_intpin(child);
236#ifndef SUN4V
237 } else if (intr >= 255) {
238 /*
239 * A fully specified interrupt (including IGN), as present on
240 * SPARCengine Ultra AX and e450. Extract the INO and return it.
240 * SPARCengine Ultra AX and E450. Extract the INO and return
241 * it.
241 */
242 return (INTINO(intr));
243#endif
244 }
245 /*
246 * If we got intr from a property, it may or may not be an intpin.
247 * For on-board devices, it frequently is not, and is completely out
242 */
243 return (INTINO(intr));
244#endif
245 }
246 /*
247 * If we got intr from a property, it may or may not be an intpin.
248 * For on-board devices, it frequently is not, and is completely out
248 * of the valid intpin range. For PCI slots, it hopefully is, otherwise
249 * we will have trouble interfacing with non-OFW buses such as cardbus.
249 * of the valid intpin range. For PCI slots, it hopefully is,
250 * otherwise we will have trouble interfacing with non-OFW buses
251 * such as cardbus.
250 * Since we cannot tell which it is without violating layering, we
252 * Since we cannot tell which it is without violating layering, we
251 * will always use the route_interrupt method, and treat exceptions on
252 * the level they become apparent.
253 * will always use the route_interrupt method, and treat exceptions
254 * on the level they become apparent.
253 */
254 return (PCIB_ROUTE_INTERRUPT(device_get_parent(dev), child, intr));
255}
256
257static const struct ofw_bus_devinfo *
258ofw_pcibus_get_devinfo(device_t bus, device_t dev)
259{
260 struct ofw_pcibus_devinfo *dinfo;
261
262 dinfo = device_get_ivars(dev);
263 return (&dinfo->opd_obdinfo);
264}
255 */
256 return (PCIB_ROUTE_INTERRUPT(device_get_parent(dev), child, intr));
257}
258
259static const struct ofw_bus_devinfo *
260ofw_pcibus_get_devinfo(device_t bus, device_t dev)
261{
262 struct ofw_pcibus_devinfo *dinfo;
263
264 dinfo = device_get_ivars(dev);
265 return (&dinfo->opd_obdinfo);
266}