Path: blob/master/arch/alpha/kernel/core_tsunami.c
10817 views
/*1* linux/arch/alpha/kernel/core_tsunami.c2*3* Based on code written by David A. Rusling ([email protected]).4*5* Code common to all TSUNAMI core logic chips.6*/78#define __EXTERN_INLINE inline9#include <asm/io.h>10#include <asm/core_tsunami.h>11#undef __EXTERN_INLINE1213#include <linux/types.h>14#include <linux/pci.h>15#include <linux/sched.h>16#include <linux/init.h>17#include <linux/bootmem.h>1819#include <asm/ptrace.h>20#include <asm/smp.h>21#include <asm/vga.h>2223#include "proto.h"24#include "pci_impl.h"2526/* Save Tsunami configuration data as the console had it set up. */2728struct29{30unsigned long wsba[4];31unsigned long wsm[4];32unsigned long tba[4];33} saved_config[2] __attribute__((common));3435/*36* NOTE: Herein lie back-to-back mb instructions. They are magic.37* One plausible explanation is that the I/O controller does not properly38* handle the system transaction. Another involves timing. Ho hum.39*/4041/*42* BIOS32-style PCI interface:43*/4445#define DEBUG_CONFIG 04647#if DEBUG_CONFIG48# define DBG_CFG(args) printk args49#else50# define DBG_CFG(args)51#endif525354/*55* Given a bus, device, and function number, compute resulting56* configuration space address57* accordingly. It is therefore not safe to have concurrent58* invocations to configuration space access routines, but there59* really shouldn't be any need for this.60*61* Note that all config space accesses use Type 1 address format.62*63* Note also that type 1 is determined by non-zero bus number.64*65* Type 1:66*67* 3 3|3 3 2 2|2 2 2 2|2 2 2 2|1 1 1 1|1 1 1 1|1 168* 3 2|1 0 9 8|7 6 5 4|3 2 1 0|9 8 7 6|5 4 3 2|1 0 9 8|7 6 5 4|3 2 1 069* +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+70* | | | | | | | | | | |B|B|B|B|B|B|B|B|D|D|D|D|D|F|F|F|R|R|R|R|R|R|0|1|71* +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+72*73* 31:24 reserved74* 23:16 bus number (8 bits = 128 possible buses)75* 15:11 Device number (5 bits)76* 10:8 function number77* 7:2 register number78*79* Notes:80* The function number selects which function of a multi-function device81* (e.g., SCSI and Ethernet).82*83* The register selects a DWORD (32 bit) register offset. Hence it84* doesn't get shifted by 2 bits as we want to "drop" the bottom two85* bits.86*/8788static int89mk_conf_addr(struct pci_bus *pbus, unsigned int device_fn, int where,90unsigned long *pci_addr, unsigned char *type1)91{92struct pci_controller *hose = pbus->sysdata;93unsigned long addr;94u8 bus = pbus->number;9596DBG_CFG(("mk_conf_addr(bus=%d ,device_fn=0x%x, where=0x%x, "97"pci_addr=0x%p, type1=0x%p)\n",98bus, device_fn, where, pci_addr, type1));99100if (!pbus->parent) /* No parent means peer PCI bus. */101bus = 0;102*type1 = (bus != 0);103104addr = (bus << 16) | (device_fn << 8) | where;105addr |= hose->config_space_base;106107*pci_addr = addr;108DBG_CFG(("mk_conf_addr: returning pci_addr 0x%lx\n", addr));109return 0;110}111112static int113tsunami_read_config(struct pci_bus *bus, unsigned int devfn, int where,114int size, u32 *value)115{116unsigned long addr;117unsigned char type1;118119if (mk_conf_addr(bus, devfn, where, &addr, &type1))120return PCIBIOS_DEVICE_NOT_FOUND;121122switch (size) {123case 1:124*value = __kernel_ldbu(*(vucp)addr);125break;126case 2:127*value = __kernel_ldwu(*(vusp)addr);128break;129case 4:130*value = *(vuip)addr;131break;132}133134return PCIBIOS_SUCCESSFUL;135}136137static int138tsunami_write_config(struct pci_bus *bus, unsigned int devfn, int where,139int size, u32 value)140{141unsigned long addr;142unsigned char type1;143144if (mk_conf_addr(bus, devfn, where, &addr, &type1))145return PCIBIOS_DEVICE_NOT_FOUND;146147switch (size) {148case 1:149__kernel_stb(value, *(vucp)addr);150mb();151__kernel_ldbu(*(vucp)addr);152break;153case 2:154__kernel_stw(value, *(vusp)addr);155mb();156__kernel_ldwu(*(vusp)addr);157break;158case 4:159*(vuip)addr = value;160mb();161*(vuip)addr;162break;163}164165return PCIBIOS_SUCCESSFUL;166}167168struct pci_ops tsunami_pci_ops =169{170.read = tsunami_read_config,171.write = tsunami_write_config,172};173174void175tsunami_pci_tbi(struct pci_controller *hose, dma_addr_t start, dma_addr_t end)176{177tsunami_pchip *pchip = hose->index ? TSUNAMI_pchip1 : TSUNAMI_pchip0;178volatile unsigned long *csr;179unsigned long value;180181/* We can invalidate up to 8 tlb entries in a go. The flush182matches against <31:16> in the pci address. */183csr = &pchip->tlbia.csr;184if (((start ^ end) & 0xffff0000) == 0)185csr = &pchip->tlbiv.csr;186187/* For TBIA, it doesn't matter what value we write. For TBI,188it's the shifted tag bits. */189value = (start & 0xffff0000) >> 12;190191*csr = value;192mb();193*csr;194}195196#ifdef NXM_MACHINE_CHECKS_ON_TSUNAMI197static long __init198tsunami_probe_read(volatile unsigned long *vaddr)199{200long dont_care, probe_result;201int cpu = smp_processor_id();202int s = swpipl(IPL_MCHECK - 1);203204mcheck_taken(cpu) = 0;205mcheck_expected(cpu) = 1;206mb();207dont_care = *vaddr;208draina();209mcheck_expected(cpu) = 0;210probe_result = !mcheck_taken(cpu);211mcheck_taken(cpu) = 0;212setipl(s);213214printk("dont_care == 0x%lx\n", dont_care);215216return probe_result;217}218219static long __init220tsunami_probe_write(volatile unsigned long *vaddr)221{222long true_contents, probe_result = 1;223224TSUNAMI_cchip->misc.csr |= (1L << 28); /* clear NXM... */225true_contents = *vaddr;226*vaddr = 0;227draina();228if (TSUNAMI_cchip->misc.csr & (1L << 28)) {229int source = (TSUNAMI_cchip->misc.csr >> 29) & 7;230TSUNAMI_cchip->misc.csr |= (1L << 28); /* ...and unlock NXS. */231probe_result = 0;232printk("tsunami_probe_write: unit %d at 0x%016lx\n", source,233(unsigned long)vaddr);234}235if (probe_result)236*vaddr = true_contents;237return probe_result;238}239#else240#define tsunami_probe_read(ADDR) 1241#endif /* NXM_MACHINE_CHECKS_ON_TSUNAMI */242243static void __init244tsunami_init_one_pchip(tsunami_pchip *pchip, int index)245{246struct pci_controller *hose;247248if (tsunami_probe_read(&pchip->pctl.csr) == 0)249return;250251hose = alloc_pci_controller();252if (index == 0)253pci_isa_hose = hose;254hose->io_space = alloc_resource();255hose->mem_space = alloc_resource();256257/* This is for userland consumption. For some reason, the 40-bit258PIO bias that we use in the kernel through KSEG didn't work for259the page table based user mappings. So make sure we get the26043-bit PIO bias. */261hose->sparse_mem_base = 0;262hose->sparse_io_base = 0;263hose->dense_mem_base264= (TSUNAMI_MEM(index) & 0xffffffffffL) | 0x80000000000L;265hose->dense_io_base266= (TSUNAMI_IO(index) & 0xffffffffffL) | 0x80000000000L;267268hose->config_space_base = TSUNAMI_CONF(index);269hose->index = index;270271hose->io_space->start = TSUNAMI_IO(index) - TSUNAMI_IO_BIAS;272hose->io_space->end = hose->io_space->start + TSUNAMI_IO_SPACE - 1;273hose->io_space->name = pci_io_names[index];274hose->io_space->flags = IORESOURCE_IO;275276hose->mem_space->start = TSUNAMI_MEM(index) - TSUNAMI_MEM_BIAS;277hose->mem_space->end = hose->mem_space->start + 0xffffffff;278hose->mem_space->name = pci_mem_names[index];279hose->mem_space->flags = IORESOURCE_MEM;280281if (request_resource(&ioport_resource, hose->io_space) < 0)282printk(KERN_ERR "Failed to request IO on hose %d\n", index);283if (request_resource(&iomem_resource, hose->mem_space) < 0)284printk(KERN_ERR "Failed to request MEM on hose %d\n", index);285286/*287* Save the existing PCI window translations. SRM will288* need them when we go to reboot.289*/290291saved_config[index].wsba[0] = pchip->wsba[0].csr;292saved_config[index].wsm[0] = pchip->wsm[0].csr;293saved_config[index].tba[0] = pchip->tba[0].csr;294295saved_config[index].wsba[1] = pchip->wsba[1].csr;296saved_config[index].wsm[1] = pchip->wsm[1].csr;297saved_config[index].tba[1] = pchip->tba[1].csr;298299saved_config[index].wsba[2] = pchip->wsba[2].csr;300saved_config[index].wsm[2] = pchip->wsm[2].csr;301saved_config[index].tba[2] = pchip->tba[2].csr;302303saved_config[index].wsba[3] = pchip->wsba[3].csr;304saved_config[index].wsm[3] = pchip->wsm[3].csr;305saved_config[index].tba[3] = pchip->tba[3].csr;306307/*308* Set up the PCI to main memory translation windows.309*310* Note: Window 3 is scatter-gather only311*312* Window 0 is scatter-gather 8MB at 8MB (for isa)313* Window 1 is scatter-gather (up to) 1GB at 1GB314* Window 2 is direct access 2GB at 2GB315*316* NOTE: we need the align_entry settings for Acer devices on ES40,317* specifically floppy and IDE when memory is larger than 2GB.318*/319hose->sg_isa = iommu_arena_new(hose, 0x00800000, 0x00800000, 0);320/* Initially set for 4 PTEs, but will be overridden to 64K for ISA. */321hose->sg_isa->align_entry = 4;322323hose->sg_pci = iommu_arena_new(hose, 0x40000000,324size_for_memory(0x40000000), 0);325hose->sg_pci->align_entry = 4; /* Tsunami caches 4 PTEs at a time */326327__direct_map_base = 0x80000000;328__direct_map_size = 0x80000000;329330pchip->wsba[0].csr = hose->sg_isa->dma_base | 3;331pchip->wsm[0].csr = (hose->sg_isa->size - 1) & 0xfff00000;332pchip->tba[0].csr = virt_to_phys(hose->sg_isa->ptes);333334pchip->wsba[1].csr = hose->sg_pci->dma_base | 3;335pchip->wsm[1].csr = (hose->sg_pci->size - 1) & 0xfff00000;336pchip->tba[1].csr = virt_to_phys(hose->sg_pci->ptes);337338pchip->wsba[2].csr = 0x80000000 | 1;339pchip->wsm[2].csr = (0x80000000 - 1) & 0xfff00000;340pchip->tba[2].csr = 0;341342pchip->wsba[3].csr = 0;343344/* Enable the Monster Window to make DAC pci64 possible. */345pchip->pctl.csr |= pctl_m_mwin;346347tsunami_pci_tbi(hose, 0, -1);348}349350351void __iomem *352tsunami_ioportmap(unsigned long addr)353{354FIXUP_IOADDR_VGA(addr);355return (void __iomem *)(addr + TSUNAMI_IO_BIAS);356}357358void __iomem *359tsunami_ioremap(unsigned long addr, unsigned long size)360{361FIXUP_MEMADDR_VGA(addr);362return (void __iomem *)(addr + TSUNAMI_MEM_BIAS);363}364365#ifndef CONFIG_ALPHA_GENERIC366EXPORT_SYMBOL(tsunami_ioportmap);367EXPORT_SYMBOL(tsunami_ioremap);368#endif369370void __init371tsunami_init_arch(void)372{373#ifdef NXM_MACHINE_CHECKS_ON_TSUNAMI374unsigned long tmp;375376/* Ho hum.. init_arch is called before init_IRQ, but we need to be377able to handle machine checks. So install the handler now. */378wrent(entInt, 0);379380/* NXMs just don't matter to Tsunami--unless they make it381choke completely. */382tmp = (unsigned long)(TSUNAMI_cchip - 1);383printk("%s: probing bogus address: 0x%016lx\n", __func__, bogus_addr);384printk("\tprobe %s\n",385tsunami_probe_write((unsigned long *)bogus_addr)386? "succeeded" : "failed");387#endif /* NXM_MACHINE_CHECKS_ON_TSUNAMI */388389#if 0390printk("%s: CChip registers:\n", __func__);391printk("%s: CSR_CSC 0x%lx\n", __func__, TSUNAMI_cchip->csc.csr);392printk("%s: CSR_MTR 0x%lx\n", __func__, TSUNAMI_cchip.mtr.csr);393printk("%s: CSR_MISC 0x%lx\n", __func__, TSUNAMI_cchip->misc.csr);394printk("%s: CSR_DIM0 0x%lx\n", __func__, TSUNAMI_cchip->dim0.csr);395printk("%s: CSR_DIM1 0x%lx\n", __func__, TSUNAMI_cchip->dim1.csr);396printk("%s: CSR_DIR0 0x%lx\n", __func__, TSUNAMI_cchip->dir0.csr);397printk("%s: CSR_DIR1 0x%lx\n", __func__, TSUNAMI_cchip->dir1.csr);398printk("%s: CSR_DRIR 0x%lx\n", __func__, TSUNAMI_cchip->drir.csr);399400printk("%s: DChip registers:\n");401printk("%s: CSR_DSC 0x%lx\n", __func__, TSUNAMI_dchip->dsc.csr);402printk("%s: CSR_STR 0x%lx\n", __func__, TSUNAMI_dchip->str.csr);403printk("%s: CSR_DREV 0x%lx\n", __func__, TSUNAMI_dchip->drev.csr);404#endif405/* With multiple PCI busses, we play with I/O as physical addrs. */406ioport_resource.end = ~0UL;407408/* Find how many hoses we have, and initialize them. TSUNAMI409and TYPHOON can have 2, but might only have 1 (DS10). */410411tsunami_init_one_pchip(TSUNAMI_pchip0, 0);412if (TSUNAMI_cchip->csc.csr & 1L<<14)413tsunami_init_one_pchip(TSUNAMI_pchip1, 1);414415/* Check for graphic console location (if any). */416find_console_vga_hose();417}418419static void420tsunami_kill_one_pchip(tsunami_pchip *pchip, int index)421{422pchip->wsba[0].csr = saved_config[index].wsba[0];423pchip->wsm[0].csr = saved_config[index].wsm[0];424pchip->tba[0].csr = saved_config[index].tba[0];425426pchip->wsba[1].csr = saved_config[index].wsba[1];427pchip->wsm[1].csr = saved_config[index].wsm[1];428pchip->tba[1].csr = saved_config[index].tba[1];429430pchip->wsba[2].csr = saved_config[index].wsba[2];431pchip->wsm[2].csr = saved_config[index].wsm[2];432pchip->tba[2].csr = saved_config[index].tba[2];433434pchip->wsba[3].csr = saved_config[index].wsba[3];435pchip->wsm[3].csr = saved_config[index].wsm[3];436pchip->tba[3].csr = saved_config[index].tba[3];437}438439void440tsunami_kill_arch(int mode)441{442tsunami_kill_one_pchip(TSUNAMI_pchip0, 0);443if (TSUNAMI_cchip->csc.csr & 1L<<14)444tsunami_kill_one_pchip(TSUNAMI_pchip1, 1);445}446447static inline void448tsunami_pci_clr_err_1(tsunami_pchip *pchip)449{450pchip->perror.csr;451pchip->perror.csr = 0x040;452mb();453pchip->perror.csr;454}455456static inline void457tsunami_pci_clr_err(void)458{459tsunami_pci_clr_err_1(TSUNAMI_pchip0);460461/* TSUNAMI and TYPHOON can have 2, but might only have 1 (DS10) */462if (TSUNAMI_cchip->csc.csr & 1L<<14)463tsunami_pci_clr_err_1(TSUNAMI_pchip1);464}465466void467tsunami_machine_check(unsigned long vector, unsigned long la_ptr)468{469/* Clear error before any reporting. */470mb();471mb(); /* magic */472draina();473tsunami_pci_clr_err();474wrmces(0x7);475mb();476477process_mcheck_info(vector, la_ptr, "TSUNAMI",478mcheck_expected(smp_processor_id()));479}480481482