100f892fcSMacpaul Lin /* 200f892fcSMacpaul Lin * include/asm-nds32/macro.h 300f892fcSMacpaul Lin * 400f892fcSMacpaul Lin * Copyright (C) 2009 Jean-Christophe PLAGNIOL-VILLARD <plagnioj@jcrosoft.com> 500f892fcSMacpaul Lin * Copyright (C) 2011 Andes Technology Corporation 600f892fcSMacpaul Lin * Macpaul Lin, Andes Technology Corporation <macpaul@andestech.com> 700f892fcSMacpaul Lin * 81a459660SWolfgang Denk * SPDX-License-Identifier: GPL-2.0+ 900f892fcSMacpaul Lin */ 1000f892fcSMacpaul Lin 1100f892fcSMacpaul Lin #ifndef __ASM_NDS_MACRO_H 1200f892fcSMacpaul Lin #define __ASM_NDS_MACRO_H 1300f892fcSMacpaul Lin #ifdef __ASSEMBLY__ 1400f892fcSMacpaul Lin 1500f892fcSMacpaul Lin /* 1600f892fcSMacpaul Lin * These macros provide a convenient way to write 8, 16 and 32 bit data 1700f892fcSMacpaul Lin * to an "immediate address (address used by periphal)" only. 1800f892fcSMacpaul Lin * Registers r4 and r5 are used, any data in these registers are 1900f892fcSMacpaul Lin * overwritten by the macros. 2000f892fcSMacpaul Lin * The macros are valid for any NDS32 architecture, they do not implement 2100f892fcSMacpaul Lin * any memory barriers so caution is recommended when using these when the 2200f892fcSMacpaul Lin * caches are enabled or on a multi-core system. 2300f892fcSMacpaul Lin */ 2400f892fcSMacpaul Lin 2500f892fcSMacpaul Lin .macro write32, addr, data 26*b19cc6bfSrick li $r4, \addr 27*b19cc6bfSrick li $r5, \data 2800f892fcSMacpaul Lin swi $r5, [$r4] 2900f892fcSMacpaul Lin .endm 3000f892fcSMacpaul Lin 3100f892fcSMacpaul Lin .macro write16, addr, data 32*b19cc6bfSrick li $r4, \addr 33*b19cc6bfSrick li $r5, \data 3400f892fcSMacpaul Lin shi $r5, [$r4] 3500f892fcSMacpaul Lin .endm 3600f892fcSMacpaul Lin 3700f892fcSMacpaul Lin .macro write8, addr, data 38*b19cc6bfSrick li $r4, \addr 39*b19cc6bfSrick li $r5, \data 4000f892fcSMacpaul Lin sbi $r5, [$r4] 4100f892fcSMacpaul Lin .endm 4200f892fcSMacpaul Lin 4300f892fcSMacpaul Lin /* 4400f892fcSMacpaul Lin * This macro read a value from a register, then do OR operation 4500f892fcSMacpaul Lin * (set bit fields) to the value, and then store it back to the register. 4600f892fcSMacpaul Lin * Note: Instruction 'ori' supports immediate value up to 15 bits. 4700f892fcSMacpaul Lin */ 4800f892fcSMacpaul Lin .macro setbf32, addr, data 49*b19cc6bfSrick li $r4, \addr 5000f892fcSMacpaul Lin lwi $r5, [$r4] 51*b19cc6bfSrick li $r6, \data 5200f892fcSMacpaul Lin or $r5, $r5, $r6 5300f892fcSMacpaul Lin swi $r5, [$r4] 5400f892fcSMacpaul Lin .endm 5500f892fcSMacpaul Lin 5600f892fcSMacpaul Lin .macro setbf15, addr, data 57*b19cc6bfSrick li $r4, \addr 5800f892fcSMacpaul Lin lwi $r5, [$r4] 59*b19cc6bfSrick ori $r5, $r5, \data 6000f892fcSMacpaul Lin swi $r5, [$r4] 6100f892fcSMacpaul Lin .endm 6200f892fcSMacpaul Lin 6300f892fcSMacpaul Lin /* 6400f892fcSMacpaul Lin * This macro generates a loop that can be used for delays in the code. 6500f892fcSMacpaul Lin * Register r4 is used, any data in this register is overwritten by the 6600f892fcSMacpaul Lin * macro. 6700f892fcSMacpaul Lin * The macro is valid for any NDS32 architeture. The actual time spent in the 6800f892fcSMacpaul Lin * loop will vary from CPU to CPU though. 6900f892fcSMacpaul Lin */ 7000f892fcSMacpaul Lin 7100f892fcSMacpaul Lin .macro wait_timer, time 72*b19cc6bfSrick li $r4, \time 7300f892fcSMacpaul Lin 1: 7400f892fcSMacpaul Lin nop 7500f892fcSMacpaul Lin addi $r4, $r4, -1 7600f892fcSMacpaul Lin bnez $r4, 1b 7700f892fcSMacpaul Lin .endm 7800f892fcSMacpaul Lin 7900f892fcSMacpaul Lin #endif /* __ASSEMBLY__ */ 8000f892fcSMacpaul Lin #endif /* __ASM_ARM_MACRO_H */ 81