void panic_cplb_error(int cplb_panic, struct pt_regs *fp) { switch (cplb_panic) { case CPLB_NO_UNLOCKED: printk(KERN_EMERG "All CPLBs are locked\n"); break; case CPLB_PROT_VIOL: return; case CPLB_NO_ADDR_MATCH: return; case CPLB_UNKNOWN_ERR: printk(KERN_EMERG "Unknown CPLB Exception\n"); break; } oops_in_progress = 1; printk(KERN_EMERG "DCPLB_FAULT_ADDR=%p\n", (void *)bfin_read_DCPLB_FAULT_ADDR()); printk(KERN_EMERG "ICPLB_FAULT_ADDR=%p\n", (void *)bfin_read_ICPLB_FAULT_ADDR()); dump_bfin_process(fp); dump_bfin_mem((void *)fp->retx); show_regs(fp); dump_stack(); panic("Unrecoverable event\n"); }
void show_regs(struct pt_regs *fp) { char buf [150]; printk(KERN_NOTICE "\n" KERN_NOTICE "SEQUENCER STATUS:\n"); printk(KERN_NOTICE " SEQSTAT: %08lx IPEND: %04lx SYSCFG: %04lx\n", (long)fp->seqstat, fp->ipend, fp->syscfg); decode_address(buf, fp->rete); printk(KERN_NOTICE " RETE: %s\n", buf); decode_address(buf, fp->retn); printk(KERN_NOTICE " RETN: %s\n", buf); decode_address(buf, fp->retx); printk(KERN_NOTICE " RETX: %s\n", buf); decode_address(buf, fp->rets); printk(KERN_NOTICE " RETS: %s\n", buf); decode_address(buf, fp->pc); printk(KERN_NOTICE " PC: %s\n", buf); if ((long)fp->seqstat & SEQSTAT_EXCAUSE) { decode_address(buf, bfin_read_DCPLB_FAULT_ADDR()); printk(KERN_NOTICE "DCPLB_FAULT_ADDR: %s\n", buf); decode_address(buf, bfin_read_ICPLB_FAULT_ADDR()); printk(KERN_NOTICE "ICPLB_FAULT_ADDR: %s\n", buf); } printk(KERN_NOTICE "\n" KERN_NOTICE "PROCESSOR STATE:\n"); printk(KERN_NOTICE " R0 : %08lx R1 : %08lx R2 : %08lx R3 : %08lx\n", fp->r0, fp->r1, fp->r2, fp->r3); printk(KERN_NOTICE " R4 : %08lx R5 : %08lx R6 : %08lx R7 : %08lx\n", fp->r4, fp->r5, fp->r6, fp->r7); printk(KERN_NOTICE " P0 : %08lx P1 : %08lx P2 : %08lx P3 : %08lx\n", fp->p0, fp->p1, fp->p2, fp->p3); printk(KERN_NOTICE " P4 : %08lx P5 : %08lx FP : %08lx SP : %08lx\n", fp->p4, fp->p5, fp->fp, (long)fp); printk(KERN_NOTICE " LB0: %08lx LT0: %08lx LC0: %08lx\n", fp->lb0, fp->lt0, fp->lc0); printk(KERN_NOTICE " LB1: %08lx LT1: %08lx LC1: %08lx\n", fp->lb1, fp->lt1, fp->lc1); printk(KERN_NOTICE " B0 : %08lx L0 : %08lx M0 : %08lx I0 : %08lx\n", fp->b0, fp->l0, fp->m0, fp->i0); printk(KERN_NOTICE " B1 : %08lx L1 : %08lx M1 : %08lx I1 : %08lx\n", fp->b1, fp->l1, fp->m1, fp->i1); printk(KERN_NOTICE " B2 : %08lx L2 : %08lx M2 : %08lx I2 : %08lx\n", fp->b2, fp->l2, fp->m2, fp->i2); printk(KERN_NOTICE " B3 : %08lx L3 : %08lx M3 : %08lx I3 : %08lx\n", fp->b3, fp->l3, fp->m3, fp->i3); printk(KERN_NOTICE "A0.w: %08lx A0.x: %08lx A1.w: %08lx A1.x: %08lx\n", fp->a0w, fp->a0x, fp->a1w, fp->a1x); printk(KERN_NOTICE "USP : %08lx ASTAT: %08lx\n", rdusp(), fp->astat); printk(KERN_NOTICE "\n"); }
MGR_ATTR static int dcplb_miss(int cpu) { unsigned long addr = bfin_read_DCPLB_FAULT_ADDR(); int status = bfin_read_DCPLB_STATUS(); int idx; unsigned long d_data, base, addr1, eaddr; nr_dcplb_miss[cpu]++; if (unlikely(status & FAULT_USERSUPV)) nr_dcplb_supv_miss[cpu]++; base = 0; idx = 0; do { eaddr = dcplb_bounds[idx].eaddr; if (addr < eaddr) break; base = eaddr; } while (++idx < dcplb_nr_bounds); if (unlikely(idx == dcplb_nr_bounds)) return CPLB_NO_ADDR_MATCH; d_data = dcplb_bounds[idx].data; if (unlikely(d_data == 0)) return CPLB_NO_ADDR_MATCH; addr1 = addr & ~(SIZE_4M - 1); addr &= ~(SIZE_1M - 1); d_data |= PAGE_SIZE_1MB; if (addr1 >= base && (addr1 + SIZE_4M) <= eaddr) { /* * This works because * (PAGE_SIZE_4MB & PAGE_SIZE_1MB) == PAGE_SIZE_1MB. */ d_data |= PAGE_SIZE_4MB; addr = addr1; } /* Pick entry to evict */ idx = evict_one_dcplb(cpu); write_dcplb_data(cpu, idx, d_data, addr); return CPLB_RELOADED; }
MGR_ATTR static noinline int dcplb_miss(unsigned int cpu) { unsigned long addr = bfin_read_DCPLB_FAULT_ADDR(); int status = bfin_read_DCPLB_STATUS(); unsigned long *mask; int idx; unsigned long d_data; nr_dcplb_miss[cpu]++; d_data = CPLB_SUPV_WR | CPLB_VALID | CPLB_DIRTY | PAGE_SIZE_4KB; #ifdef CONFIG_BFIN_EXTMEM_DCACHEABLE if (bfin_addr_dcacheable(addr)) { d_data |= CPLB_L1_CHBL | ANOMALY_05000158_WORKAROUND; # ifdef CONFIG_BFIN_EXTMEM_WRITETHROUGH d_data |= CPLB_L1_AOW | CPLB_WT; # endif } #endif if (L2_LENGTH && addr >= L2_START && addr < L2_START + L2_LENGTH) { addr = L2_START; d_data = L2_DMEMORY; } else if (addr >= physical_mem_end) { if (addr >= ASYNC_BANK0_BASE && addr < ASYNC_BANK3_BASE + ASYNC_BANK3_SIZE) { #if defined(CONFIG_ROMFS_ON_MTD) && defined(CONFIG_MTD_ROM) mask = current_rwx_mask[cpu]; if (mask) { int page = (addr - (ASYNC_BANK0_BASE - _ramend)) >> PAGE_SHIFT; int idx = page >> 5; int bit = 1 << (page & 31); if (mask[idx] & bit) d_data |= CPLB_USER_RD; } #endif } else if (addr >= BOOT_ROM_START && addr < BOOT_ROM_START + BOOT_ROM_LENGTH