1 /* 2 * Supervisor Mode Access Prevention support 3 * 4 * Copyright (C) 2012 Intel Corporation 5 * Author: H. Peter Anvin <hpa@linux.intel.com> 6 * 7 * This program is free software; you can redistribute it and/or 8 * modify it under the terms of the GNU General Public License 9 * as published by the Free Software Foundation; version 2 10 * of the License. 11 */ 12 13 #ifndef _ASM_X86_SMAP_H 14 #define _ASM_X86_SMAP_H 15 16 #include <linux/stringify.h> 17 #include <asm/nops.h> 18 #include <asm/cpufeature.h> 19 20 /* "Raw" instruction opcodes */ 21 #define __ASM_CLAC .byte 0x0f,0x01,0xca 22 #define __ASM_STAC .byte 0x0f,0x01,0xcb 23 24 #ifdef __ASSEMBLY__ 25 26 #include <asm/alternative-asm.h> 27 28 #ifdef CONFIG_X86_SMAP 29 30 #define ASM_CLAC \ 31 ALTERNATIVE "", __stringify(__ASM_CLAC), X86_FEATURE_SMAP 32 33 #define ASM_STAC \ 34 ALTERNATIVE "", __stringify(__ASM_STAC), X86_FEATURE_SMAP 35 36 #else /* CONFIG_X86_SMAP */ 37 38 #define ASM_CLAC 39 #define ASM_STAC 40 41 #endif /* CONFIG_X86_SMAP */ 42 43 #else /* __ASSEMBLY__ */ 44 45 #include <asm/alternative.h> 46 47 #ifdef CONFIG_X86_SMAP 48 49 static __always_inline void clac(void) 50 { 51 /* Note: a barrier is implicit in alternative() */ 52 alternative("", __stringify(__ASM_CLAC), X86_FEATURE_SMAP); 53 } 54 55 static __always_inline void stac(void) 56 { 57 /* Note: a barrier is implicit in alternative() */ 58 alternative("", __stringify(__ASM_STAC), X86_FEATURE_SMAP); 59 } 60 61 /* These macros can be used in asm() statements */ 62 #define ASM_CLAC \ 63 ALTERNATIVE("", __stringify(__ASM_CLAC), X86_FEATURE_SMAP) 64 #define ASM_STAC \ 65 ALTERNATIVE("", __stringify(__ASM_STAC), X86_FEATURE_SMAP) 66 67 #else /* CONFIG_X86_SMAP */ 68 69 static inline void clac(void) { } 70 static inline void stac(void) { } 71 72 #define ASM_CLAC 73 #define ASM_STAC 74 75 #endif /* CONFIG_X86_SMAP */ 76 77 #endif /* __ASSEMBLY__ */ 78 79 #endif /* _ASM_X86_SMAP_H */ 80