1/* SPDX-License-Identifier: GPL-2.0 WITH Linux-syscall-note */ 2/* 3 * Compiler-dependent intrinsics. 4 * 5 * Copyright (C) 2002-2003 Hewlett-Packard Co 6 * David Mosberger-Tang <davidm@hpl.hp.com> 7 */ 8#ifndef _UAPI_ASM_IA64_INTRINSICS_H 9#define _UAPI_ASM_IA64_INTRINSICS_H 10 11 12#ifndef __ASSEMBLY__ 13 14#include <linux/types.h> 15/* include compiler specific intrinsics */ 16#include <asm/ia64regs.h> 17#include <asm/gcc_intrin.h> 18#include <asm/cmpxchg.h> 19 20#define ia64_set_rr0_to_rr4(val0, val1, val2, val3, val4) \ 21do { \ 22 ia64_set_rr(0x0000000000000000UL, (val0)); \ 23 ia64_set_rr(0x2000000000000000UL, (val1)); \ 24 ia64_set_rr(0x4000000000000000UL, (val2)); \ 25 ia64_set_rr(0x6000000000000000UL, (val3)); \ 26 ia64_set_rr(0x8000000000000000UL, (val4)); \ 27} while (0) 28 29/* 30 * Force an unresolved reference if someone tries to use 31 * ia64_fetch_and_add() with a bad value. 32 */ 33extern unsigned long __bad_size_for_ia64_fetch_and_add (void); 34extern unsigned long __bad_increment_for_ia64_fetch_and_add (void); 35 36#define IA64_FETCHADD(tmp,v,n,sz,sem) \ 37({ \ 38 switch (sz) { \ 39 case 4: \ 40 tmp = ia64_fetchadd4_##sem((unsigned int *) v, n); \ 41 break; \ 42 \ 43 case 8: \ 44 tmp = ia64_fetchadd8_##sem((unsigned long *) v, n); \ 45 break; \ 46 \ 47 default: \ 48 __bad_size_for_ia64_fetch_and_add(); \ 49 } \ 50}) 51 52#define ia64_fetchadd(i,v,sem) \ 53({ \ 54 __u64 _tmp; \ 55 volatile __typeof__(*(v)) *_v = (v); \ 56 /* Can't use a switch () here: gcc isn't always smart enough for that... */ \ 57 if ((i) == -16) \ 58 IA64_FETCHADD(_tmp, _v, -16, sizeof(*(v)), sem); \ 59 else if ((i) == -8) \ 60 IA64_FETCHADD(_tmp, _v, -8, sizeof(*(v)), sem); \ 61 else if ((i) == -4) \ 62 IA64_FETCHADD(_tmp, _v, -4, sizeof(*(v)), sem); \ 63 else if ((i) == -1) \ 64 IA64_FETCHADD(_tmp, _v, -1, sizeof(*(v)), sem); \ 65 else if ((i) == 1) \ 66 IA64_FETCHADD(_tmp, _v, 1, sizeof(*(v)), sem); \ 67 else if ((i) == 4) \ 68 IA64_FETCHADD(_tmp, _v, 4, sizeof(*(v)), sem); \ 69 else if ((i) == 8) \ 70 IA64_FETCHADD(_tmp, _v, 8, sizeof(*(v)), sem); \ 71 else if ((i) == 16) \ 72 IA64_FETCHADD(_tmp, _v, 16, sizeof(*(v)), sem); \ 73 else \ 74 _tmp = __bad_increment_for_ia64_fetch_and_add(); \ 75 (__typeof__(*(v))) (_tmp); /* return old value */ \ 76}) 77 78#define ia64_fetch_and_add(i,v) (ia64_fetchadd(i, v, rel) + (i)) /* return new value */ 79 80#endif 81 82#endif /* _UAPI_ASM_IA64_INTRINSICS_H */ 83