abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi/*
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * CDDL HEADER START
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * The contents of this file are subject to the terms of the
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * Common Development and Distribution License (the "License").
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * You may not use this file except in compliance with the License.
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * or http://www.opensolaris.org/os/licensing.
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * See the License for the specific language governing permissions
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * and limitations under the License.
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * When distributing Covered Code, include this CDDL HEADER in each
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * If applicable, add the following below this CDDL HEADER, with the
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * fields enclosed by brackets "[]" replaced with your own identifying
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * information: Portions Copyright [yyyy] [name of copyright owner]
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * CDDL HEADER END
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi */
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi/*
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * Copyright (c) 2012, Joyent, Inc. All rights reserved.
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi */
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi/*
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * This library exists to understand and parse the pci.ids database that is
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * maintained at http://pci-ids.ucw.cz/ and in the gate at cmd/hwdata. This
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * database provides a way to map the PCI device, vendor, and subsystem ids to
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * a human understandable name.
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * This library exports this data in a similar way to a tree. The handle that
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * is returned from pcidb_open is the root of the tree. The next level are the
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * vendors. Each vendor has a unique set of devices and each device has a unique
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * set of subvendor and subdevice pairs.
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * Parsing information:
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * The database is formatted in the following basic format:
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * vendor_id<two spaces>vendor_name
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * <tab>device_id<two spaces>device_name
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * <tab><tab>subvendor<space>subdevice<two spaces>subsystem_name
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * For any given vendor, there can be multiple devices. And for any given device
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * there will be multiple subsystems. In addition, there can be comments that
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * start a line which use the '#' character.
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * At the end of the file, there are a series of PCI classes. Those will start
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * with a single C<space>. Once we hit those, we stop all parsing. We currently
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi * don't care about consuming or presenting those.
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi */
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi#include <sys/types.h>
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi#include <stdint.h>
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi#include <stdio.h>
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi#include <stdlib.h>
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi#include <errno.h>
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi#include <string.h>
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi#include <assert.h>
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi#include <unistd.h>
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi#include "pcidb.h"
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi#define PCI_NAME_MAX 256
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi#define PCI_READLINE 1024
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi/* Forward declarations */
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchistruct pcidb_vendor;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchistruct pcidb_device;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchistruct pcidb_subvd;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchistruct pcidb_subvd {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi uint16_t ps_vid;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi uint16_t ps_did;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi char ps_name[PCI_NAME_MAX];
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi struct pcidb_subvd *ps_prev;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi struct pcidb_subvd *ps_next;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi struct pcidb_device *ps_dev;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi struct pcidb_vendor *ps_vend;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi};
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchistruct pcidb_device {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi uint16_t pd_id;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi char pd_name[PCI_NAME_MAX];
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi struct pcidb_subvd *pd_sstart;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi struct pcidb_subvd *pd_send;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi struct pcidb_device *pd_next;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi struct pcidb_device *pd_prev;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi struct pcidb_vendor *pd_vend;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi};
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchistruct pcidb_vendor {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi uint16_t pv_id;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi char pv_name[PCI_NAME_MAX];
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi struct pcidb_device *pv_dstart;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi struct pcidb_device *pv_dend;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi struct pcidb_vendor *pv_prev;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi struct pcidb_vendor *pv_next;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi};
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchistruct pcidb_hdl {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi pcidb_vendor_t *ph_vstart;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi pcidb_vendor_t *ph_vend;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi};
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchitypedef enum pcidb_parse {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi PDB_VENDOR,
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi PDB_DEVICE,
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi PDB_SUBDEV
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi} pcidb_parse_t;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchistatic const char *pci_db = "/usr/share/hwdata/pci.ids";
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchistatic void
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcihdl_add_vendor(pcidb_hdl_t *hdl, pcidb_vendor_t *v)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (hdl->ph_vstart == NULL && hdl->ph_vend == NULL) {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi hdl->ph_vstart = v;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi hdl->ph_vend = v;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi v->pv_prev = NULL;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi v->pv_next = NULL;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi } else {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi v->pv_prev = hdl->ph_vend;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi v->pv_next = NULL;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi hdl->ph_vend->pv_next = v;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi hdl->ph_vend = v;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi }
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchistatic pcidb_vendor_t *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchiparse_vendor(char *buf, pcidb_hdl_t *hdl)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi pcidb_vendor_t *v;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi size_t len;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi v = malloc(sizeof (pcidb_vendor_t));
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (v == NULL)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (NULL);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi pcihdl_add_vendor(hdl, v);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi v->pv_dstart = NULL;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi v->pv_dend = NULL;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi buf[4] = '\0';
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi v->pv_id = strtol(buf, NULL, 16);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi buf += 6;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi len = strlen(buf);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (buf[len-1] == '\n')
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi buf[len-1] = '\0';
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi (void) strlcpy(v->pv_name, buf, PCI_NAME_MAX);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (v);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchistatic void
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchiinsert_device(pcidb_vendor_t *v, pcidb_device_t *d)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi d->pd_vend = v;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (v->pv_dstart == NULL && v->pv_dend == NULL) {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi v->pv_dstart = d;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi v->pv_dend = d;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi d->pd_next = NULL;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi d->pd_prev = NULL;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi } else {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi d->pd_prev = v->pv_dend;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi d->pd_next = NULL;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi v->pv_dend->pd_next = d;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi v->pv_dend = d;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi }
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchistatic pcidb_device_t *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchiparse_device(char *buf, pcidb_vendor_t *v)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi pcidb_device_t *d;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi size_t len;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi d = malloc(sizeof (pcidb_device_t));
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (d == NULL)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (d);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi d->pd_sstart = NULL;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi d->pd_send = NULL;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi insert_device(v, d);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi buf++;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi buf[4] = '\0';
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi d->pd_id = strtol(buf, NULL, 16);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi buf += 6;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi len = strlen(buf);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (buf[len-1] == '\n')
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi buf[len-1] = '\0';
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi (void) strlcpy(d->pd_name, buf, PCI_NAME_MAX);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (d);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchistatic void
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchiinsert_subdev(pcidb_device_t *d, pcidb_subvd_t *s)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi s->ps_dev = d;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi s->ps_vend = d->pd_vend;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (d->pd_sstart == NULL) {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi d->pd_sstart = s;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi d->pd_send = s;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi s->ps_prev = NULL;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi s->ps_next = NULL;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi } else {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi s->ps_prev = d->pd_send;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi s->ps_next = NULL;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi d->pd_send->ps_next = s;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi d->pd_send = s;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi }
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchistatic pcidb_subvd_t *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchiparse_subdev(char *buf, pcidb_device_t *d)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi pcidb_subvd_t *s;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi size_t len;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi s = malloc(sizeof (pcidb_subvd_t));
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (s == NULL)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (NULL);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi insert_subdev(d, s);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi buf += 2;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi buf[4] = '\0';
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi s->ps_vid = strtol(buf, NULL, 16);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi buf += 5;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi buf[4] = '\0';
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi s->ps_did = strtol(buf, NULL, 16);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi buf += 6;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi len = strlen(buf);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (buf[len-1] == '\n')
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi buf[len-1] = '\0';
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi (void) strlcpy(s->ps_name, buf, PCI_NAME_MAX);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (s);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchistatic int
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchireadline(FILE *f, char *buf, size_t len)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi for (;;) {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (fgets(buf, len, f) == NULL)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (-1);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (buf[0] == 'C')
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (-1);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (buf[0] != '#' && buf[0] != '\n')
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (0);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi }
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchistatic int
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchiparse_db(FILE *f, pcidb_hdl_t *hdl)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi char buf[1024];
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi pcidb_vendor_t *v = NULL;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi pcidb_device_t *d = NULL;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi pcidb_parse_t state = PDB_VENDOR;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi for (;;) {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi errno = 0;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (readline(f, buf, sizeof (buf)) != 0) {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (errno != 0)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (-1);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi else
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (0);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi }
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchinewstate:
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi switch (state) {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi case PDB_VENDOR:
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi v = parse_vendor(buf, hdl);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (v == NULL)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (NULL);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi state = PDB_DEVICE;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi continue;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi case PDB_DEVICE:
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (buf[0] != '\t') {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi state = PDB_VENDOR;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi goto newstate;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi }
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (buf[1] == '\t') {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi state = PDB_SUBDEV;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi goto newstate;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi }
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi assert(v != NULL);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi d = parse_device(buf, v);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (d == NULL)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (NULL);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi continue;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi case PDB_SUBDEV:
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (buf[0] != '\t') {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi state = PDB_VENDOR;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi goto newstate;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi }
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (buf[0] == '\t' && buf[1] != '\t') {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi state = PDB_DEVICE;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi goto newstate;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi }
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi assert(buf[0] == '\t' && buf[1] == '\t');
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi assert(d != NULL);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi (void) parse_subdev(buf, d);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi }
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi }
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_hdl_t *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_open(int version)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi pcidb_hdl_t *h;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi FILE *f;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (version != PCIDB_VERSION) {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi errno = EINVAL;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (NULL);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi }
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi h = malloc(sizeof (pcidb_hdl_t));
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (h == NULL)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (NULL);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi h->ph_vstart = NULL;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi h->ph_vend = NULL;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi f = fopen(pci_db, "rF");
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (f == NULL) {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi free(h);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (NULL);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi }
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (parse_db(f, h) < 0) {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi pcidb_close(h);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi free(h);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (NULL);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi }
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (h);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchivoid
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_close(pcidb_hdl_t *h)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi pcidb_vendor_t *v, *tv;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi pcidb_device_t *d, *td;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi pcidb_subvd_t *s, *ts;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (h == NULL)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi v = h->ph_vstart;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi while (v != NULL) {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi d = v->pv_dstart;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi while (d != NULL) {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi s = d->pd_sstart;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi while (s != NULL) {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi ts = s;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi s = s->ps_next;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi free(ts);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi }
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi td = d;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi d = d->pd_next;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi free(td);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi }
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi tv = v;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi v = v->pv_next;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi free(tv);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi }
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi free(h);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_vendor_t *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_lookup_vendor(pcidb_hdl_t *hdl, uint16_t id)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi pcidb_vendor_t *v;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi for (v = hdl->ph_vstart; v != NULL; v = v->pv_next) {
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (v->pv_id == id)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (v);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi }
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (NULL);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchiconst char *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_vendor_name(pcidb_vendor_t *v)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (v->pv_name);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchiuint16_t
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_vendor_id(pcidb_vendor_t *v)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (v->pv_id);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_vendor_t *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_vendor_iter(pcidb_hdl_t *h)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (h->ph_vstart);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_vendor_t *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_vendor_iter_next(pcidb_vendor_t *v)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi assert(v != NULL);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (v->pv_next);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_device_t *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_lookup_device_by_vendor(pcidb_vendor_t *v, uint16_t id)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi pcidb_device_t *d;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi assert(v != NULL);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi for (d = v->pv_dstart; d != NULL; d = d->pd_next)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (d->pd_id == id)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (d);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (NULL);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_device_t *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_lookup_device(pcidb_hdl_t *h, uint16_t vid, uint16_t did)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi pcidb_vendor_t *v;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi v = pcidb_lookup_vendor(h, vid);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (v == NULL)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (NULL);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (pcidb_lookup_device_by_vendor(v, did));
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_device_t *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_device_iter(pcidb_vendor_t *v)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (v->pv_dstart);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_device_t *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_device_iter_next(pcidb_device_t *d)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (d->pd_next);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchiconst char *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_device_name(pcidb_device_t *d)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (d->pd_name);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchiuint16_t
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_device_id(pcidb_device_t *d)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (d->pd_id);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_vendor_t *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_device_vendor(pcidb_device_t *d)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (d->pd_vend);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_subvd_t *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_lookup_subvd_by_device(pcidb_device_t *d, uint16_t svid, uint16_t sdid)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi pcidb_subvd_t *s;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi assert(d != NULL);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi for (s = d->pd_sstart; s != NULL; s = s->ps_next)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (s->ps_vid == svid && s->ps_did == sdid)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (s);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (NULL);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_subvd_t *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_lookup_subvd_by_vendor(pcidb_vendor_t *v, uint16_t devid, uint16_t svid,
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi uint16_t sdid)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi pcidb_device_t *d;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi assert(v != NULL);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi d = pcidb_lookup_device_by_vendor(v, devid);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (d == NULL)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (NULL);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (pcidb_lookup_subvd_by_device(d, svid, sdid));
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_subvd_t *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_lookup_subvd(pcidb_hdl_t *h, uint16_t vid, uint16_t did, uint16_t svid,
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi uint16_t sdid)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi pcidb_device_t *d;
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi assert(h != NULL);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi d = pcidb_lookup_device(h, vid, did);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi if (d == NULL)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (NULL);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (pcidb_lookup_subvd_by_device(d, svid, sdid));
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_subvd_t *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_subvd_iter(pcidb_device_t *d)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (d->pd_sstart);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_subvd_t *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_subvd_iter_next(pcidb_subvd_t *s)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (s->ps_next);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchiconst char *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_subvd_name(pcidb_subvd_t *s)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (s->ps_name);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchiuint16_t
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_subvd_svid(pcidb_subvd_t *s)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (s->ps_vid);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchiuint16_t
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_subvd_sdid(pcidb_subvd_t *s)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (s->ps_did);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_device_t *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_subvd_device(pcidb_subvd_t *s)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (s->ps_dev);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_vendor_t *
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchipcidb_subvd_vendor(pcidb_subvd_t *s)
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi{
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi return (s->ps_vend);
abc79d9dd51e98eafb6fc25b4a0b4f66bef40b00Robert Mustacchi}