linux/arch/alpha/kernel/core_lca.c
<<
>>
Prefs
   1/*
   2 *      linux/arch/alpha/kernel/core_lca.c
   3 *
   4 * Written by David Mosberger (davidm@cs.arizona.edu) with some code
   5 * taken from Dave Rusling's (david.rusling@reo.mts.dec.com) 32-bit
   6 * bios code.
   7 *
   8 * Code common to all LCA core logic chips.
   9 */
  10
  11#define __EXTERN_INLINE inline
  12#include <asm/io.h>
  13#include <asm/core_lca.h>
  14#undef __EXTERN_INLINE
  15
  16#include <linux/types.h>
  17#include <linux/pci.h>
  18#include <linux/init.h>
  19#include <linux/tty.h>
  20
  21#include <asm/ptrace.h>
  22#include <asm/irq_regs.h>
  23#include <asm/smp.h>
  24
  25#include "proto.h"
  26#include "pci_impl.h"
  27
  28
  29/*
  30 * BIOS32-style PCI interface:
  31 */
  32
  33/*
  34 * Machine check reasons.  Defined according to PALcode sources
  35 * (osf.h and platform.h).
  36 */
  37#define MCHK_K_TPERR            0x0080
  38#define MCHK_K_TCPERR           0x0082
  39#define MCHK_K_HERR             0x0084
  40#define MCHK_K_ECC_C            0x0086
  41#define MCHK_K_ECC_NC           0x0088
  42#define MCHK_K_UNKNOWN          0x008A
  43#define MCHK_K_CACKSOFT         0x008C
  44#define MCHK_K_BUGCHECK         0x008E
  45#define MCHK_K_OS_BUGCHECK      0x0090
  46#define MCHK_K_DCPERR           0x0092
  47#define MCHK_K_ICPERR           0x0094
  48
  49
  50/*
  51 * Platform-specific machine-check reasons:
  52 */
  53#define MCHK_K_SIO_SERR         0x204   /* all platforms so far */
  54#define MCHK_K_SIO_IOCHK        0x206   /* all platforms so far */
  55#define MCHK_K_DCSR             0x208   /* all but Noname */
  56
  57
  58/*
  59 * Given a bus, device, and function number, compute resulting
  60 * configuration space address and setup the LCA_IOC_CONF register
  61 * accordingly.  It is therefore not safe to have concurrent
  62 * invocations to configuration space access routines, but there
  63 * really shouldn't be any need for this.
  64 *
  65 * Type 0:
  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 1 
  68 *  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 0
  69 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
  70 * | | | | | | | | | | | | | | | | | | | | | | | |F|F|F|R|R|R|R|R|R|0|0|
  71 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
  72 *
  73 *      31:11   Device select bit.
  74 *      10:8    Function number
  75 *       7:2    Register number
  76 *
  77 * Type 1:
  78 *
  79 *  3 3|3 3 2 2|2 2 2 2|2 2 2 2|1 1 1 1|1 1 1 1|1 1 
  80 *  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 0
  81 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
  82 * | | | | | | | | | | |B|B|B|B|B|B|B|B|D|D|D|D|D|F|F|F|R|R|R|R|R|R|0|1|
  83 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
  84 *
  85 *      31:24   reserved
  86 *      23:16   bus number (8 bits = 128 possible buses)
  87 *      15:11   Device number (5 bits)
  88 *      10:8    function number
  89 *       7:2    register number
  90 *  
  91 * Notes:
  92 *      The function number selects which function of a multi-function device 
  93 *      (e.g., SCSI and Ethernet).
  94 * 
  95 *      The register selects a DWORD (32 bit) register offset.  Hence it
  96 *      doesn't get shifted by 2 bits as we want to "drop" the bottom two
  97 *      bits.
  98 */
  99
 100static int
 101mk_conf_addr(struct pci_bus *pbus, unsigned int device_fn, int where,
 102             unsigned long *pci_addr)
 103{
 104        unsigned long addr;
 105        u8 bus = pbus->number;
 106
 107        if (bus == 0) {
 108                int device = device_fn >> 3;
 109                int func = device_fn & 0x7;
 110
 111                /* Type 0 configuration cycle.  */
 112
 113                if (device > 12) {
 114                        return -1;
 115                }
 116
 117                *(vulp)LCA_IOC_CONF = 0;
 118                addr = (1 << (11 + device)) | (func << 8) | where;
 119        } else {
 120                /* Type 1 configuration cycle.  */
 121                *(vulp)LCA_IOC_CONF = 1;
 122                addr = (bus << 16) | (device_fn << 8) | where;
 123        }
 124        *pci_addr = addr;
 125        return 0;
 126}
 127
 128static unsigned int
 129conf_read(unsigned long addr)
 130{
 131        unsigned long flags, code, stat0;
 132        unsigned int value;
 133
 134        local_irq_save(flags);
 135
 136        /* Reset status register to avoid loosing errors.  */
 137        stat0 = *(vulp)LCA_IOC_STAT0;
 138        *(vulp)LCA_IOC_STAT0 = stat0;
 139        mb();
 140
 141        /* Access configuration space.  */
 142        value = *(vuip)addr;
 143        draina();
 144
 145        stat0 = *(vulp)LCA_IOC_STAT0;
 146        if (stat0 & LCA_IOC_STAT0_ERR) {
 147                code = ((stat0 >> LCA_IOC_STAT0_CODE_SHIFT)
 148                        & LCA_IOC_STAT0_CODE_MASK);
 149                if (code != 1) {
 150                        printk("lca.c:conf_read: got stat0=%lx\n", stat0);
 151                }
 152
 153                /* Reset error status.  */
 154                *(vulp)LCA_IOC_STAT0 = stat0;
 155                mb();
 156
 157                /* Reset machine check.  */
 158                wrmces(0x7);
 159
 160                value = 0xffffffff;
 161        }
 162        local_irq_restore(flags);
 163        return value;
 164}
 165
 166static void
 167conf_write(unsigned long addr, unsigned int value)
 168{
 169        unsigned long flags, code, stat0;
 170
 171        local_irq_save(flags);  /* avoid getting hit by machine check */
 172
 173        /* Reset status register to avoid loosing errors.  */
 174        stat0 = *(vulp)LCA_IOC_STAT0;
 175        *(vulp)LCA_IOC_STAT0 = stat0;
 176        mb();
 177
 178        /* Access configuration space.  */
 179        *(vuip)addr = value;
 180        draina();
 181
 182        stat0 = *(vulp)LCA_IOC_STAT0;
 183        if (stat0 & LCA_IOC_STAT0_ERR) {
 184                code = ((stat0 >> LCA_IOC_STAT0_CODE_SHIFT)
 185                        & LCA_IOC_STAT0_CODE_MASK);
 186                if (code != 1) {
 187                        printk("lca.c:conf_write: got stat0=%lx\n", stat0);
 188                }
 189
 190                /* Reset error status.  */
 191                *(vulp)LCA_IOC_STAT0 = stat0;
 192                mb();
 193
 194                /* Reset machine check. */
 195                wrmces(0x7);
 196        }
 197        local_irq_restore(flags);
 198}
 199
 200static int
 201lca_read_config(struct pci_bus *bus, unsigned int devfn, int where,
 202                int size, u32 *value)
 203{
 204        unsigned long addr, pci_addr;
 205        long mask;
 206        int shift;
 207
 208        if (mk_conf_addr(bus, devfn, where, &pci_addr))
 209                return PCIBIOS_DEVICE_NOT_FOUND;
 210
 211        shift = (where & 3) * 8;
 212        mask = (size - 1) * 8;
 213        addr = (pci_addr << 5) + mask + LCA_CONF;
 214        *value = conf_read(addr) >> (shift);
 215        return PCIBIOS_SUCCESSFUL;
 216}
 217
 218static int 
 219lca_write_config(struct pci_bus *bus, unsigned int devfn, int where, int size,
 220                 u32 value)
 221{
 222        unsigned long addr, pci_addr;
 223        long mask;
 224
 225        if (mk_conf_addr(bus, devfn, where, &pci_addr))
 226                return PCIBIOS_DEVICE_NOT_FOUND;
 227
 228        mask = (size - 1) * 8;
 229        addr = (pci_addr << 5) + mask + LCA_CONF;
 230        conf_write(addr, value << ((where & 3) * 8));
 231        return PCIBIOS_SUCCESSFUL;
 232}
 233
 234struct pci_ops lca_pci_ops = 
 235{
 236        .read =         lca_read_config,
 237        .write =        lca_write_config,
 238};
 239
 240void
 241lca_pci_tbi(struct pci_controller *hose, dma_addr_t start, dma_addr_t end)
 242{
 243        wmb();
 244        *(vulp)LCA_IOC_TBIA = 0;
 245        mb();
 246}
 247
 248void __init
 249lca_init_arch(void)
 250{
 251        struct pci_controller *hose;
 252
 253        /*
 254         * Create our single hose.
 255         */
 256
 257        pci_isa_hose = hose = alloc_pci_controller();
 258        hose->io_space = &ioport_resource;
 259        hose->mem_space = &iomem_resource;
 260        hose->index = 0;
 261
 262        hose->sparse_mem_base = LCA_SPARSE_MEM - IDENT_ADDR;
 263        hose->dense_mem_base = LCA_DENSE_MEM - IDENT_ADDR;
 264        hose->sparse_io_base = LCA_IO - IDENT_ADDR;
 265        hose->dense_io_base = 0;
 266
 267        /*
 268         * Set up the PCI to main memory translation windows.
 269         *
 270         * Mimic the SRM settings for the direct-map window.
 271         *   Window 0 is scatter-gather 8MB at 8MB (for isa).
 272         *   Window 1 is direct access 1GB at 1GB.
 273         *
 274         * Note that we do not try to save any of the DMA window CSRs
 275         * before setting them, since we cannot read those CSRs on LCA.
 276         */
 277        hose->sg_isa = iommu_arena_new(hose, 0x00800000, 0x00800000, 0);
 278        hose->sg_pci = NULL;
 279        __direct_map_base = 0x40000000;
 280        __direct_map_size = 0x40000000;
 281
 282        *(vulp)LCA_IOC_W_BASE0 = hose->sg_isa->dma_base | (3UL << 32);
 283        *(vulp)LCA_IOC_W_MASK0 = (hose->sg_isa->size - 1) & 0xfff00000;
 284        *(vulp)LCA_IOC_T_BASE0 = virt_to_phys(hose->sg_isa->ptes);
 285
 286        *(vulp)LCA_IOC_W_BASE1 = __direct_map_base | (2UL << 32);
 287        *(vulp)LCA_IOC_W_MASK1 = (__direct_map_size - 1) & 0xfff00000;
 288        *(vulp)LCA_IOC_T_BASE1 = 0;
 289
 290        *(vulp)LCA_IOC_TB_ENA = 0x80;
 291
 292        lca_pci_tbi(hose, 0, -1);
 293
 294        /*
 295         * Disable PCI parity for now.  The NCR53c810 chip has
 296         * troubles meeting the PCI spec which results in
 297         * data parity errors.
 298         */
 299        *(vulp)LCA_IOC_PAR_DIS = 1UL<<5;
 300
 301        /*
 302         * Finally, set up for restoring the correct HAE if using SRM.
 303         * Again, since we cannot read many of the CSRs on the LCA,
 304         * one of which happens to be the HAE, we save the value that
 305         * the SRM will expect...
 306         */
 307        if (alpha_using_srm)
 308                srm_hae = 0x80000000UL;
 309}
 310
 311/*
 312 * Constants used during machine-check handling.  I suppose these
 313 * could be moved into lca.h but I don't see much reason why anybody
 314 * else would want to use them.
 315 */
 316
 317#define ESR_EAV         (1UL<< 0)       /* error address valid */
 318#define ESR_CEE         (1UL<< 1)       /* correctable error */
 319#define ESR_UEE         (1UL<< 2)       /* uncorrectable error */
 320#define ESR_WRE         (1UL<< 3)       /* write-error */
 321#define ESR_SOR         (1UL<< 4)       /* error source */
 322#define ESR_CTE         (1UL<< 7)       /* cache-tag error */
 323#define ESR_MSE         (1UL<< 9)       /* multiple soft errors */
 324#define ESR_MHE         (1UL<<10)       /* multiple hard errors */
 325#define ESR_NXM         (1UL<<12)       /* non-existent memory */
 326
 327#define IOC_ERR         (  1<<4)        /* ioc logs an error */
 328#define IOC_CMD_SHIFT   0
 329#define IOC_CMD         (0xf<<IOC_CMD_SHIFT)
 330#define IOC_CODE_SHIFT  8
 331#define IOC_CODE        (0xf<<IOC_CODE_SHIFT)
 332#define IOC_LOST        (  1<<5)
 333#define IOC_P_NBR       ((__u32) ~((1<<13) - 1))
 334
 335static void
 336mem_error(unsigned long esr, unsigned long ear)
 337{
 338        printk("    %s %s error to %s occurred at address %x\n",
 339               ((esr & ESR_CEE) ? "Correctable" :
 340                (esr & ESR_UEE) ? "Uncorrectable" : "A"),
 341               (esr & ESR_WRE) ? "write" : "read",
 342               (esr & ESR_SOR) ? "memory" : "b-cache",
 343               (unsigned) (ear & 0x1ffffff8));
 344        if (esr & ESR_CTE) {
 345                printk("    A b-cache tag parity error was detected.\n");
 346        }
 347        if (esr & ESR_MSE) {
 348                printk("    Several other correctable errors occurred.\n");
 349        }
 350        if (esr & ESR_MHE) {
 351                printk("    Several other uncorrectable errors occurred.\n");
 352        }
 353        if (esr & ESR_NXM) {
 354                printk("    Attempted to access non-existent memory.\n");
 355        }
 356}
 357
 358static void
 359ioc_error(__u32 stat0, __u32 stat1)
 360{
 361        static const char * const pci_cmd[] = {
 362                "Interrupt Acknowledge", "Special", "I/O Read", "I/O Write",
 363                "Rsvd 1", "Rsvd 2", "Memory Read", "Memory Write", "Rsvd3",
 364                "Rsvd4", "Configuration Read", "Configuration Write",
 365                "Memory Read Multiple", "Dual Address", "Memory Read Line",
 366                "Memory Write and Invalidate"
 367        };
 368        static const char * const err_name[] = {
 369                "exceeded retry limit", "no device", "bad data parity",
 370                "target abort", "bad address parity", "page table read error",
 371                "invalid page", "data error"
 372        };
 373        unsigned code = (stat0 & IOC_CODE) >> IOC_CODE_SHIFT;
 374        unsigned cmd  = (stat0 & IOC_CMD)  >> IOC_CMD_SHIFT;
 375
 376        printk("    %s initiated PCI %s cycle to address %x"
 377               " failed due to %s.\n",
 378               code > 3 ? "PCI" : "CPU", pci_cmd[cmd], stat1, err_name[code]);
 379
 380        if (code == 5 || code == 6) {
 381                printk("    (Error occurred at PCI memory address %x.)\n",
 382                       (stat0 & ~IOC_P_NBR));
 383        }
 384        if (stat0 & IOC_LOST) {
 385                printk("    Other PCI errors occurred simultaneously.\n");
 386        }
 387}
 388
 389void
 390lca_machine_check(unsigned long vector, unsigned long la_ptr)
 391{
 392        const char * reason;
 393        union el_lca el;
 394
 395        el.c = (struct el_common *) la_ptr;
 396
 397        wrmces(rdmces());       /* reset machine check pending flag */
 398
 399        printk(KERN_CRIT "LCA machine check: vector=%#lx pc=%#lx code=%#x\n",
 400               vector, get_irq_regs()->pc, (unsigned int) el.c->code);
 401
 402        /*
 403         * The first quadword after the common header always seems to
 404         * be the machine check reason---don't know why this isn't
 405         * part of the common header instead.  In the case of a long
 406         * logout frame, the upper 32 bits is the machine check
 407         * revision level, which we ignore for now.
 408         */
 409        switch ((unsigned int) el.c->code) {
 410        case MCHK_K_TPERR:      reason = "tag parity error"; break;
 411        case MCHK_K_TCPERR:     reason = "tag control parity error"; break;
 412        case MCHK_K_HERR:       reason = "access to non-existent memory"; break;
 413        case MCHK_K_ECC_C:      reason = "correctable ECC error"; break;
 414        case MCHK_K_ECC_NC:     reason = "non-correctable ECC error"; break;
 415        case MCHK_K_CACKSOFT:   reason = "MCHK_K_CACKSOFT"; break;
 416        case MCHK_K_BUGCHECK:   reason = "illegal exception in PAL mode"; break;
 417        case MCHK_K_OS_BUGCHECK: reason = "callsys in kernel mode"; break;
 418        case MCHK_K_DCPERR:     reason = "d-cache parity error"; break;
 419        case MCHK_K_ICPERR:     reason = "i-cache parity error"; break;
 420        case MCHK_K_SIO_SERR:   reason = "SIO SERR occurred on PCI bus"; break;
 421        case MCHK_K_SIO_IOCHK:  reason = "SIO IOCHK occurred on ISA bus"; break;
 422        case MCHK_K_DCSR:       reason = "MCHK_K_DCSR"; break;
 423        case MCHK_K_UNKNOWN:
 424        default:                reason = "unknown"; break;
 425        }
 426
 427        switch (el.c->size) {
 428        case sizeof(struct el_lca_mcheck_short):
 429                printk(KERN_CRIT
 430                       "  Reason: %s (short frame%s, dc_stat=%#lx):\n",
 431                       reason, el.c->retry ? ", retryable" : "",
 432                       el.s->dc_stat);
 433                if (el.s->esr & ESR_EAV) {
 434                        mem_error(el.s->esr, el.s->ear);
 435                }
 436                if (el.s->ioc_stat0 & IOC_ERR) {
 437                        ioc_error(el.s->ioc_stat0, el.s->ioc_stat1);
 438                }
 439                break;
 440
 441        case sizeof(struct el_lca_mcheck_long):
 442                printk(KERN_CRIT "  Reason: %s (long frame%s):\n",
 443                       reason, el.c->retry ? ", retryable" : "");
 444                printk(KERN_CRIT
 445                       "    reason: %#lx  exc_addr: %#lx  dc_stat: %#lx\n", 
 446                       el.l->pt[0], el.l->exc_addr, el.l->dc_stat);
 447                printk(KERN_CRIT "    car: %#lx\n", el.l->car);
 448                if (el.l->esr & ESR_EAV) {
 449                        mem_error(el.l->esr, el.l->ear);
 450                }
 451                if (el.l->ioc_stat0 & IOC_ERR) {
 452                        ioc_error(el.l->ioc_stat0, el.l->ioc_stat1);
 453                }
 454                break;
 455
 456        default:
 457                printk(KERN_CRIT "  Unknown errorlog size %d\n", el.c->size);
 458        }
 459
 460        /* Dump the logout area to give all info.  */
 461#ifdef CONFIG_VERBOSE_MCHECK
 462        if (alpha_verbose_mcheck > 1) {
 463                unsigned long * ptr = (unsigned long *) la_ptr;
 464                long i;
 465                for (i = 0; i < el.c->size / sizeof(long); i += 2) {
 466                        printk(KERN_CRIT " +%8lx %016lx %016lx\n",
 467                               i*sizeof(long), ptr[i], ptr[i+1]);
 468                }
 469        }
 470#endif /* CONFIG_VERBOSE_MCHECK */
 471}
 472
 473/*
 474 * The following routines are needed to support the SPEED changing
 475 * necessary to successfully manage the thermal problem on the AlphaBook1.
 476 */
 477
 478void
 479lca_clock_print(void)
 480{
 481        long    pmr_reg;
 482
 483        pmr_reg = LCA_READ_PMR;
 484
 485        printk("Status of clock control:\n");
 486        printk("\tPrimary clock divisor\t0x%lx\n", LCA_GET_PRIMARY(pmr_reg));
 487        printk("\tOverride clock divisor\t0x%lx\n", LCA_GET_OVERRIDE(pmr_reg));
 488        printk("\tInterrupt override is %s\n",
 489               (pmr_reg & LCA_PMR_INTO) ? "on" : "off"); 
 490        printk("\tDMA override is %s\n",
 491               (pmr_reg & LCA_PMR_DMAO) ? "on" : "off"); 
 492
 493}
 494
 495int
 496lca_get_clock(void)
 497{
 498        long    pmr_reg;
 499
 500        pmr_reg = LCA_READ_PMR;
 501        return(LCA_GET_PRIMARY(pmr_reg));
 502
 503}
 504
 505void
 506lca_clock_fiddle(int divisor)
 507{
 508        long    pmr_reg;
 509
 510        pmr_reg = LCA_READ_PMR;
 511        LCA_SET_PRIMARY_CLOCK(pmr_reg, divisor);
 512        /* lca_norm_clock = divisor; */
 513        LCA_WRITE_PMR(pmr_reg);
 514        mb();
 515}
 516