Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 92335
b: refs/heads/master
c: 5d750b9
h: refs/heads/master
i:
  92333: ae5a80b
  92331: 2ca2a24
  92327: f9d259d
  92319: 7352777
v: v3
  • Loading branch information
Bernd Schmidt authored and Bryan Wu committed Apr 24, 2008
1 parent 878ff64 commit 8c27bf0
Show file tree
Hide file tree
Showing 4 changed files with 41 additions and 99 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: 00d205a1ce1a24a1a9d9ebfbddbae56021cba826
refs/heads/master: 5d750b9e4f6ca7d366b4954517ff8be9ee07e1bf
15 changes: 7 additions & 8 deletions trunk/arch/blackfin/kernel/traps.c
Original file line number Diff line number Diff line change
Expand Up @@ -67,6 +67,8 @@ void __init trap_init(void)
CSYNC();
}

void *saved_icplb_fault_addr, *saved_dcplb_fault_addr;

int kstack_depth_to_print = 48;

static void decode_address(char *buf, unsigned long address)
Expand Down Expand Up @@ -703,10 +705,7 @@ void dump_bfin_mem(struct pt_regs *fp)
unsigned short *addr, *erraddr, val = 0, err = 0;
char sti = 0, buf[6];

if (unlikely((fp->seqstat & SEQSTAT_EXCAUSE) == VEC_HWERR))
erraddr = (void *)fp->pc;
else
erraddr = (void *)fp->retx;
erraddr = (void *)fp->pc;

printk(KERN_NOTICE "return address: [0x%p]; contents of:", erraddr);

Expand Down Expand Up @@ -830,9 +829,9 @@ void show_regs(struct pt_regs *fp)

if (((long)fp->seqstat & SEQSTAT_EXCAUSE) &&
(((long)fp->seqstat & SEQSTAT_EXCAUSE) != VEC_HWERR)) {
decode_address(buf, bfin_read_DCPLB_FAULT_ADDR());
decode_address(buf, saved_dcplb_fault_addr);
printk(KERN_NOTICE "DCPLB_FAULT_ADDR: %s\n", buf);
decode_address(buf, bfin_read_ICPLB_FAULT_ADDR());
decode_address(buf, saved_icplb_fault_addr);
printk(KERN_NOTICE "ICPLB_FAULT_ADDR: %s\n", buf);
}

Expand Down Expand Up @@ -940,8 +939,8 @@ void panic_cplb_error(int cplb_panic, struct pt_regs *fp)

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());
printk(KERN_EMERG "DCPLB_FAULT_ADDR=%p\n", saved_dcplb_fault_addr);
printk(KERN_EMERG "ICPLB_FAULT_ADDR=%p\n", saved_icplb_fault_addr);
dump_bfin_process(fp);
dump_bfin_mem(fp);
show_regs(fp);
Expand Down
121 changes: 33 additions & 88 deletions trunk/arch/blackfin/mach-common/entry.S
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@
#include <linux/unistd.h>
#include <asm/blackfin.h>
#include <asm/errno.h>
#include <asm/fixed_code.h>
#include <asm/thread_info.h> /* TIF_NEED_RESCHED */
#include <asm/asm-offsets.h>
#include <asm/trace.h>
Expand All @@ -52,15 +53,6 @@
# define EX_SCRATCH_REG CYCLES
#endif

#if ANOMALY_05000281
ENTRY(_safe_speculative_execution)
NOP;
NOP;
NOP;
jump _safe_speculative_execution;
ENDPROC(_safe_speculative_execution)
#endif

#ifdef CONFIG_EXCPT_IRQ_SYSC_L1
.section .l1.text
#else
Expand Down Expand Up @@ -230,6 +222,26 @@ ENTRY(_ex_trap_c)
[p4] = p5;
csync;

p4.l = lo(DCPLB_FAULT_ADDR);
p4.h = hi(DCPLB_FAULT_ADDR);
r7 = [p4];
p5.h = _saved_dcplb_fault_addr;
p5.l = _saved_dcplb_fault_addr;
[p5] = r7;

r7 = [p4 + (ICPLB_FAULT_ADDR - DCPLB_FAULT_ADDR)];
p5.h = _saved_icplb_fault_addr;
p5.l = _saved_icplb_fault_addr;
[p5] = r7;

p4.l = __retx;
p4.h = __retx;
r6 = retx;
[p4] = r6;
p4.l = lo(SAFE_USER_INSTRUCTION);
p4.h = hi(SAFE_USER_INSTRUCTION);
retx = p4;

/* Disable all interrupts, but make sure level 5 is enabled so
* we can switch to that level. Save the old mask. */
cli r6;
Expand All @@ -239,23 +251,6 @@ ENTRY(_ex_trap_c)
r6 = 0x3f;
sti r6;

/* Save the excause into a circular buffer, in case the instruction
* which caused this excecptions causes others.
*/
P5.l = _in_ptr_excause;
P5.h = _in_ptr_excause;
R7 = [P5];
R7 += 4;
R6 = 0xF;
R7 = R7 & R6;
[P5] = R7;
R6.l = _excause_circ_buf;
R6.h = _excause_circ_buf;
R7 = R7 + R6;
p5 = R7;
R6 = SEQSTAT;
[P5] = R6;

(R7:6,P5:4) = [sp++];
ASTAT = [sp++];
SP = EX_SCRATCH_REG;
Expand Down Expand Up @@ -312,6 +307,11 @@ ENDPROC(_double_fault)
ENTRY(_exception_to_level5)
SAVE_ALL_SYS

p4.l = __retx;
p4.h = __retx;
r6 = [p4];
[sp + PT_PC] = r6;

/* Restore interrupt mask. We haven't pushed RETI, so this
* doesn't enable interrupts until we return from this handler. */
p4.l = _excpt_saved_imask;
Expand All @@ -333,42 +333,11 @@ ENTRY(_exception_to_level5)
r0 = [p2]; /* Read current IPEND */
[sp + PT_IPEND] = r0; /* Store IPEND */

/* Pop the excause from the circular buffer and push it on the stack
* (in the right place - if you change the location of SEQSTAT, you
* must change this offset.
*/
.L_excep_to_5_again:
P5.l = _out_ptr_excause;
P5.h = _out_ptr_excause;
R7 = [P5];
R7 += 4;
R6 = 0xF;
R7 = R7 & R6;
[P5] = R7;
R6.l = _excause_circ_buf;
R6.h = _excause_circ_buf;
R7 = R7 + R6;
P5 = R7;
R1 = [P5];
[SP + PT_SEQSTAT] = r1;

r0 = sp; /* stack frame pt_regs pointer argument ==> r0 */
SP += -12;
call _trap_c;
SP += 12;

/* See if anything else is in the exception buffer
* if there is, process it
*/
P5.l = _out_ptr_excause;
P5.h = _out_ptr_excause;
P4.l = _in_ptr_excause;
P4.h = _in_ptr_excause;
R6 = [P5];
R7 = [P4];
CC = R6 == R7;
if ! CC JUMP .L_excep_to_5_again

call _ret_from_exception;
RESTORE_ALL_SYS
rti;
Expand Down Expand Up @@ -732,8 +701,8 @@ ENTRY(_return_from_int)
[p0] = p1;
csync;
#if ANOMALY_05000281
r0.l = _safe_speculative_execution;
r0.h = _safe_speculative_execution;
r0.l = lo(SAFE_USER_INSTRUCTION);
r0.h = hi(SAFE_USER_INSTRUCTION);
reti = r0;
#endif
r0 = 0x801f (z);
Expand All @@ -746,8 +715,8 @@ ENDPROC(_return_from_int)

ENTRY(_lower_to_irq14)
#if ANOMALY_05000281
r0.l = _safe_speculative_execution;
r0.h = _safe_speculative_execution;
r0.l = lo(SAFE_USER_INSTRUCTION);
r0.h = hi(SAFE_USER_INSTRUCTION);
reti = r0;
#endif
r0 = 0x401f;
Expand Down Expand Up @@ -814,20 +783,6 @@ _schedule_and_signal:
rti;
ENDPROC(_lower_to_irq14)

/* Make sure when we start, that the circular buffer is initialized properly
* R0 and P0 are call clobbered, so we can use them here.
*/
ENTRY(_init_exception_buff)
r0 = 0;
p0.h = _in_ptr_excause;
p0.l = _in_ptr_excause;
[p0] = r0;
p0.h = _out_ptr_excause;
p0.l = _out_ptr_excause;
[p0] = r0;
rts;
ENDPROC(_init_exception_buff)

/* We handle this 100% in exception space - to reduce overhead
* Only potiential problem is if the software buffer gets swapped out of the
* CPLB table - then double fault. - so we don't let this happen in other places
Expand Down Expand Up @@ -1403,17 +1358,7 @@ _exception_stack_top:
_last_cplb_fault_retx:
.long 0;
#endif
/*
* Single instructions can have multiple faults, which need to be
* handled by traps.c, in irq5. We store the exception cause to ensure
* we don't miss a double fault condition
*/
ENTRY(_in_ptr_excause)
.long 0;
ENTRY(_out_ptr_excause)
/* Used to save the real RETX when temporarily storing a safe
* return address. */
__retx:
.long 0;
ALIGN
ENTRY(_excause_circ_buf)
.rept 4
.long 0
.endr
2 changes: 0 additions & 2 deletions trunk/arch/blackfin/mach-common/ints-priority.c
Original file line number Diff line number Diff line change
Expand Up @@ -939,8 +939,6 @@ int __init init_arch_irq(void)

local_irq_disable();

init_exception_buff();

#ifdef CONFIG_BF54x
# ifdef CONFIG_PINTx_REASSIGN
pint[0]->assign = CONFIG_PINT0_ASSIGN;
Expand Down

0 comments on commit 8c27bf0

Please sign in to comment.