summaryrefslogtreecommitdiffstats
path: root/sys/pci/pci.c
diff options
context:
space:
mode:
authorroger <roger@FreeBSD.org>1999-05-31 22:13:37 +0000
committerroger <roger@FreeBSD.org>1999-05-31 22:13:37 +0000
commit4d37f3729be0a83ecedc31dfe8b0811bdf1bcfd2 (patch)
tree914bbff488d9b51275d2629f388e23048b220b2f /sys/pci/pci.c
parentd17fc0888d6a250d427fdecad8c383a01d53df57 (diff)
downloadFreeBSD-src-4d37f3729be0a83ecedc31dfe8b0811bdf1bcfd2.zip
FreeBSD-src-4d37f3729be0a83ecedc31dfe8b0811bdf1bcfd2.tar.gz
On the new Meteor cards, the Philips SAA 7116 is connected to the PCI bus
via an IBM PCI-PCI bridge (82351 or 82352 or 82353) The driver must identify if it is on a secondary PCI bus, which is created via the IBM PCI-PCI bridge. If it is, then it must initialise the IBM PCI-PCI bridge correctly. To do this, the following new functions are added. Because they use the pcici_t tag, they are considered 2.2 compatibility APIs pcici_t * pci_get_parent_from_tag(pcici_t tag); int pci_get_bus_from_tag(pcici_t tag); (The _from_tag suffix is used to prevent clashes with similarly named newbus PCI API functions) Submitted by: Anton Berezin <tobez@plab.ku.dk> Reviewed by: Doug Rabson <dfr@nlsystems.com> Reworked by: Me (roger)
Diffstat (limited to 'sys/pci/pci.c')
-rw-r--r--sys/pci/pci.c48
1 files changed, 47 insertions, 1 deletions
diff --git a/sys/pci/pci.c b/sys/pci/pci.c
index 8bc9c1d..2c86832 100644
--- a/sys/pci/pci.c
+++ b/sys/pci/pci.c
@@ -23,7 +23,7 @@
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
- * $Id: pci.c,v 1.106 1999/05/30 16:53:36 phk Exp $
+ * $Id: pci.c,v 1.107 1999/05/31 11:29:01 phk Exp $
*
*/
@@ -555,6 +555,52 @@ pci_conf_match(struct pci_match_conf *matches, int num_matches,
return(1);
}
+/*
+ * Locate the parent of a PCI device by scanning the PCI devlist
+ * and return the entry for the parent.
+ * For devices on PCI Bus 0 (the host bus), this is the PCI Host.
+ * For devices on secondary PCI busses, this is that bus' PCI-PCI Bridge.
+ */
+
+pcicfgregs *
+pci_devlist_get_parent(pcicfgregs *cfg)
+{
+ struct devlist *devlist_head;
+ struct pci_devinfo *dinfo;
+ pcicfgregs *bridge_cfg;
+ int i;
+
+ dinfo = STAILQ_FIRST(devlist_head = &pci_devq);
+
+ /* If the device is on PCI bus 0, look for the host */
+ if (cfg->bus == 0) {
+ for (i = 0; (dinfo != NULL) && (i < pci_numdevs);
+ dinfo = STAILQ_NEXT(dinfo, pci_links), i++) {
+ bridge_cfg = &dinfo->cfg;
+ if (bridge_cfg->baseclass == PCIC_BRIDGE
+ && bridge_cfg->subclass == PCIS_BRIDGE_HOST
+ && bridge_cfg->bus == cfg->bus) {
+ return bridge_cfg;
+ }
+ }
+ }
+
+ /* If the device is not on PCI bus 0, look for the PCI-PCI bridge */
+ if (cfg->bus > 0) {
+ for (i = 0; (dinfo != NULL) && (i < pci_numdevs);
+ dinfo = STAILQ_NEXT(dinfo, pci_links), i++) {
+ bridge_cfg = &dinfo->cfg;
+ if (bridge_cfg->baseclass == PCIC_BRIDGE
+ && bridge_cfg->subclass == PCIS_BRIDGE_PCI
+ && bridge_cfg->secondarybus == cfg->bus) {
+ return bridge_cfg;
+ }
+ }
+ }
+
+ return NULL;
+}
+
static int
pci_ioctl(dev_t dev, u_long cmd, caddr_t data, int flag, struct proc *p)
{
OpenPOWER on IntegriCloud