1 /* Configuration definitions. 2 Copyright (C) 2008, 2009 Red Hat, Inc. 3 This file is part of elfutils. 4 5 This file is free software; you can redistribute it and/or modify 6 it under the terms of either 7 8 * the GNU Lesser General Public License as published by the Free 9 Software Foundation; either version 3 of the License, or (at 10 your option) any later version 11 12 or 13 14 * the GNU General Public License as published by the Free 15 Software Foundation; either version 2 of the License, or (at 16 your option) any later version 17 18 or both in parallel, as here. 19 20 elfutils is distributed in the hope that it will be useful, but 21 WITHOUT ANY WARRANTY; without even the implied warranty of 22 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 23 General Public License for more details. 24 25 You should have received copies of the GNU General Public License and 26 the GNU Lesser General Public License along with this program. If 27 not, see <http://www.gnu.org/licenses/>. */ 28 29 #ifndef EU_CONFIG_H 30 #define EU_CONFIG_H 1 31 32 #ifdef USE_LOCKS 33 # include <pthread.h> 34 # include <assert.h> 35 # define rwlock_define(class,name) class pthread_rwlock_t name 36 # define RWLOCK_CALL(call) \ 37 ({ int _err = pthread_rwlock_ ## call; assert_perror (_err); }) 38 # define rwlock_init(lock) RWLOCK_CALL (init (&lock, NULL)) 39 # define rwlock_fini(lock) RWLOCK_CALL (destroy (&lock)) 40 # define rwlock_rdlock(lock) RWLOCK_CALL (rdlock (&lock)) 41 # define rwlock_wrlock(lock) RWLOCK_CALL (wrlock (&lock)) 42 # define rwlock_unlock(lock) RWLOCK_CALL (unlock (&lock)) 43 #else 44 /* Eventually we will allow multi-threaded applications to use the 45 libraries. Therefore we will add the necessary locking although 46 the macros used expand to nothing for now. */ 47 # define rwlock_define(class,name) class int name 48 # define rwlock_init(lock) ((void) (lock)) 49 # define rwlock_fini(lock) ((void) (lock)) 50 # define rwlock_rdlock(lock) ((void) (lock)) 51 # define rwlock_wrlock(lock) ((void) (lock)) 52 # define rwlock_unlock(lock) ((void) (lock)) 53 #endif /* USE_LOCKS */ 54 55 /* gettext helper macros. */ 56 #define N_(Str) Str 57 #define _(Str) dgettext ("elfutils", Str) 58 59 /* Compiler-specific definitions. */ 60 #define strong_alias(name, aliasname) \ 61 extern __typeof (name) aliasname __attribute__ ((alias (#name))); 62 63 #ifdef __i386__ 64 # define internal_function __attribute__ ((regparm (3), stdcall)) 65 #else 66 # define internal_function /* nothing */ 67 #endif 68 69 #define internal_strong_alias(name, aliasname) \ 70 extern __typeof (name) aliasname __attribute__ ((alias (#name))) internal_function; 71 72 #ifdef HAVE_VISIBILITY 73 #define attribute_hidden \ 74 __attribute__ ((visibility ("hidden"))) 75 #else 76 #define attribute_hidden /* empty */ 77 #endif 78 79 #ifdef HAVE_GCC_STRUCT 80 #define attribute_packed \ 81 __attribute__ ((packed, gcc_struct)) 82 #else 83 #define attribute_packed \ 84 __attribute__ ((packed)) 85 #endif 86 87 /* Define ALLOW_UNALIGNED if the architecture allows operations on 88 unaligned memory locations. */ 89 #define SANITIZE_UNDEFINED 1 90 #if (defined __i386__ || defined __x86_64__) && ! CHECK_UNDEFINED 91 # define ALLOW_UNALIGNED 1 92 #else 93 # define ALLOW_UNALIGNED 0 94 #endif 95 96 #if DEBUGPRED 97 # ifdef __x86_64__ 98 asm (".section predict_data, \"aw\"; .previous\n" 99 ".section predict_line, \"a\"; .previous\n" 100 ".section predict_file, \"a\"; .previous"); 101 # ifndef PIC 102 # define debugpred__(e, E) \ 103 ({ long int _e = !!(e); \ 104 asm volatile (".pushsection predict_data; ..predictcnt%=: .quad 0; .quad 0\n" \ 105 ".section predict_line; .quad %c1\n" \ 106 ".section predict_file; .quad %c2; .popsection\n" \ 107 "addq $1,..predictcnt%=(,%0,8)" \ 108 : : "r" (_e == E), "i" (__LINE__), "i" (__FILE__)); \ 109 __builtin_expect (_e, E); \ 110 }) 111 # endif 112 # elif defined __i386__ 113 asm (".section predict_data, \"aw\"; .previous\n" 114 ".section predict_line, \"a\"; .previous\n" 115 ".section predict_file, \"a\"; .previous"); 116 # ifndef PIC 117 # define debugpred__(e, E) \ 118 ({ long int _e = !!(e); \ 119 asm volatile (".pushsection predict_data; ..predictcnt%=: .long 0; .long 0\n" \ 120 ".section predict_line; .long %c1\n" \ 121 ".section predict_file; .long %c2; .popsection\n" \ 122 "incl ..predictcnt%=(,%0,8)" \ 123 : : "r" (_e == E), "i" (__LINE__), "i" (__FILE__)); \ 124 __builtin_expect (_e, E); \ 125 }) 126 # endif 127 # endif 128 # ifdef debugpred__ 129 # define unlikely(e) debugpred__ (e,0) 130 # define likely(e) debugpred__ (e,1) 131 # endif 132 #endif 133 #ifndef likely 134 # define unlikely(expr) __builtin_expect (!!(expr), 0) 135 # define likely(expr) __builtin_expect (!!(expr), 1) 136 #endif 137 138 #define obstack_calloc(ob, size) \ 139 ({ size_t _s = (size); memset (obstack_alloc (ob, _s), '\0', _s); }) 140 #define obstack_strdup(ob, str) \ 141 ({ const char *_s = (str); obstack_copy0 (ob, _s, strlen (_s)); }) 142 #define obstack_strndup(ob, str, n) \ 143 ({ const char *_s = (str); obstack_copy0 (ob, _s, strnlen (_s, n)); }) 144 145 #if __STDC_VERSION__ >= 199901L 146 # define flexarr_size /* empty */ 147 #else 148 # define flexarr_size 0 149 #endif 150 151 /* Calling conventions. */ 152 #ifdef __i386__ 153 # define CALLING_CONVENTION regparm (3), stdcall 154 # define AND_CALLING_CONVENTION , regparm (3), stdcall 155 #else 156 # define CALLING_CONVENTION 157 # define AND_CALLING_CONVENTION 158 #endif 159 160 /* Avoid PLT entries. */ 161 #ifdef PIC 162 # define INTUSE(name) _INTUSE(name) 163 # define _INTUSE(name) __##name##_internal 164 # define INTDEF(name) _INTDEF(name) 165 # define _INTDEF(name) \ 166 extern __typeof__ (name) __##name##_internal __attribute__ ((alias (#name))); 167 # define INTDECL(name) _INTDECL(name) 168 # define _INTDECL(name) \ 169 extern __typeof__ (name) __##name##_internal attribute_hidden; 170 #else 171 # define INTUSE(name) name 172 # define INTDEF(name) /* empty */ 173 # define INTDECL(name) /* empty */ 174 #endif 175 176 /* This macro is used by the tests conditionalize for standalone building. */ 177 #define ELFUTILS_HEADER(name) <lib##name.h> 178 179 /* Don't reorder with global asm blocks or optimize away. (Doesn't reliably 180 keep it in the same LTO partition, though; -flto-partition=none may be 181 still needed for some gcc versions < 10.) */ 182 #ifdef __has_attribute 183 # if __has_attribute(no_reorder) 184 # define used_in_asm __attribute__ ((externally_visible, no_reorder)) 185 # endif 186 #endif 187 #ifndef used_in_asm 188 # define used_in_asm /* empty */ 189 #endif 190 191 #ifdef SYMBOL_VERSIONING 192 # define NEW_INTDEF(name) __typeof (name) INTUSE(name) \ 193 __attribute__ ((alias ("_new." #name))) attribute_hidden; 194 # ifdef __has_attribute 195 # if __has_attribute(symver) 196 # define NEW_VERSION(name, version) \ 197 __typeof (name) name __asm__ ("_new." #name) \ 198 __attribute__ ((symver (#name "@@" #version))); 199 # define OLD_VERSION(name, version) _OLD_VERSION1(name, __COUNTER__, version) 200 # define _OLD_VERSION1(name, num, version) _OLD_VERSION2(name, num, version) 201 # define _OLD_VERSION2(name, num, version) \ 202 __typeof (name) _compat_old##num##_##name \ 203 __asm__ ("_compat." #version "." #name) \ 204 __attribute__ ((alias ("_new." #name), symver (#name "@" #version))); 205 # define COMPAT_VERSION_NEWPROTO(name, version, prefix) \ 206 __typeof (_compat_##prefix##_##name) _compat_##prefix##_##name \ 207 __asm__ ("_compat." #version "." #name) \ 208 __attribute__ ((symver (#name "@" #version))); 209 # define COMPAT_VERSION(name, version, prefix) \ 210 asm (".symver _compat." #version "." #name "," #name "@" #version); \ 211 __typeof (name) _compat_##prefix##_##name \ 212 __asm__ ("_compat." #version "." #name) \ 213 __attribute__ ((symver (#name "@" #version))); 214 # endif 215 # endif 216 # ifndef NEW_VERSION 217 # define OLD_VERSION(name, version) \ 218 asm (".globl _compat." #version "." #name "\n\t" \ 219 "_compat." #version "." #name " = _new." #name "\n\t" \ 220 ".symver _compat." #version "." #name "," #name "@" #version); 221 # define NEW_VERSION(name, version) \ 222 __typeof (name) name __asm__ ("_new." #name) used_in_asm; \ 223 asm (".symver _new." #name ", " #name "@@" #version); 224 # define COMPAT_VERSION_NEWPROTO(name, version, prefix) \ 225 __typeof (_compat_##prefix##_##name) _compat_##prefix##_##name \ 226 __asm__ ("_compat." #version "." #name) used_in_asm; \ 227 asm (".symver _compat." #version "." #name ", " #name "@" #version); 228 # define COMPAT_VERSION(name, version, prefix) \ 229 __typeof (name) _compat_##prefix##_##name \ 230 __asm__ ("_compat." #version "." #name) used_in_asm; \ 231 asm (".symver _compat." #version "." #name ", " #name "@" #version); 232 # endif 233 #else 234 # define NEW_INTDEF(name) INTDEF(name) 235 # define OLD_VERSION(name, version) /* Nothing for static linking. */ 236 # define NEW_VERSION(name, version) /* Nothing for static linking. */ 237 # define COMPAT_VERSION_NEWPROTO(name, version, prefix) \ 238 error "should use #ifdef SYMBOL_VERSIONING" 239 # define COMPAT_VERSION(name, version, prefix) \ 240 error "should use #ifdef SYMBOL_VERSIONING" 241 #endif 242 243 #ifndef FALLTHROUGH 244 # ifdef HAVE_FALLTHROUGH 245 # define FALLTHROUGH __attribute__ ((fallthrough)) 246 # else 247 # define FALLTHROUGH ((void) 0) 248 # endif 249 #endif 250 251 #endif /* eu-config.h */ 252