1/* $OpenBSD: namespace.h,v 1.3 2018/03/12 06:19:19 guenther Exp $ */ 2 3#ifndef _LIBM_NAMESPACE_H_ 4#define _LIBM_NAMESPACE_H_ 5 6/* 7 * Copyright (c) 2015 Philip Guenther <guenther@openbsd.org> 8 * 9 * Permission to use, copy, modify, and distribute this software for any 10 * purpose with or without fee is hereby granted, provided that the above 11 * copyright notice and this permission notice appear in all copies. 12 * 13 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 14 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 15 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 16 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 17 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 18 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 19 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 20 */ 21 22/* 23 * The goal: calls from inside libc to other libc functions should be via 24 * identifiers that are of hidden visibility and--to avoid confusion--are 25 * in the reserved namespace. By doing this these calls are protected 26 * from overriding by applications and on many platforms can avoid creation 27 * or use of GOT or PLT entries. I've chosen a prefix of "_libm_" for this. 28 * These will not be declared directly; instead, the gcc "asm labels" 29 * extension will be used rename the function. 30 * 31 * In order to actually set up the desired asm labels, we use these in 32 * the internal .h files: 33 * PROTO_NORMAL(x) Symbols used both internally and externally 34 * This makes gcc convert use of x to use _libm_x instead. Use 35 * DEF_STD(x) or DEF_NONSTD(x) to create the external alias. 36 * ex: PROTO_NORMAL(ceil) 37 * 38 * PROTO_STD_DEPRECATED(x) Standard C symbols that are not used internally 39 * This just marks the symbol as deprecated, with no renaming. 40 * Do not use DEF_*(x) with this. 41 * ex: PROTO_STD_DEPRECATED(tgammal) 42 * 43 * PROTO_DEPRECATED(x) Symbols not in C that are not used internally 44 * This marks the symbol as deprecated and, in the static lib, weak. 45 * No renaming is done. Do not use DEF_*(x) with this. 46 * ex: PROTO_DEPRECATED(creat) 47 * 48 * Finally, to create the expected aliases, we use these in the .c files 49 * where the definitions are: 50 * DEF_STD(x) Symbols reserved to or specified by ISO C 51 * This defines x as a strong alias for _libm_x; this must only 52 * be used for symbols that are reserved by the C standard 53 * (or reserved in the external identifier namespace). 54 * Matches with PROTO_NORMAL() 55 * ex: DEF_STD(fopen) 56 * 57 * DEF_NONSTD(x) Symbols used internally and not in ISO C 58 * This defines x as a alias for _libm_x, weak in the static version 59 * Matches with PROTO_NORMAL() 60 * ex: DEF_NONSTD(lseek) 61 * 62 * LDBL_CLONE(x) long double aliases that are used 63 * This defines xl and _libm_xl as aliases for _libm_x. 64 * Matches with LDBL_PROTO_NORMAL() 65 * 66 * LDBL_UNUSED_CLONE(x) long double aliases that are unused 67 * This defines xl as an alias for _libm_x. 68 * Matches with LDBL_PROTO_STD_DEPRECATED() 69 * 70 * LDBL_MAYBE_CLONE(x) 71 * LDBL_MAYBE_UNUSED_CLONE(x) 72 * Like LDBL_CLONE() and LDBL_UNUSED_CLONE(), except they do nothing 73 * if LDBL_MANT_DIG != DBL_MANT_DIG 74 * 75 * MAKE_UNUSED_CLONE(dst, src) Unused symbols that are exact clones 76 * of other symbols 77 * This declares dst as being the same type as dst, and makes 78 * _libm_dst a strong, hidden alias for _libm_src. You still need to 79 * DEF_STD(dst) or DEF_NONSTD(dst) to alias dst itself 80 * ex: MAKE_UNUSED_CLONE(nexttoward, nextafter); 81 */ 82 83#include <sys/cdefs.h> /* for __dso_hidden and __{weak,strong}_alias */ 84 85#ifndef PIC 86# define WEAK_IN_STATIC_ALIAS(x,y) __weak_alias(x,y) 87# define WEAK_IN_STATIC __attribute__((weak)) 88#else 89# define WEAK_IN_STATIC_ALIAS(x,y) __strong_alias(x,y) 90# define WEAK_IN_STATIC /* nothing */ 91#endif 92 93#define HIDDEN(x) _libm_##x 94#define HIDDEN_STRING(x) "_libm_" __STRING(x) 95 96#define PROTO_NORMAL(x) __dso_hidden typeof(x) HIDDEN(x), x asm(HIDDEN_STRING(x)) 97#define PROTO_STD_DEPRECATED(x) typeof(x) HIDDEN(x), x __attribute__((deprecated)) 98#define PROTO_DEPRECATED(x) PROTO_STD_DEPRECATED(x) WEAK_IN_STATIC 99 100#define DEF_STD(x) __strong_alias(x, HIDDEN(x)) 101#define DEF_NONSTD(x) WEAK_IN_STATIC_ALIAS(x, HIDDEN(x)) 102 103#define MAKE_UNUSED_CLONE(dst, src) __strong_alias(dst, src) 104#define LDBL_UNUSED_CLONE(x) __strong_alias(x##l, HIDDEN(x)) 105#define LDBL_NONSTD_UNUSED_CLONE(x) WEAK_IN_STATIC_ALIAS(x##l, HIDDEN(x)) 106#define LDBL_CLONE(x) LDBL_UNUSED_CLONE(x); \ 107 __dso_hidden typeof(HIDDEN(x##l)) HIDDEN(x##l) \ 108 __attribute__((alias (HIDDEN_STRING(x)))) 109#define LDBL_NONSTD_CLONE(x) LDBL_NONSTD_UNUSED_CLONE(x); \ 110 __dso_hidden typeof(HIDDEN(x##l)) HIDDEN(x##l) \ 111 __attribute__((alias (HIDDEN_STRING(x)))) 112 113#if __LDBL_MANT_DIG__ == __DBL_MANT_DIG__ 114# define LDBL_PROTO_NORMAL(x) typeof(x) HIDDEN(x) 115# define LDBL_PROTO_STD_DEPRECATED(x) typeof(x) HIDDEN(x) 116# define LDBL_MAYBE_CLONE(x) LDBL_CLONE(x) 117# define LDBL_MAYBE_UNUSED_CLONE(x) LDBL_UNUSED_CLONE(x) 118# define LDBL_MAYBE_NONSTD_UNUSED_CLONE(x) LDBL_NONSTD_UNUSED_CLONE(x) 119# define LDBL_MAYBE_NONSTD_CLONE(x) LDBL_NONSTD_CLONE(x) 120#else 121# define LDBL_PROTO_NORMAL(x) PROTO_NORMAL(x) 122# define LDBL_PROTO_STD_DEPRECATED(x) PROTO_STD_DEPRECATED(x) 123# define LDBL_MAYBE_CLONE(x) __asm("") 124# define LDBL_MAYBE_UNUSED_CLONE(x) __asm("") 125# define LDBL_MAYBE_NONSTD_UNUSED_CLONE(x) __asm("") 126# define LDBL_MAYBE_NONSTD_CLONE(x) __asm("") 127#endif 128 129#endif /* _LIBM_NAMESPACE_H_ */ 130