| /* | |
| * linux/arch/unicore32/include/asm/assembler.h | |
| * | |
| * Code specific to PKUnity SoC and UniCore ISA | |
| * | |
| * Copyright (C) 2001-2010 GUAN Xue-tao | |
| * | |
| * This program is free software; you can redistribute it and/or modify | |
| * it under the terms of the GNU General Public License version 2 as | |
| * published by the Free Software Foundation. | |
| * | |
| * Do not include any C declarations in this file - it is included by | |
| * assembler source. | |
| */ | |
| #ifndef __ASSEMBLY__ | |
| #error "Only include this from assembly code" | |
| #endif | |
| #include <asm/ptrace.h> | |
| /* | |
| * Little Endian independent macros for shifting bytes within registers. | |
| */ | |
| #define pull >> | |
| #define push << | |
| #define get_byte_0 << #0 | |
| #define get_byte_1 >> #8 | |
| #define get_byte_2 >> #16 | |
| #define get_byte_3 >> #24 | |
| #define put_byte_0 << #0 | |
| #define put_byte_1 << #8 | |
| #define put_byte_2 << #16 | |
| #define put_byte_3 << #24 | |
| #define cadd cmpadd | |
| #define cand cmpand | |
| #define csub cmpsub | |
| #define cxor cmpxor | |
| /* | |
| * Enable and disable interrupts | |
| */ | |
| .macro disable_irq, temp | |
| mov \temp, asr | |
| andn \temp, \temp, #0xFF | |
| or \temp, \temp, #PSR_I_BIT | PRIV_MODE | |
| mov.a asr, \temp | |
| .endm | |
| .macro enable_irq, temp | |
| mov \temp, asr | |
| andn \temp, \temp, #0xFF | |
| or \temp, \temp, #PRIV_MODE | |
| mov.a asr, \temp | |
| .endm | |
| #define USER(x...) \ | |
| 9999: x; \ | |
| .pushsection __ex_table, "a"; \ | |
| .align 3; \ | |
| .long 9999b, 9001f; \ | |
| .popsection | |
| .macro notcond, cond, nexti = .+8 | |
| .ifc \cond, eq | |
| bne \nexti | |
| .else; .ifc \cond, ne | |
| beq \nexti | |
| .else; .ifc \cond, ea | |
| bub \nexti | |
| .else; .ifc \cond, ub | |
| bea \nexti | |
| .else; .ifc \cond, fs | |
| bns \nexti | |
| .else; .ifc \cond, ns | |
| bfs \nexti | |
| .else; .ifc \cond, fv | |
| bnv \nexti | |
| .else; .ifc \cond, nv | |
| bfv \nexti | |
| .else; .ifc \cond, ua | |
| beb \nexti | |
| .else; .ifc \cond, eb | |
| bua \nexti | |
| .else; .ifc \cond, eg | |
| bsl \nexti | |
| .else; .ifc \cond, sl | |
| beg \nexti | |
| .else; .ifc \cond, sg | |
| bel \nexti | |
| .else; .ifc \cond, el | |
| bsg \nexti | |
| .else; .ifnc \cond, al | |
| .error "Unknown cond in notcond macro argument" | |
| .endif; .endif; .endif; .endif; .endif; .endif; .endif | |
| .endif; .endif; .endif; .endif; .endif; .endif; .endif | |
| .endif | |
| .endm | |
| .macro usracc, instr, reg, ptr, inc, cond, rept, abort | |
| .rept \rept | |
| notcond \cond, .+8 | |
| 9999 : | |
| .if \inc == 1 | |
| \instr\()b.u \reg, [\ptr], #\inc | |
| .elseif \inc == 4 | |
| \instr\()w.u \reg, [\ptr], #\inc | |
| .else | |
| .error "Unsupported inc macro argument" | |
| .endif | |
| .pushsection __ex_table, "a" | |
| .align 3 | |
| .long 9999b, \abort | |
| .popsection | |
| .endr | |
| .endm | |
| .macro strusr, reg, ptr, inc, cond = al, rept = 1, abort = 9001f | |
| usracc st, \reg, \ptr, \inc, \cond, \rept, \abort | |
| .endm | |
| .macro ldrusr, reg, ptr, inc, cond = al, rept = 1, abort = 9001f | |
| usracc ld, \reg, \ptr, \inc, \cond, \rept, \abort | |
| .endm | |
| .macro nop8 | |
| .rept 8 | |
| nop | |
| .endr | |
| .endm |