diff options
Diffstat (limited to 'arch/m68k/mm/hwtest.c')
-rw-r--r-- | arch/m68k/mm/hwtest.c | 78 |
1 files changed, 43 insertions, 35 deletions
diff --git a/arch/m68k/mm/hwtest.c b/arch/m68k/mm/hwtest.c index 2c7dde3c6430..fb8be4dd38c4 100644 --- a/arch/m68k/mm/hwtest.c +++ b/arch/m68k/mm/hwtest.c | |||
@@ -25,29 +25,32 @@ | |||
25 | 25 | ||
26 | #include <linux/module.h> | 26 | #include <linux/module.h> |
27 | 27 | ||
28 | int hwreg_present( volatile void *regp ) | 28 | int hwreg_present(volatile void *regp) |
29 | { | 29 | { |
30 | int ret = 0; | 30 | int ret = 0; |
31 | long save_sp, save_vbr; | 31 | unsigned long flags; |
32 | long tmp_vectors[3]; | 32 | long save_sp, save_vbr; |
33 | long tmp_vectors[3]; | ||
33 | 34 | ||
34 | __asm__ __volatile__ | 35 | local_irq_save(flags); |
35 | ( "movec %/vbr,%2\n\t" | 36 | __asm__ __volatile__ ( |
36 | "movel #Lberr1,%4@(8)\n\t" | 37 | "movec %/vbr,%2\n\t" |
37 | "movec %4,%/vbr\n\t" | 38 | "movel #Lberr1,%4@(8)\n\t" |
38 | "movel %/sp,%1\n\t" | 39 | "movec %4,%/vbr\n\t" |
39 | "moveq #0,%0\n\t" | 40 | "movel %/sp,%1\n\t" |
40 | "tstb %3@\n\t" | 41 | "moveq #0,%0\n\t" |
42 | "tstb %3@\n\t" | ||
41 | "nop\n\t" | 43 | "nop\n\t" |
42 | "moveq #1,%0\n" | 44 | "moveq #1,%0\n" |
43 | "Lberr1:\n\t" | 45 | "Lberr1:\n\t" |
44 | "movel %1,%/sp\n\t" | 46 | "movel %1,%/sp\n\t" |
45 | "movec %2,%/vbr" | 47 | "movec %2,%/vbr" |
46 | : "=&d" (ret), "=&r" (save_sp), "=&r" (save_vbr) | 48 | : "=&d" (ret), "=&r" (save_sp), "=&r" (save_vbr) |
47 | : "a" (regp), "a" (tmp_vectors) | 49 | : "a" (regp), "a" (tmp_vectors) |
48 | ); | 50 | ); |
51 | local_irq_restore(flags); | ||
49 | 52 | ||
50 | return( ret ); | 53 | return ret; |
51 | } | 54 | } |
52 | EXPORT_SYMBOL(hwreg_present); | 55 | EXPORT_SYMBOL(hwreg_present); |
53 | 56 | ||
@@ -55,31 +58,36 @@ EXPORT_SYMBOL(hwreg_present); | |||
55 | * by a bus error handler. Returns 1 if successful, 0 otherwise. | 58 | * by a bus error handler. Returns 1 if successful, 0 otherwise. |
56 | */ | 59 | */ |
57 | 60 | ||
58 | int hwreg_write( volatile void *regp, unsigned short val ) | 61 | int hwreg_write(volatile void *regp, unsigned short val) |
59 | { | 62 | { |
60 | int ret; | 63 | int ret; |
61 | long save_sp, save_vbr; | 64 | unsigned long flags; |
62 | long tmp_vectors[3]; | 65 | long save_sp, save_vbr; |
66 | long tmp_vectors[3]; | ||
63 | 67 | ||
64 | __asm__ __volatile__ | 68 | local_irq_save(flags); |
65 | ( "movec %/vbr,%2\n\t" | 69 | __asm__ __volatile__ ( |
66 | "movel #Lberr2,%4@(8)\n\t" | 70 | "movec %/vbr,%2\n\t" |
67 | "movec %4,%/vbr\n\t" | 71 | "movel #Lberr2,%4@(8)\n\t" |
68 | "movel %/sp,%1\n\t" | 72 | "movec %4,%/vbr\n\t" |
69 | "moveq #0,%0\n\t" | 73 | "movel %/sp,%1\n\t" |
70 | "movew %5,%3@\n\t" | 74 | "moveq #0,%0\n\t" |
71 | "nop \n\t" /* If this nop isn't present, 'ret' may already be | 75 | "movew %5,%3@\n\t" |
72 | * loaded with 1 at the time the bus error | 76 | "nop\n\t" |
73 | * happens! */ | 77 | /* |
74 | "moveq #1,%0\n" | 78 | * If this nop isn't present, 'ret' may already be loaded |
79 | * with 1 at the time the bus error happens! | ||
80 | */ | ||
81 | "moveq #1,%0\n" | ||
75 | "Lberr2:\n\t" | 82 | "Lberr2:\n\t" |
76 | "movel %1,%/sp\n\t" | 83 | "movel %1,%/sp\n\t" |
77 | "movec %2,%/vbr" | 84 | "movec %2,%/vbr" |
78 | : "=&d" (ret), "=&r" (save_sp), "=&r" (save_vbr) | 85 | : "=&d" (ret), "=&r" (save_sp), "=&r" (save_vbr) |
79 | : "a" (regp), "a" (tmp_vectors), "g" (val) | 86 | : "a" (regp), "a" (tmp_vectors), "g" (val) |
80 | ); | 87 | ); |
88 | local_irq_restore(flags); | ||
81 | 89 | ||
82 | return( ret ); | 90 | return ret; |
83 | } | 91 | } |
84 | EXPORT_SYMBOL(hwreg_write); | 92 | EXPORT_SYMBOL(hwreg_write); |
85 | 93 | ||