1 /* 2 * Copyright (C) 2016 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #pragma once 18 19 // The `annotate` attribute always pulls the annotated (inline) function into the object files, thus 20 // we should only annotate headers when we are running versioner. 21 #if defined(__BIONIC_VERSIONER) 22 23 #define __INTRODUCED_IN(api_level) __attribute__((annotate("introduced_in=" #api_level))) 24 #define __INTRODUCED_IN_NO_GUARD_FOR_NDK(api_level) __attribute__((annotate("introduced_in=" #api_level))) __VERSIONER_NO_GUARD 25 #define __DEPRECATED_IN(api_level) __attribute__((annotate("deprecated_in=" #api_level))) 26 #define __REMOVED_IN(api_level) __attribute__((annotate("obsoleted_in=" #api_level))) 27 #define __INTRODUCED_IN_32(api_level) __attribute__((annotate("introduced_in_32=" #api_level))) 28 #define __INTRODUCED_IN_64(api_level) __attribute__((annotate("introduced_in_64=" #api_level))) 29 #define __INTRODUCED_IN_ARM(api_level) __attribute__((annotate("introduced_in_arm=" #api_level))) 30 #define __INTRODUCED_IN_X86(api_level) __attribute__((annotate("introduced_in_x86=" #api_level))) 31 #define __INTRODUCED_IN_X86_NO_GUARD_FOR_NDK(api_level) __attribute__((annotate("introduced_in_x86=" #api_level))) __VERSIONER_NO_GUARD 32 33 #define __VERSIONER_NO_GUARD __attribute__((annotate("versioner_no_guard"))) 34 #define __VERSIONER_FORTIFY_INLINE __attribute__((annotate("versioner_fortify_inline"))) 35 36 #else 37 38 // When headers are not processed by the versioner (i.e. compiled into object files), 39 // the availability attributed is emitted instead. The clang compiler will make the symbol weak 40 // when targeting old api_level and enforce the reference to the symbol to be guarded with 41 // __builtin_available(android api_level, *). 42 43 // The 'strict' flag is required for NDK clients where the use of "-Wunguarded-availability" cannot 44 // be enforced. In the case, the absence of 'strict' makes it possible to call an unavailable API 45 // without the __builtin_available check, which will cause a link error at runtime. 46 // Android platform build system defines this macro along with -Wunguarded-availability 47 // 48 // The _NO_GUARD_FOR_NDK variants keep the __VERSIONER_NO_GUARD behavior working for the NDK. This 49 // allows libc++ to refer to these functions in inlines without needing to guard them, needed since 50 // libc++ doesn't currently guard these calls. There's no risk to the apps though because using 51 // those APIs will still cause a link error. 52 #if defined(__ANDROID_UNAVAILABLE_SYMBOLS_ARE_WEAK__) 53 #define __BIONIC_AVAILABILITY(__what) __attribute__((__availability__(android,__what))) 54 #define __INTRODUCED_IN_NO_GUARD_FOR_NDK(api_level) __INTRODUCED_IN_X86(api_level) 55 #define __INTRODUCED_IN_X86_NO_GUARD_FOR_NDK(api_level) __INTRODUCED_IN_X86(api_level) 56 #else 57 #define __BIONIC_AVAILABILITY(__what) __attribute__((__availability__(android,strict,__what))) 58 #define __INTRODUCED_IN_NO_GUARD_FOR_NDK(api_level) 59 #define __INTRODUCED_IN_X86_NO_GUARD_FOR_NDK(api_level) 60 #endif 61 62 #define __INTRODUCED_IN(api_level) __BIONIC_AVAILABILITY(introduced=api_level) 63 #define __DEPRECATED_IN(api_level) __BIONIC_AVAILABILITY(deprecated=api_level) 64 #define __REMOVED_IN(api_level) __BIONIC_AVAILABILITY(obsoleted=api_level) 65 66 // The same availability attribute can't be annotated multiple times. Therefore, the macros are 67 // defined for the configuration that it is valid for so that declarations like the below doesn't 68 // cause inconsistent availability values which is an error with -Wavailability: 69 // 70 // void foo() __INTRODUCED_IN_32(30) __INTRODUCED_IN_64(31); 71 // 72 // This also takes the advantage of the fact that we never use bitness-specific macro with 73 // arch-specific macro. In other words, 74 // 75 // void foo() __INTRODUCED_IN_ARM(30) __INTRODUCED_IN_64(31); 76 // 77 // hasn't been supported and won't be. 78 #if !defined(__LP64__) 79 #define __INTRODUCED_IN_32(api_level) __BIONIC_AVAILABILITY(introduced=api_level) 80 #define __INTRODUCED_IN_64(api_level) 81 #else 82 #define __INTRODUCED_IN_32(api_level) 83 #define __INTRODUCED_IN_64(api_level) __BIONIC_AVAILABILITY(introduced=api_level) 84 #endif 85 86 #if defined(__arm__) || defined(__aarch64__) 87 #define __INTRODUCED_IN_ARM(api_level) __BIONIC_AVAILABILITY(introduced=api_level) 88 #define __INTRODUCED_IN_X86(api_level) 89 #elif defined(__i386__) || defined(__x86_64__) 90 #define __INTRODUCED_IN_ARM(api_level) 91 #define __INTRODUCED_IN_X86(api_level) __BIONIC_AVAILABILITY(introduced=api_level) 92 #else 93 #define __INTRODUCED_IN_ARM(api_level) 94 #define __INTRODUCED_IN_X86(api_level) 95 #endif 96 97 #define __VERSIONER_NO_GUARD 98 #define __VERSIONER_FORTIFY_INLINE 99 100 #endif // defined(__BIONIC_VERSIONER) 101