This patch adds support for running on Malta boards using coreFPGA6 core cards, including support for the msc01 system controller used with them. The system controller is detected at runtime allowing one U-boot binary to run on a Malta with either. Due to the PCI I/O base differing between Maltas using gt64120 & msc01 system controllers, the UART setup is modified slightly. A second UART is added so that there is one pointing at the correct address for each system controller. The Malta board then defines its own default_serial_console function to select the correct one at runtime. The incorrect UART will simply not function. Tested on: - A coreFPGA6 Malta running interAptiv and proAptiv bitstreams, both with and without an L2 cache. - QEMU. Signed-off-by: Paul Burton <paul.burton@imgtec.com>master
parent
a257f6263b
commit
baf37f06c5
@ -0,0 +1,125 @@ |
||||
/*
|
||||
* Copyright (C) 2013 Imagination Technologies |
||||
* Author: Paul Burton <paul.burton@imgtec.com> |
||||
* |
||||
* SPDX-License-Identifier: GPL-2.0+ |
||||
*/ |
||||
|
||||
#include <common.h> |
||||
#include <msc01.h> |
||||
#include <pci.h> |
||||
#include <pci_msc01.h> |
||||
#include <asm/io.h> |
||||
|
||||
#define PCI_ACCESS_READ 0 |
||||
#define PCI_ACCESS_WRITE 1 |
||||
|
||||
struct msc01_pci_controller { |
||||
struct pci_controller hose; |
||||
void *base; |
||||
}; |
||||
|
||||
static inline struct msc01_pci_controller * |
||||
hose_to_msc01(struct pci_controller *hose) |
||||
{ |
||||
return container_of(hose, struct msc01_pci_controller, hose); |
||||
} |
||||
|
||||
static int msc01_config_access(struct msc01_pci_controller *msc01, |
||||
unsigned char access_type, pci_dev_t bdf, |
||||
int where, u32 *data) |
||||
{ |
||||
const u32 aborts = MSC01_PCI_INTSTAT_MA_MSK | MSC01_PCI_INTSTAT_TA_MSK; |
||||
void *intstat = msc01->base + MSC01_PCI_INTSTAT_OFS; |
||||
void *cfgdata = msc01->base + MSC01_PCI_CFGDATA_OFS; |
||||
unsigned int bus = PCI_BUS(bdf); |
||||
unsigned int dev = PCI_DEV(bdf); |
||||
unsigned int devfn = PCI_DEV(bdf) << 3 | PCI_FUNC(bdf); |
||||
|
||||
/* clear abort status */ |
||||
__raw_writel(aborts, intstat); |
||||
|
||||
/* setup address */ |
||||
__raw_writel((bus << MSC01_PCI_CFGADDR_BNUM_SHF) | |
||||
(dev << MSC01_PCI_CFGADDR_DNUM_SHF) | |
||||
(devfn << MSC01_PCI_CFGADDR_FNUM_SHF) | |
||||
((where / 4) << MSC01_PCI_CFGADDR_RNUM_SHF), |
||||
msc01->base + MSC01_PCI_CFGADDR_OFS); |
||||
|
||||
/* perform access */ |
||||
if (access_type == PCI_ACCESS_WRITE) |
||||
__raw_writel(*data, cfgdata); |
||||
else |
||||
*data = __raw_readl(cfgdata); |
||||
|
||||
/* check for aborts */ |
||||
if (__raw_readl(intstat) & aborts) { |
||||
/* clear abort status */ |
||||
__raw_writel(aborts, intstat); |
||||
return -1; |
||||
} |
||||
|
||||
return 0; |
||||
} |
||||
|
||||
static int msc01_read_config_dword(struct pci_controller *hose, pci_dev_t dev, |
||||
int where, u32 *value) |
||||
{ |
||||
struct msc01_pci_controller *msc01 = hose_to_msc01(hose); |
||||
|
||||
*value = 0xffffffff; |
||||
return msc01_config_access(msc01, PCI_ACCESS_READ, dev, where, value); |
||||
} |
||||
|
||||
static int msc01_write_config_dword(struct pci_controller *hose, pci_dev_t dev, |
||||
int where, u32 value) |
||||
{ |
||||
struct msc01_pci_controller *gt = hose_to_msc01(hose); |
||||
u32 data = value; |
||||
|
||||
return msc01_config_access(gt, PCI_ACCESS_WRITE, dev, where, &data); |
||||
} |
||||
|
||||
void msc01_pci_init(void *base, unsigned long sys_bus, unsigned long sys_phys, |
||||
unsigned long sys_size, unsigned long mem_bus, |
||||
unsigned long mem_phys, unsigned long mem_size, |
||||
unsigned long io_bus, unsigned long io_phys, |
||||
unsigned long io_size) |
||||
{ |
||||
static struct msc01_pci_controller global_msc01; |
||||
struct msc01_pci_controller *msc01; |
||||
struct pci_controller *hose; |
||||
|
||||
msc01 = &global_msc01; |
||||
msc01->base = base; |
||||
|
||||
hose = &msc01->hose; |
||||
|
||||
hose->first_busno = 0; |
||||
hose->last_busno = 0; |
||||
|
||||
/* System memory space */ |
||||
pci_set_region(&hose->regions[0], sys_bus, sys_phys, sys_size, |
||||
PCI_REGION_MEM | PCI_REGION_SYS_MEMORY); |
||||
|
||||
/* PCI memory space */ |
||||
pci_set_region(&hose->regions[1], mem_bus, mem_phys, mem_size, |
||||
PCI_REGION_MEM); |
||||
|
||||
/* PCI I/O space */ |
||||
pci_set_region(&hose->regions[2], io_bus, io_phys, io_size, |
||||
PCI_REGION_IO); |
||||
|
||||
hose->region_count = 3; |
||||
|
||||
pci_set_ops(hose, |
||||
pci_hose_read_config_byte_via_dword, |
||||
pci_hose_read_config_word_via_dword, |
||||
msc01_read_config_dword, |
||||
pci_hose_write_config_byte_via_dword, |
||||
pci_hose_write_config_word_via_dword, |
||||
msc01_write_config_dword); |
||||
|
||||
pci_register_hose(hose); |
||||
hose->last_busno = pci_hose_scan(hose); |
||||
} |
@ -0,0 +1,135 @@ |
||||
/*
|
||||
* Copyright (C) 2013 Imagination Technologies |
||||
* Author: Paul Burton <paul.burton@imgtec.com> |
||||
* |
||||
* SPDX-License-Identifier: GPL-2.0+ |
||||
*/ |
||||
|
||||
#ifndef __MSC01_H__ |
||||
#define __MSC01_H__ |
||||
|
||||
/*
|
||||
* Bus Interface Unit |
||||
*/ |
||||
|
||||
#define MSC01_BIU_IP1BAS1L_OFS 0x0208 |
||||
#define MSC01_BIU_IP1MSK1L_OFS 0x0218 |
||||
#define MSC01_BIU_IP1BAS2L_OFS 0x0248 |
||||
#define MSC01_BIU_IP1MSK2L_OFS 0x0258 |
||||
#define MSC01_BIU_IP2BAS1L_OFS 0x0288 |
||||
#define MSC01_BIU_IP2MSK1L_OFS 0x0298 |
||||
#define MSC01_BIU_IP2BAS2L_OFS 0x02c8 |
||||
#define MSC01_BIU_IP2MSK2L_OFS 0x02d8 |
||||
#define MSC01_BIU_IP3BAS1L_OFS 0x0308 |
||||
#define MSC01_BIU_IP3MSK1L_OFS 0x0318 |
||||
#define MSC01_BIU_IP3BAS2L_OFS 0x0348 |
||||
#define MSC01_BIU_IP3MSK2L_OFS 0x0358 |
||||
#define MSC01_BIU_MCBAS1L_OFS 0x0388 |
||||
#define MSC01_BIU_MCMSK1L_OFS 0x0398 |
||||
#define MSC01_BIU_MCBAS2L_OFS 0x03c8 |
||||
#define MSC01_BIU_MCMSK2L_OFS 0x03d8 |
||||
|
||||
/*
|
||||
* PCI Bridge |
||||
*/ |
||||
|
||||
#define MSC01_PCI_SC2PMBASL_OFS 0x0208 |
||||
#define MSC01_PCI_SC2PMMSKL_OFS 0x0218 |
||||
#define MSC01_PCI_SC2PMMAPL_OFS 0x0228 |
||||
#define MSC01_PCI_SC2PIOBASL_OFS 0x0248 |
||||
#define MSC01_PCI_SC2PIOMSKL_OFS 0x0258 |
||||
#define MSC01_PCI_SC2PIOMAPL_OFS 0x0268 |
||||
#define MSC01_PCI_P2SCMSKL_OFS 0x0308 |
||||
#define MSC01_PCI_P2SCMAPL_OFS 0x0318 |
||||
#define MSC01_PCI_INTSTAT_OFS 0x0608 |
||||
#define MSC01_PCI_CFGADDR_OFS 0x0610 |
||||
#define MSC01_PCI_CFGDATA_OFS 0x0618 |
||||
#define MSC01_PCI_HEAD0_OFS 0x2000 |
||||
#define MSC01_PCI_HEAD1_OFS 0x2008 |
||||
#define MSC01_PCI_HEAD2_OFS 0x2010 |
||||
#define MSC01_PCI_HEAD3_OFS 0x2018 |
||||
#define MSC01_PCI_HEAD4_OFS 0x2020 |
||||
#define MSC01_PCI_HEAD5_OFS 0x2028 |
||||
#define MSC01_PCI_HEAD6_OFS 0x2030 |
||||
#define MSC01_PCI_HEAD7_OFS 0x2038 |
||||
#define MSC01_PCI_HEAD8_OFS 0x2040 |
||||
#define MSC01_PCI_HEAD9_OFS 0x2048 |
||||
#define MSC01_PCI_HEAD10_OFS 0x2050 |
||||
#define MSC01_PCI_HEAD11_OFS 0x2058 |
||||
#define MSC01_PCI_HEAD12_OFS 0x2060 |
||||
#define MSC01_PCI_HEAD13_OFS 0x2068 |
||||
#define MSC01_PCI_HEAD14_OFS 0x2070 |
||||
#define MSC01_PCI_HEAD15_OFS 0x2078 |
||||
#define MSC01_PCI_BAR0_OFS 0x2220 |
||||
#define MSC01_PCI_CFG_OFS 0x2380 |
||||
#define MSC01_PCI_SWAP_OFS 0x2388 |
||||
|
||||
#define MSC01_PCI_SC2PMMSKL_MSK_MSK 0xff000000 |
||||
#define MSC01_PCI_SC2PIOMSKL_MSK_MSK 0xff000000 |
||||
|
||||
#define MSC01_PCI_INTSTAT_TA_SHF 6 |
||||
#define MSC01_PCI_INTSTAT_TA_MSK (0x1 << MSC01_PCI_INTSTAT_TA_SHF) |
||||
#define MSC01_PCI_INTSTAT_MA_SHF 7 |
||||
#define MSC01_PCI_INTSTAT_MA_MSK (0x1 << MSC01_PCI_INTSTAT_MA_SHF) |
||||
|
||||
#define MSC01_PCI_CFGADDR_BNUM_SHF 16 |
||||
#define MSC01_PCI_CFGADDR_BNUM_MSK (0xff << MSC01_PCI_CFGADDR_BNUM_SHF) |
||||
#define MSC01_PCI_CFGADDR_DNUM_SHF 11 |
||||
#define MSC01_PCI_CFGADDR_DNUM_MSK (0x1f << MSC01_PCI_CFGADDR_DNUM_SHF) |
||||
#define MSC01_PCI_CFGADDR_FNUM_SHF 8 |
||||
#define MSC01_PCI_CFGADDR_FNUM_MSK (0x3 << MSC01_PCI_CFGADDR_FNUM_SHF) |
||||
#define MSC01_PCI_CFGADDR_RNUM_SHF 2 |
||||
#define MSC01_PCI_CFGADDR_RNUM_MSK (0x3f << MSC01_PCI_CFGADDR_RNUM_SHF) |
||||
|
||||
#define MSC01_PCI_HEAD0_VENDORID_SHF 0 |
||||
#define MSC01_PCI_HEAD0_DEVICEID_SHF 16 |
||||
|
||||
#define MSC01_PCI_HEAD2_REV_SHF 0 |
||||
#define MSC01_PCI_HEAD2_CLASS_SHF 16 |
||||
|
||||
#define MSC01_PCI_CFG_EN_SHF 15 |
||||
#define MSC01_PCI_CFG_EN_MSK (0x1 << MSC01_PCI_CFG_EN_SHF) |
||||
#define MSC01_PCI_CFG_G_SHF 16 |
||||
#define MSC01_PCI_CFG_G_MSK (0x1 << MSC01_PCI_CFG_G_SHF) |
||||
#define MSC01_PCI_CFG_RA_SHF 17 |
||||
#define MSC01_PCI_CFG_RA_MSK (0x1 << MSC01_PCI_CFG_RA_SHF) |
||||
|
||||
#define MSC01_PCI_SWAP_BAR0_BSWAP_SHF 0 |
||||
#define MSC01_PCI_SWAP_IO_BSWAP_SHF 18 |
||||
|
||||
/*
|
||||
* Peripheral Bus Controller |
||||
*/ |
||||
|
||||
#define MSC01_PBC_CLKCFG_OFS 0x0100 |
||||
#define MSC01_PBC_CS0CFG_OFS 0x0400 |
||||
#define MSC01_PBC_CS0TIM_OFS 0x0500 |
||||
#define MSC01_PBC_CS0RW_OFS 0x0600 |
||||
|
||||
#define MSC01_PBC_CLKCFG_SHF 0 |
||||
#define MSC01_PBC_CLKCFG_MSK (0x1f << MSC01_PBC_CLKCFG_SHF) |
||||
|
||||
#define MSC01_PBC_CS0CFG_WS_SHF 0 |
||||
#define MSC01_PBC_CS0CFG_WS_MSK (0x1f << MSC01_PBC_CS0CFG_WS_SHF) |
||||
#define MSC01_PBC_CS0CFG_WSIDLE_SHF 8 |
||||
#define MSC01_PBC_CS0CFG_WSIDLE_MSK (0x1f << MSC01_PBC_CS0CFG_WSIDLE_SHF) |
||||
#define MSC01_PBC_CS0CFG_DTYP_SHF 16 |
||||
#define MSC01_PBC_CS0CFG_DTYP_MSK (0x3 << MSC01_PBC_CS0CFG_DTYP_SHF) |
||||
#define MSC01_PBC_CS0CFG_ADM_SHF 20 |
||||
#define MSC01_PBC_CS0CFG_ADM_MSK (0x1 << MSC01_PBC_CS0CFG_ADM_SHF) |
||||
|
||||
#define MSC01_PBC_CS0TIM_CAT_SHF 0 |
||||
#define MSC01_PBC_CS0TIM_CAT_MSK (0x1f << MSC01_PBC_CS0TIM_CAT_SHF) |
||||
#define MSC01_PBC_CS0TIM_CDT_SHF 8 |
||||
#define MSC01_PBC_CS0TIM_CDT_MSK (0x1f << MSC01_PBC_CS0TIM_CDT_SHF) |
||||
|
||||
#define MSC01_PBC_CS0RW_WAT_SHF 0 |
||||
#define MSC01_PBC_CS0RW_WAT_MSK (0x1f << MSC01_PBC_CS0RW_WAT_SHF) |
||||
#define MSC01_PBC_CS0RW_WDT_SHF 8 |
||||
#define MSC01_PBC_CS0RW_WDT_MSK (0x1f << MSC01_PBC_CS0RW_WDT_SHF) |
||||
#define MSC01_PBC_CS0RW_RAT_SHF 16 |
||||
#define MSC01_PBC_CS0RW_RAT_MSK (0x1f << MSC01_PBC_CS0RW_RAT_SHF) |
||||
#define MSC01_PBC_CS0RW_RDT_SHF 24 |
||||
#define MSC01_PBC_CS0RW_RDT_MSK (0x1f << MSC01_PBC_CS0RW_RDT_SHF) |
||||
|
||||
#endif /* __MSC01_H__ */ |
@ -0,0 +1,17 @@ |
||||
/*
|
||||
* Copyright (C) 2013 Imagination Technologies |
||||
* Author: Paul Burton <paul.burton@imgtec.com> |
||||
* |
||||
* SPDX-License-Identifier: GPL-2.0+ |
||||
*/ |
||||
|
||||
#ifndef __PCI_MSC01_H__ |
||||
#define __PCI_MSC01_H__ |
||||
|
||||
extern void msc01_pci_init(void *base, unsigned long sys_bus, |
||||
unsigned long sys_phys, unsigned long sys_size, |
||||
unsigned long mem_bus, unsigned long mem_phys, |
||||
unsigned long mem_size, unsigned long io_bus, |
||||
unsigned long io_phys, unsigned long io_size); |
||||
|
||||
#endif /* __PCI_MSC01_H__ */ |
Loading…
Reference in new issue