From 43b29cf891c78a2cd01d22a2731c7da828d79e0a Mon Sep 17 00:00:00 2001 From: Stefan Reinauer Date: Fri, 6 Mar 2009 19:11:52 +0000 Subject: Fix mmconf (PCIe memory mapped config space access) support in v2. It was horribly broken and thus never used by any platform. This needs to get straightened out so current chipsets drivers can use the full feature set. Create wrapper functions similar to the io pci config space ones. Signed-off-by: Stefan Reinauer Acked-by: Myles Watson git-svn-id: svn://svn.coreboot.org/coreboot/trunk@3981 2b7e53f0-3cfb-0310-b3e9-8179ed1497e1 --- src/arch/i386/include/arch/romcc_io.h | 24 +++++++++--------- src/arch/i386/lib/pci_ops_mmconf.c | 1 + src/config/Options.lb | 7 ++++++ src/devices/pci_ops.c | 39 ++++++++++++++++++++++++++++++ src/include/device/pci_ops.h | 9 +++++++ src/northbridge/amd/amdfam10/northbridge.c | 2 +- src/northbridge/intel/i945/northbridge.c | 8 ++++-- 7 files changed, 75 insertions(+), 15 deletions(-) (limited to 'src') diff --git a/src/arch/i386/include/arch/romcc_io.h b/src/arch/i386/include/arch/romcc_io.h index 0728193a9a..aaba32ab01 100644 --- a/src/arch/i386/include/arch/romcc_io.h +++ b/src/arch/i386/include/arch/romcc_io.h @@ -105,13 +105,13 @@ static inline __attribute__((always_inline)) uint8_t pci_io_read_config8(device_ static inline __attribute__((always_inline)) uint8_t pci_mmio_read_config8(device_t dev, unsigned where) { unsigned addr; - addr = dev | where; + addr = MMCONF_BASE_ADDRESS | dev | where; return read8x(addr); } #endif static inline __attribute__((always_inline)) uint8_t pci_read_config8(device_t dev, unsigned where) { -#if MMCONF_SUPPORT +#if MMCONF_SUPPORT_DEFAULT return pci_mmio_read_config8(dev, where); #else return pci_io_read_config8(dev, where); @@ -134,14 +134,14 @@ static inline __attribute__((always_inline)) uint16_t pci_io_read_config16(devic static inline __attribute__((always_inline)) uint16_t pci_mmio_read_config16(device_t dev, unsigned where) { unsigned addr; - addr = dev | where; + addr = MMCONF_BASE_ADDRESS | dev | where; return read16x(addr); } #endif static inline __attribute__((always_inline)) uint16_t pci_read_config16(device_t dev, unsigned where) { -#if MMCONF_SUPPORT +#if MMCONF_SUPPORT_DEFAULT return pci_mmio_read_config16(dev, where); #else return pci_io_read_config16(dev, where); @@ -165,14 +165,14 @@ static inline __attribute__((always_inline)) uint32_t pci_io_read_config32(devic static inline __attribute__((always_inline)) uint32_t pci_mmio_read_config32(device_t dev, unsigned where) { unsigned addr; - addr = dev | where; + addr = MMCONF_BASE_ADDRESS | dev | where; return read32x(addr); } #endif static inline __attribute__((always_inline)) uint32_t pci_read_config32(device_t dev, unsigned where) { -#if MMCONF_SUPPORT +#if MMCONF_SUPPORT_DEFAULT return pci_mmio_read_config32(dev, where); #else return pci_io_read_config32(dev, where); @@ -195,14 +195,14 @@ static inline __attribute__((always_inline)) void pci_io_write_config8(device_t static inline __attribute__((always_inline)) void pci_mmio_write_config8(device_t dev, unsigned where, uint8_t value) { unsigned addr; - addr = dev | where; + addr = MMCONF_BASE_ADDRESS | dev | where; write8x(addr, value); } #endif static inline __attribute__((always_inline)) void pci_write_config8(device_t dev, unsigned where, uint8_t value) { -#if MMCONF_SUPPORT +#if MMCONF_SUPPORT_DEFAULT pci_mmio_write_config8(dev, where, value); #else pci_io_write_config8(dev, where, value); @@ -226,14 +226,14 @@ static inline __attribute__((always_inline)) void pci_io_write_config16(device_t static inline __attribute__((always_inline)) void pci_mmio_write_config16(device_t dev, unsigned where, uint16_t value) { unsigned addr; - addr = dev | where; + addr = MMCONF_BASE_ADDRESS | dev | where; write16x(addr, value); } #endif static inline __attribute__((always_inline)) void pci_write_config16(device_t dev, unsigned where, uint16_t value) { -#if MMCONF_SUPPORT +#if MMCONF_SUPPORT_DEFAULT pci_mmio_write_config16(dev, where, value); #else pci_io_write_config16(dev, where, value); @@ -257,14 +257,14 @@ static inline __attribute__((always_inline)) void pci_io_write_config32(device_t static inline __attribute__((always_inline)) void pci_mmio_write_config32(device_t dev, unsigned where, uint32_t value) { unsigned addr; - addr = dev | where; + addr = MMCONF_BASE_ADDRESS | dev | where; write32x(addr, value); } #endif static inline __attribute__((always_inline)) void pci_write_config32(device_t dev, unsigned where, uint32_t value) { -#if MMCONF_SUPPORT +#if MMCONF_SUPPORT_DEFAULT pci_mmio_write_config32(dev, where, value); #else pci_io_write_config32(dev, where, value); diff --git a/src/arch/i386/lib/pci_ops_mmconf.c b/src/arch/i386/lib/pci_ops_mmconf.c index 5095c31cd7..c037a7b4cd 100644 --- a/src/arch/i386/lib/pci_ops_mmconf.c +++ b/src/arch/i386/lib/pci_ops_mmconf.c @@ -13,6 +13,7 @@ */ #define PCI_MMIO_ADDR(SEGBUS, DEVFN, WHERE) ( \ + MMCONF_BASE_ADDRESS | \ (((SEGBUS) & 0xFFF) << 20) | \ (((DEVFN) & 0xFF) << 12) | \ ((WHERE) & 0xFFF)) diff --git a/src/config/Options.lb b/src/config/Options.lb index d2c47be55e..1ad1ef8ca4 100644 --- a/src/config/Options.lb +++ b/src/config/Options.lb @@ -983,6 +983,13 @@ define MMCONF_SUPPORT_DEFAULT comment "enable mmconfig for pci conf" end +define MMCONF_BASE_ADDRESS + default none + format "0x%x" + export used + comment "enable mmconfig base address" +end + define HW_MEM_HOLE_SIZEK default 0 export always diff --git a/src/devices/pci_ops.c b/src/devices/pci_ops.c index 412b0c5b4b..c6d85f284e 100644 --- a/src/devices/pci_ops.c +++ b/src/devices/pci_ops.c @@ -3,6 +3,7 @@ * * Copyright (C) 2004 Linux Networx * (Written by Eric Biederman for Linux Networx) + * Copyright (C) 2009 coresystems GmbH * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -79,3 +80,41 @@ void pci_write_config32(device_t dev, unsigned where, uint32_t val) struct bus *pbus = get_pbus(dev); ops_pci_bus(pbus)->write32(pbus, dev->bus->secondary, dev->path.pci.devfn, where, val); } + +#if MMCONF_SUPPORT +uint8_t pci_mmio_read_config8(device_t dev, unsigned where) +{ + struct bus *pbus = get_pbus(dev); + return pci_ops_mmconf.read8(pbus, dev->bus->secondary, dev->path.pci.devfn, where); +} + +uint16_t pci_mmio_read_config16(device_t dev, unsigned where) +{ + struct bus *pbus = get_pbus(dev); + return pci_ops_mmconf.read16(pbus, dev->bus->secondary, dev->path.pci.devfn, where); +} + +uint32_t pci_mmio_read_config32(device_t dev, unsigned where) +{ + struct bus *pbus = get_pbus(dev); + return pci_ops_mmconf.read32(pbus, dev->bus->secondary, dev->path.pci.devfn, where); +} + +void pci_mmio_write_config8(device_t dev, unsigned where, uint8_t val) +{ + struct bus *pbus = get_pbus(dev); + pci_ops_mmconf.write8(pbus, dev->bus->secondary, dev->path.pci.devfn, where, val); +} + +void pci_mmio_write_config16(device_t dev, unsigned where, uint16_t val) +{ + struct bus *pbus = get_pbus(dev); + pci_ops_mmconf.write16(pbus, dev->bus->secondary, dev->path.pci.devfn, where, val); +} + +void pci_mmio_write_config32(device_t dev, unsigned where, uint32_t val) +{ + struct bus *pbus = get_pbus(dev); + pci_ops_mmconf.write32(pbus, dev->bus->secondary, dev->path.pci.devfn, where, val); +} +#endif diff --git a/src/include/device/pci_ops.h b/src/include/device/pci_ops.h index 49f263fe6c..ae58fed050 100644 --- a/src/include/device/pci_ops.h +++ b/src/include/device/pci_ops.h @@ -12,4 +12,13 @@ void pci_write_config8(device_t dev, unsigned where, uint8_t val); void pci_write_config16(device_t dev, unsigned where, uint16_t val); void pci_write_config32(device_t dev, unsigned where, uint32_t val); +#if MMCONF_SUPPORT +uint8_t pci_mmio_read_config8(device_t dev, unsigned where); +uint16_t pci_mmio_read_config16(device_t dev, unsigned where); +uint32_t pci_mmio_read_config32(device_t dev, unsigned where); +void pci_mmio_write_config8(device_t dev, unsigned where, uint8_t val); +void pci_mmio_write_config16(device_t dev, unsigned where, uint16_t val); +void pci_mmio_write_config32(device_t dev, unsigned where, uint32_t val); +#endif + #endif /* PCI_OPS_H */ diff --git a/src/northbridge/amd/amdfam10/northbridge.c b/src/northbridge/amd/amdfam10/northbridge.c index 38b152c8e8..bdb743387d 100644 --- a/src/northbridge/amd/amdfam10/northbridge.c +++ b/src/northbridge/amd/amdfam10/northbridge.c @@ -1176,7 +1176,7 @@ static struct device_operations pci_domain_ops = { .enable_resources = enable_childrens_resources, .init = 0, .scan_bus = pci_domain_scan_bus, -#if MMCONF_SUPPORT +#if MMCONF_SUPPORT_DEFAULT .ops_pci_bus = &pci_ops_mmconf, #else .ops_pci_bus = &pci_cf8_conf1, diff --git a/src/northbridge/intel/i945/northbridge.c b/src/northbridge/intel/i945/northbridge.c index 9cb5cefe62..ad1d938710 100644 --- a/src/northbridge/intel/i945/northbridge.c +++ b/src/northbridge/intel/i945/northbridge.c @@ -1,7 +1,7 @@ /* * This file is part of the coreboot project. * - * Copyright (C) 2007-2008 coresystems GmbH + * Copyright (C) 2007-2009 coresystems GmbH * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -199,7 +199,11 @@ static struct device_operations pci_domain_ops = { .enable_resources = enable_childrens_resources, .init = 0, .scan_bus = pci_domain_scan_bus, - .ops_pci_bus = &pci_cf8_conf1, /* Do we want to use the memory mapped space here? */ +#if MMCONF_SUPPORT_DEFAULT + .ops_pci_bus = &pci_ops_mmconf, +#else + .ops_pci_bus = &pci_cf8_conf1, +#endif }; static void mc_read_resources(device_t dev) -- cgit v1.2.3