summaryrefslogtreecommitdiffstats
path: root/c/src/lib/libbsp/mips
diff options
context:
space:
mode:
authorSebastian Huber <sebastian.huber@embedded-brains.de>2018-04-23 12:50:58 +0200
committerSebastian Huber <sebastian.huber@embedded-brains.de>2018-04-23 15:18:45 +0200
commit5a4e3dc0a5af631b1723858bc50a9af1545392fb (patch)
treef2825a86e99fbf1982fc484278483a03728ccc3a /c/src/lib/libbsp/mips
parent6e1cf37da57769f0291740982143957fb60a43cd (diff)
downloadrtems-5a4e3dc0a5af631b1723858bc50a9af1545392fb.tar.bz2
bsps: Move PCI drivers to bsps
This patch is a part of the BSP source reorganization. Update #3285.
Diffstat (limited to 'c/src/lib/libbsp/mips')
-rw-r--r--c/src/lib/libbsp/mips/malta/Makefile.am2
-rw-r--r--c/src/lib/libbsp/mips/malta/pci/pci.c1102
2 files changed, 1 insertions, 1103 deletions
diff --git a/c/src/lib/libbsp/mips/malta/Makefile.am b/c/src/lib/libbsp/mips/malta/Makefile.am
index 3240ea9ea2..68567e3959 100644
--- a/c/src/lib/libbsp/mips/malta/Makefile.am
+++ b/c/src/lib/libbsp/mips/malta/Makefile.am
@@ -51,7 +51,7 @@ librtemsbsp_a_SOURCES += ../../../../../../bsps/mips/shared/irq/installisrentrie
librtemsbsp_a_SOURCES += ../../../../../../bsps/mips/shared/irq/isr_entries.S
# pci
-librtemsbsp_a_SOURCES += pci/pci.c
+librtemsbsp_a_SOURCES += ../../../../../../bsps/mips/malta/pci/pci.c
librtemsbsp_a_SOURCES += ../../../../../../bsps/shared/dev/pci/pci_find_device.c
#isr
diff --git a/c/src/lib/libbsp/mips/malta/pci/pci.c b/c/src/lib/libbsp/mips/malta/pci/pci.c
deleted file mode 100644
index 0932f07d35..0000000000
--- a/c/src/lib/libbsp/mips/malta/pci/pci.c
+++ /dev/null
@@ -1,1102 +0,0 @@
-/**
- * @file
- *
- * This file was based on the powerpc.
- */
-
-/*
- * COPYRIGHT (c) 1989-2012.
- * On-Line Applications Research Corporation (OAR).
- *
- * The license and distribution terms for this file may be
- * found in the file LICENSE in this distribution or at
- * http://www.rtems.org/license/LICENSE.
- */
-
-#include <rtems.h>
-#include <bsp.h>
-
-#include <bsp/pci.h>
-#include <bsp/irq.h>
-#include <rtems/bspIo.h>
-#include <rtems/endian.h>
-
-/*
- * DEFINES
- */
-
-#undef SHOW_PCI_SETTING
-
-// #define DEBUG_PCI 1
-
-/* allow for overriding these definitions */
-#ifndef PCI_CONFIG_ADDR
-#define PCI_CONFIG_ADDR 0xcf8
-#endif
-#ifndef PCI_CONFIG_DATA
-#define PCI_CONFIG_DATA 0xcfc
-#endif
-
-/* define a shortcut */
-#define pci BSP_pci_configuration
-
-#ifndef PCI_CONFIG_ADDR_VAL
-#define PCI_CONFIG_ADDR_VAL(bus, slot, funcion, offset) \
- (0x80000000|((bus)<<16)|(PCI_DEVFN((slot),(function))<<8)|(((offset)&~3)))
-#endif
-
-#ifdef DEBUG_PCI
- #define JPRINTK(fmt, ...) printk("%s: " fmt, __FUNCTION__, ##__VA_ARGS__)
-#else
- #define JPRINTK(fmt, ...)
-#endif
-
-#ifndef PCI_CONFIG_WR_ADDR
-#define PCI_CONFIG_WR_ADDR( addr, val ) out_le32((uint32_t)(addr), (val))
-#endif
-
-/* Bit encode for PCI_CONFIG_HEADER_TYPE register */
-#define PCI_CONFIG_SET_ADDR(addr, bus, slot,function,offset) \
- PCI_CONFIG_WR_ADDR( \
- (addr), \
- PCI_CONFIG_ADDR_VAL((bus), (slot), (function), (offset))\
- )
-
-#define PRINT_MSG() \
- printk("pci : Device %d:0x%02x:%d routed to interrupt_line %d\n", \
- pbus, pslot, pfun, int_name )
-
-/*
- * STRUCTURES
- */
-
-/*
- * PROTOTYPES
- */
-void print_bars(
- unsigned char slot,
- unsigned char func
-);
-int direct_pci_read_config_byte(
- unsigned char bus,
- unsigned char slot,
- unsigned char function,
- unsigned char offset,
- uint8_t *val
-);
-int direct_pci_read_config_word(
- unsigned char bus,
- unsigned char slot,
- unsigned char function,
- unsigned char offset,
- uint16_t *val
-);
-int direct_pci_read_config_dword(
- unsigned char bus,
- unsigned char slot,
- unsigned char function,
- unsigned char offset,
- uint32_t *val
-);
-int direct_pci_write_config_byte(
- unsigned char bus,
- unsigned char slot,
- unsigned char function,
- unsigned char offset,
- uint8_t val
-);
-int direct_pci_write_config_word(
- unsigned char bus,
- unsigned char slot,
- unsigned char function,
- unsigned char offset,
- uint16_t val
-);
-int direct_pci_write_config_dword(
- unsigned char bus,
- unsigned char slot,
- unsigned char function,
- unsigned char offset,
- uint32_t val
-);
-int test_intname(
- const struct _int_map *row,
- int pbus,
- int pslot,
- int pfun,
- int int_pin,
- int int_name
-);
-void pci_memory_enable(
- unsigned char bus,
- unsigned char slot,
- unsigned char function
-);
-void pci_io_enable(
- unsigned char bus,
- unsigned char slot,
- unsigned char function
-);
-void pci_busmaster_enable(
- unsigned char bus,
- unsigned char slot,
- unsigned char function
-);
-
-/*
- * GLOBALS
- */
-unsigned char ucMaxPCIBus;
-const pci_config_access_functions pci_indirect_functions = {
- indirect_pci_read_config_byte,
- indirect_pci_read_config_word,
- indirect_pci_read_config_dword,
- indirect_pci_write_config_byte,
- indirect_pci_write_config_word,
- indirect_pci_write_config_dword
-};
-
-rtems_pci_config_t BSP_pci_configuration = {
- (volatile unsigned char*)PCI_CONFIG_ADDR,
- (volatile unsigned char*)PCI_CONFIG_DATA,
- &pci_indirect_functions
-};
-
-const pci_config_access_functions pci_direct_functions = {
- direct_pci_read_config_byte,
- direct_pci_read_config_word,
- direct_pci_read_config_dword,
- direct_pci_write_config_byte,
- direct_pci_write_config_word,
- direct_pci_write_config_dword
-};
-
-/*
- * PCI specific accesses. Note these are made on 32 bit
- * boundries.
- */
-void pci_out_32(uint32_t base, uint32_t addr, uint32_t val)
-{
- volatile uint32_t *ptr;
-
- ptr = (volatile uint32_t *) (base + addr);
- *ptr = val;
-
- JPRINTK( "%p data: 0x%x\n", ptr, val);
-}
-
-void pci_out_le32(uint32_t base, uint32_t addr, uint32_t val)
-{
- volatile uint32_t *ptr;
- uint32_t data = 0;
-
- ptr = (volatile uint32_t *) (base + addr);
- rtems_uint32_to_little_endian( val, (uint8_t *) &data);
- *ptr = data;
-
- JPRINTK( "%p data: 0x%x\n", ptr, data);
-}
-
-uint8_t pci_in_8( uint32_t base, uint32_t addr ) {
- volatile uint32_t *ptr;
- uint8_t val;
- uint32_t data;
-
- data = addr/4;
- ptr = (volatile uint32_t *) (base + (data*4));
- data = *ptr;
-
- switch ( addr%4 ) {
- case 0: val = (data & 0x000000ff) >> 0; break;
- case 1: val = (data & 0x0000ff00) >> 8; break;
- case 2: val = (data & 0x00ff0000) >> 16; break;
- case 3: val = (data & 0xff000000) >> 24; break;
- }
-
- JPRINTK( "0x%x data: 0x%x raw: 0x%x\n", ptr, val, data);
-
- return val;
-}
-
-int16_t pci_in_le16( uint32_t base, uint32_t addr ) {
- volatile uint32_t *ptr;
- uint16_t val;
- uint16_t rval;
- uint32_t data;
-
- data = addr/4;
- ptr = (volatile uint32_t *) (base + (data*4));
- data = *ptr;
- if ( addr%4 == 0 )
- val = data & 0xffff;
- else
- val = (data>>16) & 0xffff;
-
- rval = rtems_uint16_from_little_endian( (uint8_t *) &val);
- JPRINTK( "0x%x data: 0x%x raw: 0x%x\n", ptr, rval, data);
- return rval;
-}
-
-int16_t pci_in_16( uint32_t base, uint32_t addr ) {
- volatile uint32_t *ptr;
- uint16_t val;
- uint32_t data;
-
- data = addr/4;
- ptr = (volatile uint32_t *) (base + (data*4));
- data = *ptr;
- if ( addr%4 == 0 )
- val = data & 0xffff;
- else
- val = (data>>16) & 0xffff;
-
- JPRINTK( "0x%x data: 0x%x raw: 0x%x\n", ptr, val, data);
- return val;
-}
-
-uint32_t pci_in_32( uint32_t base, uint32_t addr ) {
- volatile uint32_t *ptr;
- uint32_t val;
-
- ptr = (volatile uint32_t *) (base + addr);
- val = *ptr;
-
- JPRINTK( "0x%x data: 0x%x raw: 0x%x\n", ptr, val, val);
- return val;
-}
-uint32_t pci_in_le32( uint32_t base, uint32_t addr ) {
- volatile uint32_t *ptr;
- uint32_t val;
- uint32_t rval;
-
- ptr = (volatile uint32_t *) (base + addr);
- val = *ptr;
- rval = rtems_uint32_from_little_endian( (uint8_t *) &val);
-
- JPRINTK( "0x%x data: 0x%x raw: 0x%x\n", ptr, rval, val);
- return rval;
-}
-
-void pci_out_8( uint32_t base, uint32_t addr, uint8_t val ) {
- volatile uint32_t *ptr;
-
- ptr = (volatile uint32_t *) (base + addr);
- JPRINTK("Address: %p\n", ptr);
- *ptr = val;
- JPRINTK( "%p data: 0x%x\n", ptr, val);
-}
-
-void pci_out_le16( uint32_t base, uint32_t addr, uint16_t val ) {
- volatile uint32_t *ptr;
- uint32_t out_data;
- uint32_t data;
-
- ptr = (volatile uint32_t *) (base + (addr & ~0x3));
- data = *ptr;
- if ( addr%4 == 0 )
- out_data = (data & 0xffff0000) | val;
- else
- out_data = ((val << 16)&0xffff0000) | (data & 0xffff);
- rtems_uint32_to_little_endian( out_data, (uint8_t *) &data);
- *ptr = data;
-
- JPRINTK( "0x%x data: 0x%x\n", ptr, data);
-}
-
-void pci_out_16( uint32_t base, uint32_t addr, uint16_t val ) {
- volatile uint32_t *ptr;
- uint32_t out_data;
- uint32_t data;
-
- ptr = (volatile uint32_t *) (base + (addr & ~0x3));
- data = *ptr;
- if ( addr%4 == 0 )
- out_data = (data & 0xffff0000) | val;
- else
- out_data = ((val << 16)&0xffff0000) | (data & 0xffff);
- *ptr = out_data;
-
- JPRINTK( "0x%x data: 0x%x\n", ptr, out_data);
-}
-
-/*
- * INDIRECT PCI CONFIGURATION ACCESSES
- */
-int indirect_pci_read_config_byte(
- unsigned char bus,
- unsigned char slot,
- unsigned char function,
- unsigned char offset,
- uint8_t *val
-) {
-
- JPRINTK("==>\n");
- PCI_CONFIG_SET_ADDR(pci.pci_config_addr, bus, slot, function, offset);
- *val = in_8((uint32_t) (pci.pci_config_data + (offset&3)) );
- JPRINTK("\n\n");
-
- return PCIBIOS_SUCCESSFUL;
-}
-
-int indirect_pci_read_config_word(
- unsigned char bus,
- unsigned char slot,
- unsigned char function,
- unsigned char offset,
- uint16_t *val
-) {
-
- JPRINTK("==>\n");
-
- *val = 0xffff;
- if (offset&1)
- return PCIBIOS_BAD_REGISTER_NUMBER;
-
- PCI_CONFIG_SET_ADDR(pci.pci_config_addr, bus, slot, function, offset);
- *val = in_16((uint32_t)(pci.pci_config_data + (offset&3)));
-
- JPRINTK("\n\n");
-
- return PCIBIOS_SUCCESSFUL;
-}
-
-int indirect_pci_read_config_dword(
- unsigned char bus,
- unsigned char slot,
- unsigned char function,
- unsigned char offset,
- uint32_t *val
-) {
- uint32_t v;
- JPRINTK("==>\n");
-
- *val = 0xffffffff;
- if (offset&3)
- return PCIBIOS_BAD_REGISTER_NUMBER;
- PCI_CONFIG_SET_ADDR(pci.pci_config_addr, bus, slot, function, offset);
- v = in_32( (uint32_t) pci.pci_config_data );
- *val = v;
- if ( offset == 0x0b )
- JPRINTK( "%x:%x %x ==> 0x%08x, 0x%08x\n", bus, slot, function, v, *val );
-
- JPRINTK("\n\n");
-
- return PCIBIOS_SUCCESSFUL;
-}
-
-int indirect_pci_write_config_byte(
- unsigned char bus,
- unsigned char slot,
- unsigned char function,
- unsigned char offset,
- uint8_t val
-) {
-
- JPRINTK("==>\n");
-
- PCI_CONFIG_SET_ADDR(pci.pci_config_addr, bus, slot, function, offset);
- out_8( (uint32_t) (pci.pci_config_data + (offset&3)), val);
-
- JPRINTK("\n\n");
-
- return PCIBIOS_SUCCESSFUL;
-}
-
-int indirect_pci_write_config_word(
- unsigned char bus,
- unsigned char slot,
- unsigned char function,
- unsigned char offset,
- uint16_t val
-) {
-
- JPRINTK("==>\n");
-
- if (offset&1)
- return PCIBIOS_BAD_REGISTER_NUMBER;
-
- PCI_CONFIG_SET_ADDR(pci.pci_config_addr, bus, slot, function, offset);
- out_16((uint32_t)(pci.pci_config_data + (offset&3)), val);
-
- JPRINTK("\n\n");
-
- return PCIBIOS_SUCCESSFUL;
-}
-
-int indirect_pci_write_config_dword(
- unsigned char bus,
- unsigned char slot,
- unsigned char function,
- unsigned char offset,
- uint32_t val
-) {
-
- if (offset&3)
- return PCIBIOS_BAD_REGISTER_NUMBER;
-
- JPRINTK("==>\n");
-
- /*
- * The Base Address Registers get accessed big endian while the
- * other registers are little endian.
- */
- PCI_CONFIG_SET_ADDR(pci.pci_config_addr, bus, slot, function, offset);
- if ( bus == 0 && slot == 0x0b &&
- (offset >= PCI_BASE_ADDRESS_0 && offset <= PCI_BASE_ADDRESS_5) ) {
- out_32((uint32_t)pci.pci_config_data, val);
- } else {
- out_le32((uint32_t)pci.pci_config_data, val);
- }
-
- JPRINTK("\n\n");
-
- return PCIBIOS_SUCCESSFUL;
-}
-
-/*
- * DIRECT CONFIGUREATION ACCESSES.
- */
-int direct_pci_read_config_byte(
- unsigned char bus,
- unsigned char slot,
- unsigned char function,
- unsigned char offset,
- uint8_t *val
-) {
- if (bus != 0 || (1<<slot & 0xff8007fe)) {
- *val=0xff;
- return PCIBIOS_DEVICE_NOT_FOUND;
- }
-
- JPRINTK("==>\n");
-
- *val=in_8((uint32_t) (pci.pci_config_data + ((1<<slot)&~1)
- + (function<<8) + offset));
-
- JPRINTK("\n\n");
-
- return PCIBIOS_SUCCESSFUL;
-}
-
-int direct_pci_read_config_word(
- unsigned char bus,
- unsigned char slot,
- unsigned char function,
- unsigned char offset,
- uint16_t *val
-) {
- *val = 0xffff;
- if (offset&1)
- return PCIBIOS_BAD_REGISTER_NUMBER;
- if (bus != 0 || (1<<slot & 0xff8007fe))
- return PCIBIOS_DEVICE_NOT_FOUND;
-
- JPRINTK("==>\n");
-
- *val=in_le16((uint32_t)
- (pci.pci_config_data + ((1<<slot)&~1)
- + (function<<8) + offset));
-
- JPRINTK("\n\n");
-
- return PCIBIOS_SUCCESSFUL;
-}
-
-int direct_pci_read_config_dword(
- unsigned char bus,
- unsigned char slot,
- unsigned char function,
- unsigned char offset,
- uint32_t *val
-) {
- *val = 0xffffffff;
- if (offset&3)
- return PCIBIOS_BAD_REGISTER_NUMBER;
- if (bus != 0 || (1<<slot & 0xff8007fe))
- return PCIBIOS_DEVICE_NOT_FOUND;
-
- JPRINTK("==>\n");
-
- *val=in_le32((uint32_t)(pci.pci_config_data +
- ((1<<slot)&~1)+(function<<8) + offset));
-
- JPRINTK("\n\n");
-
- return PCIBIOS_SUCCESSFUL;
-}
-
-int direct_pci_write_config_byte(
- unsigned char bus,
- unsigned char slot,
- unsigned char function,
- unsigned char offset,
- uint8_t val
-) {
- if (bus != 0 || (1<<slot & 0xff8007fe))
- return PCIBIOS_DEVICE_NOT_FOUND;
-
- JPRINTK("==>\n");
-
- out_8((uint32_t) (pci.pci_config_data + ((1<<slot)&~1) +
- (function<<8) + offset),
- val);
-
- JPRINTK("\n\n");
-
- return PCIBIOS_SUCCESSFUL;
-}
-
-int direct_pci_write_config_word(
- unsigned char bus,
- unsigned char slot,
- unsigned char function,
- unsigned char offset,
- uint16_t val
-) {
- if (offset&1)
- return PCIBIOS_BAD_REGISTER_NUMBER;
- if (bus != 0 || (1<<slot & 0xff8007fe))
- return PCIBIOS_DEVICE_NOT_FOUND;
-
- JPRINTK("==>\n");
-
- out_le16((uint32_t)(pci.pci_config_data + ((1<<slot)&~1) +
- (function<<8) + offset),
- val);
-
- JPRINTK("\n\n");
-
- return PCIBIOS_SUCCESSFUL;
-}
-
-int direct_pci_write_config_dword(
- unsigned char bus,
- unsigned char slot,
- unsigned char function,
- unsigned char offset,
- uint32_t val
-) {
- if (offset&3)
- return PCIBIOS_BAD_REGISTER_NUMBER;
- if (bus != 0 || (1<<slot & 0xff8007fe))
- return PCIBIOS_DEVICE_NOT_FOUND;
-
- JPRINTK("direct_pci_write_config_dword==>\n");
-
- out_le32((uint32_t)
- (pci.pci_config_data + ((1<<slot)&~1)
- + (function<<8) + offset),
- val);
-
- JPRINTK("\n\n");
-
- return PCIBIOS_SUCCESSFUL;
-}
-
-/*
- * Validate a test interrupt name and print a warning if its not one of
- * the names defined in the routing record.
- */
-int test_intname(
- const struct _int_map *row,
- int pbus,
- int pslot,
- int pfun,
- int int_pin,
- int int_name
-) {
- int j, k;
- int _nopin= -1, _noname= -1;
-
- for (j=0; row->pin_route[j].pin > -1; j++) {
- if ( row->pin_route[j].pin == int_pin ) {
- _nopin = 0;
-
- for (k=0; k<4 && row->pin_route[j].int_name[k] > -1; k++ ) {
- if ( row->pin_route[j].int_name[k] == int_name ) {
- _noname=0; break;
- }
- }
- break;
- }
- }
-
- if( _nopin )
- {
- printk(
- "pci : Device %d:0x%02x:%d supplied a bogus interrupt_pin %d\n",
- pbus,
- pslot,
- pfun,
- int_pin
- );
- return -1;
- }
- else
- {
- if( _noname ) {
- unsigned char v = row->pin_route[j].int_name[0];
- printk(
- "pci : Device %d:0x%02x:%d supplied a suspicious interrupt_line %d, ",
- pbus,
- pslot,
- pfun,
- int_name
- );
- if ((row->opts & PCI_FIXUP_OPT_OVERRIDE_NAME) && 255 !=
- (v = row->pin_route[j].int_name[0])
- ) {
- printk("OVERRIDING with %d from fixup table\n", v);
- pci_write_config_byte(pbus,pslot,pfun,PCI_INTERRUPT_LINE,v);
- } else {
- printk("using it anyway\n");
- }
- }
- }
- return 0;
-}
-
-int FindPCIbridge( int mybus, struct pcibridge *pb )
-{
- int pbus, pslot;
- uint8_t bussec, buspri;
- uint16_t devid, vendorid, dclass;
-
- for(pbus=0; pbus< pci_bus_count(); pbus++) {
- for(pslot=0; pslot< PCI_MAX_DEVICES; pslot++) {
- pci_read_config_word(pbus, pslot, 0, PCI_DEVICE_ID, &devid);
- if ( devid == 0xffff ) continue;
-
- pci_read_config_word(pbus, pslot, 0, PCI_DEVICE_ID, &vendorid);
- if ( vendorid == 0xffff ) continue;
-
- pci_read_config_word(pbus, pslot, 0, PCI_CLASS_DEVICE, &dclass);
-
- if ( dclass == PCI_CLASS_BRIDGE_PCI ) {
- pci_read_config_byte(pbus, pslot, 0, PCI_PRIMARY_BUS, &buspri);
- pci_read_config_byte(pbus, pslot, 0, PCI_SECONDARY_BUS, &bussec);
-
- #ifdef SHOW_PCI_SETTING
- JPRINTK(
- "pci : Found bridge at %d:0x%02x, mybus %d, pribus %d, secbus %d ",
- pbus,
- pslot,
- mybus,
- buspri,
- bussec
- );
- #endif
- if ( bussec == mybus ) {
- #ifdef SHOW_PCI_SETTING
- JPRINTK("match\n");
- #endif
- /* found our nearest bridge going towards the root */
- pb->bus = pbus;
- pb->slot = pslot;
- return 0;
- }
- #ifdef SHOW_PCI_SETTING
- JPRINTK("no match\n");
- #endif
- }
-
- }
- }
- return -1;
-}
-
-void FixupPCI( const struct _int_map *bspmap, int (*swizzler)(int,int) )
-{
- unsigned char cvalue;
- uint16_t devid;
- int ismatch, i, j, pbus, pslot, pfun, int_pin, int_name, nfuns;
-
- /*
- * If the device has a non-zero INTERRUPT_PIN, assign a bsp-specific
- * INTERRUPT_NAME if one isn't already in place. Then, drivers can
- * trivially use INTERRUPT_NAME to hook up with devices.
- */
-
- for (pbus=0; pbus< pci_bus_count(); pbus++) {
- for (pslot=0; pslot< PCI_MAX_DEVICES; pslot++) {
- pci_read_config_word(pbus, pslot, 0, PCI_DEVICE_ID, &devid);
- if ( devid == 0xffff ) continue;
-
- /* got a device */
- pci_read_config_byte(pbus, pslot, 0, PCI_HEADER_TYPE, &cvalue);
- nfuns = cvalue & PCI_HEADER_TYPE_MULTI_FUNCTION ? PCI_MAX_FUNCTIONS : 1;
- for (pfun=0; pfun< nfuns; pfun++) {
-
- pci_read_config_word(pbus, pslot, pfun, PCI_DEVICE_ID, &devid);
- if( devid == 0xffff ) continue;
-
- pci_read_config_byte( pbus, pslot, pfun, PCI_INTERRUPT_PIN, &cvalue);
- int_pin = cvalue;
-
- pci_read_config_byte( pbus, pslot, pfun, PCI_INTERRUPT_LINE, &cvalue);
- int_name = cvalue;
-
- #ifdef SHOW_PCI_SETTING
- {
- unsigned short cmd,stat;
- unsigned char lat, seclat, csize;
-
- pci_read_config_word(pbus,pslot,pfun,PCI_COMMAND, &cmd );
- pci_read_config_word(pbus,pslot,pfun,PCI_STATUS, &stat );
- pci_read_config_byte(pbus,pslot,pfun,PCI_LATENCY_TIMER, &lat );
- pci_read_config_byte(pbus,pslot,pfun,PCI_SEC_LATENCY_TIMER, &seclat);
- pci_read_config_byte(pbus,pslot,pfun,PCI_CACHE_LINE_SIZE, &csize );
-
- JPRINTK(
- "pci : device %d:0x%02x:%d cmd %04X, stat %04X, latency %d, "
- " sec_latency %d, clsize %d\n",
- pbus,
- pslot,
- pfun,
- cmd,
- stat,
- lat,
- seclat,
- csize
- );
- }
- #endif
-
- if ( int_pin > 0 ) {
- ismatch = 0;
-
- /*
- * first run thru the bspmap table and see if we have an
- * explicit configuration
- */
- for (i=0; bspmap[i].bus > -1; i++) {
- if ( bspmap[i].bus == pbus && bspmap[i].slot == pslot ) {
- ismatch = -1;
-
- /* we have a record in the table that gives specific
- * pins and interrupts for devices in this slot
- */
- if ( int_name == 255 ) {
-
- /* find the vector associated with whatever pin the
- * device gives us
- */
- for ( int_name=-1, j=0; bspmap[i].pin_route[j].pin > -1; j++ ){
- if ( bspmap[i].pin_route[j].pin == int_pin ) {
- int_name = bspmap[i].pin_route[j].int_name[0];
- break;
- }
- }
-
- if ( int_name == -1 ) {
- printk(
- "pci : Unable to resolve device %d:0x%02x:%d w/ "
- "swizzled int pin %i to an interrupt_line.\n",
- pbus,
- pslot,
- pfun,
- int_pin
- );
- } else {
- PRINT_MSG();
- pci_write_config_byte(
- pbus,
- pslot,
- pfun,
- PCI_INTERRUPT_LINE,(cvalue= int_name, cvalue)
- );
- }
- } else {
- test_intname( &bspmap[i],pbus,pslot,pfun,int_pin,int_name);
- }
- break;
- }
- }
-
- if ( !ismatch ) {
- /*
- * no match, which means we're on a bus someplace. Work
- * backwards from it to one of our defined busses,
- * swizzling thru each bridge on the way.
- */
-
- /* keep pbus, pslot pointed to the device being
- * configured while we track down the bridges using
- * tbus,tslot. We keep searching the routing table because
- * we may end up finding our bridge in it
- */
-
- int tbus= pbus, tslot= pslot;
- for (;;) {
- for (i=0; bspmap[i].bus > -1; i++) {
- if ( bspmap[i].bus == tbus &&
- (bspmap[i].slot == tslot || bspmap[i].slot == -1))
- {
- ismatch = -1;
-
- /* found a record for this bus, so swizzle the
- * int_pin which we then use to find the
- * interrupt_name.
- */
- if ( int_name == 255 ) {
- /*
- * FIXME. I can't believe this little hack
- * is right. It does not yield an error in
- * convienently simple situations.
- */
- if ( tbus ) int_pin = (*swizzler)(tslot,int_pin);
-
- /*
- * int_pin points to the interrupt channel
- * this card ends up delivering interrupts
- * on. Find the int_name servicing it.
- */
- for (int_name=-1, j=0;
- bspmap[i].pin_route[j].pin > -1;
- j++)
- {
- if ( bspmap[i].pin_route[j].pin == int_pin ) {
- int_name = bspmap[i].pin_route[j].int_name[0];
- break;
- }
- }
-
- if ( int_name == -1 ) {
- printk(
- "pci : Unable to resolve device %d:0x%02x:%d w/ "
- "swizzled int pin %i to an interrupt_line.\n",
- pbus,
- pslot,
- pfun,
- int_pin
- );
- } else {
- PRINT_MSG();
- pci_write_config_byte(pbus,pslot,pfun,
- PCI_INTERRUPT_LINE,(cvalue=int_name, cvalue));
- }
- } else {
- test_intname(
- &bspmap[i],
- pbus,
- pslot,
- pfun,
- int_pin,
- int_name
- );
- }
- goto donesearch;
- }
- }
- if ( !ismatch ) {
- struct pcibridge pb;
-
- /*
- * Haven't found our bus in the int map, so work
- * upwards thru the bridges till we find it.
- */
- if ( FindPCIbridge( tbus, &pb )== 0 ) {
- int_pin = (*swizzler)(tslot,int_pin);
-
- /* our next bridge up is on pb.bus, pb.slot- now
- * instead of pointing to the device we're
- * trying to configure, we move from bridge to
- * bridge.
- */
- tbus = pb.bus;
- tslot = pb.slot;
- } else {
- printk(
- "pci : No bridge from bus %i towards root found\n",
- tbus
- );
- goto donesearch;
- }
- }
- }
- }
-
- donesearch:
- if ( !ismatch && int_pin != 0 && int_name == 255 ) {
- printk(
- "pci : Unable to match device %d:0x%02x:%d with an int "
- "routing table entry\n",
- pbus,
- pslot,
- pfun
- );
- }
- }
- }
- }
- }
-}
-
-void print_bars(
- unsigned char slot,
- unsigned char func
-)
-{
- uint32_t addr;
-
- printk( "*** BARs for slot=%d func=%d\n", slot, func );
- pci_read_config_dword (0, slot, func, PCI_BASE_ADDRESS_0, &addr);
- printk("*** PCI DEVICE BAR0: 0x%lx\n", addr);
- pci_read_config_dword (0, slot, func, PCI_BASE_ADDRESS_1, &addr);
- printk("*** PCI DEVICE BAR1: 0x%lx\n", addr);
- pci_read_config_dword (0, slot, func, PCI_BASE_ADDRESS_2, &addr);
- printk("*** PCI DEVICE BAR2: 0x%lx\n", addr);
- pci_read_config_dword (0, slot, func, PCI_BASE_ADDRESS_3, &addr);
- printk("*** PCI DEVICE BAR3: 0x%lx\n", addr);
- pci_read_config_dword (0, slot, func, PCI_BASE_ADDRESS_4, &addr);
- printk("*** PCI DEVICE BAR4: 0x%lx\n", addr);
- pci_read_config_dword (0, slot, func, PCI_BASE_ADDRESS_5, &addr);
- printk("*** PCI DEVICE BAR5: 0x%lx\n", addr);
-}
-
-void pci_memory_enable(
- unsigned char bus,
- unsigned char slot,
- unsigned char function
-)
-{
- uint16_t data;
-
- pci_read_config_word(0, slot, function, PCI_COMMAND, &data);
- data |= PCI_COMMAND_MEMORY;
- pci_write_config_word(0, slot, function, PCI_COMMAND, data );
- pci_read_config_word(0, slot, function, PCI_COMMAND, &data);
-}
-
-void pci_io_enable(
- unsigned char bus,
- unsigned char slot,
- unsigned char function
-)
-{
- uint16_t data;
-
- pci_read_config_word(0, slot, function, PCI_COMMAND, &data);
- data |= PCI_COMMAND_IO;
- pci_write_config_word(0, slot, function, PCI_COMMAND, data );
-}
-
-void pci_busmaster_enable(
- unsigned char bus,
- unsigned char slot,
- unsigned char function
-)
-{
- uint16_t data;
-
- pci_read_config_word(0, slot, function, PCI_COMMAND, &data);
- data |= PCI_COMMAND_MASTER;
- pci_write_config_word(0, slot, function, PCI_COMMAND, data );
-}
-
-/*
- * This routine determines the maximum bus number in the system
- */
-int pci_initialize(void)
-{
- unsigned char slot, func, ucNumFuncs;
- unsigned char ucHeader;
- uint32_t class;
- uint32_t device;
- uint32_t vendor;
-
- /*
- * Initialize GT_PCI0IOREMAP
- */
- pci_out_32( BSP_PCI_BASE_ADDRESS, 0xf0, 0 );
-
- /*
- * According to Linux and BSD sources, this is needed to cover up a bug
- * in some versions of the hardware.
- */
- out_le32( PCI_CONFIG_ADDR, 0x80000020 );
- out_le32( PCI_CONFIG_DATA, 0x1be00000 );
-
- /*
- * Scan PCI bus 0 looking for the known Network devices and
- * initializing the PCI for them.
- */
- for (slot=0;slot<PCI_MAX_DEVICES;slot++) {
- pci_read_config_dword(0, slot, 0, PCI_VENDOR_ID, &device);
- if (device == PCI_INVALID_VENDORDEVICEID) {
- /* This slot is empty */
- continue;
- }
-
- pci_read_config_byte(0, slot, 0, PCI_HEADER_TYPE, &ucHeader);
- if (ucHeader & PCI_HEADER_TYPE_MULTI_FUNCTION) {
- ucNumFuncs = PCI_MAX_FUNCTIONS;
- } else {
- ucNumFuncs=1;
- }
- for (func=0;func<ucNumFuncs;func++) {
- pci_read_config_dword(0, slot, func, PCI_VENDOR_ID, &device);
- if (device==PCI_INVALID_VENDORDEVICEID) {
- /* This slot/function is empty */
- continue;
- }
- vendor = device & 0xffff;
- device = device >> 16;
-
- /* This slot/function has a device fitted. */
- pci_read_config_dword(0, slot, func, PCI_CLASS_REVISION, &class);
- class >>= 16;
-
- // printk( "FOUND DEVICE 0x%04x/0x%04x class 0x%x\n",
- // vendor, device, class );
- if (class == PCI_CLASS_NETWORK_ETHERNET) {
- JPRINTK("FOUND ETHERNET\n");
-
- pci_write_config_byte(
- 0, slot, func, PCI_INTERRUPT_LINE, MALTA_IRQ_ETHERNET );
-
- /*
- * Rewrite BAR1 for RTL8139
- */
- if ( vendor == PCI_VENDOR_ID_REALTEK &&
- device == PCI_DEVICE_ID_REALTEK_8139 ) {
-
- pci_memory_enable(0, slot, func);
- pci_io_enable(0, slot, func);
- pci_busmaster_enable(0, slot, func);
-
- // BAR0: IO at 0x0000_1001
- pci_write_config_dword(0, slot, func, PCI_BASE_ADDRESS_0, 0x00001001);
-
- // BAR1: Memory at 0x1203_1000
- pci_write_config_dword(0, slot, func, PCI_BASE_ADDRESS_1, 0x12031000);
-
- // print_bars( slot, func );
- } else if ( vendor == PCI_VENDOR_ID_AMD &&
- device == PCI_DEVICE_ID_AMD_LANCE ) {
- print_bars( slot, func );
- pci_memory_enable(0, slot, func);
- pci_io_enable(0, slot, func);
- pci_busmaster_enable(0, slot, func);
-
- // BAR0: IO at 0x0000_1041
- pci_write_config_dword(0, slot, func, PCI_BASE_ADDRESS_0, 0x00001041);
-
- // BAR1: Memory at 0x1201_1020
- pci_write_config_dword(0, slot, func, PCI_BASE_ADDRESS_1, 0x12011020);
- print_bars( slot, func );
- }
-
- }
- }
- }
- return PCIB_ERR_SUCCESS;
-}
-
-/*
- * Return the number of PCI busses in the system
- */
-unsigned char pci_bus_count(void)
-{
- return (ucMaxPCIBus+1);
-}