3 * by yinghai.lu@amd.com
6 #include <console/console.h>
7 #include <device/device.h>
8 #include <device/pci.h>
9 #include <device/pnp.h>
10 #include <device/pci_ids.h>
11 #include <device/pci_ops.h>
12 #include <pc80/mc146818rtc.h>
13 #include <pc80/isa-dma.h>
16 #include <device/smbus.h>
18 #include "bcm5785_smbus.h"
22 static void sb_init(device_t dev)
28 /* Set up NMI on errors */
29 byte = inb(0x70); // RTC70
32 get_option(&nmi_option, "nmi");
34 byte &= ~(1 << 7); /* set NMI */
36 byte |= ( 1 << 7); // Can not mask NMI from PCI-E and NMI_NOW
38 if( byte != byte_old) {
45 static void bcm5785_sb_read_resources(device_t dev)
49 /* Get the normal pci resources of this device */
50 pci_dev_read_resources(dev);
51 /* Get Resource for SMBUS */
52 pci_get_resource(dev, 0x90);
54 compact_resources(dev);
56 /* Add an extra subtractive resource for both memory and I/O */
57 res = new_resource(dev, IOINDEX_SUBTRACTIVE(0, 0));
58 res->flags = IORESOURCE_IO | IORESOURCE_SUBTRACTIVE | IORESOURCE_ASSIGNED;
60 res = new_resource(dev, IOINDEX_SUBTRACTIVE(1, 0));
61 res->flags = IORESOURCE_MEM | IORESOURCE_SUBTRACTIVE | IORESOURCE_ASSIGNED;
65 static int lsmbus_recv_byte(device_t dev)
71 device = dev->path.i2c.device;
72 pbus = get_pbus_smbus(dev);
74 res = find_resource(pbus->dev, 0x90);
76 return do_smbus_recv_byte(res->base, device);
79 static int lsmbus_send_byte(device_t dev, uint8_t val)
85 device = dev->path.i2c.device;
86 pbus = get_pbus_smbus(dev);
88 res = find_resource(pbus->dev, 0x90);
90 return do_smbus_send_byte(res->base, device, val);
92 static int lsmbus_read_byte(device_t dev, uint8_t address)
98 device = dev->path.i2c.device;
99 pbus = get_pbus_smbus(dev);
101 res = find_resource(pbus->dev, 0x90);
103 return do_smbus_read_byte(res->base, device, address);
105 static int lsmbus_write_byte(device_t dev, uint8_t address, uint8_t val)
108 struct resource *res;
111 device = dev->path.i2c.device;
112 pbus = get_pbus_smbus(dev);
114 res = find_resource(pbus->dev, 0x90);
116 return do_smbus_write_byte(res->base, device, address, val);
118 static struct smbus_bus_operations lops_smbus_bus = {
119 .recv_byte = lsmbus_recv_byte,
120 .send_byte = lsmbus_send_byte,
121 .read_byte = lsmbus_read_byte,
122 .write_byte = lsmbus_write_byte,
125 static void lpci_set_subsystem(device_t dev, unsigned vendor, unsigned device)
127 pci_write_config32(dev, 0x2c,
128 ((device & 0xffff) << 16) | (vendor & 0xffff));
131 static struct pci_operations lops_pci = {
132 .set_subsystem = lpci_set_subsystem,
135 static struct device_operations sb_ops = {
136 .read_resources = bcm5785_sb_read_resources,
137 .set_resources = pci_dev_set_resources,
138 .enable_resources = pci_dev_enable_resources,
140 .scan_bus = scan_static_bus,
141 // .enable = bcm5785_enable,
142 .ops_pci = &lops_pci,
143 .ops_smbus_bus = &lops_smbus_bus,
145 static const struct pci_driver sb_driver __pci_driver = {
147 .vendor = PCI_VENDOR_ID_SERVERWORKS,
148 .device = PCI_DEVICE_ID_SERVERWORKS_BCM5785_SB_PCI_MAIN,