aboutsummaryrefslogtreecommitdiff
path: root/arch/all/compiler-gcc/bits/compiler.h
blob: ef258c29c2208c37fac8ea5f300c2797004ec1c9 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
/* ****************************************************************************
 * compiler.h -- GCC identification macros.
 * Copyright (C) 2017 Thomas "Cakeisalie5" Touhey <thomas@touhey.fr>
 *
 * This file is part of the 'all/compiler-gcc' module,
 * in libcarrot, an experimental modular libc project.
 *
 * This file is free software: you can redistribute it and/or modify it under
 * the terms of the GNU Lesser General Public License as published by the Free
 * Software Foundation, either version 3 of the License, or (at your option)
 * any later version.
 *
 * This file is distributed in the hope that it will be useful, but WITHOUT
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU Lesser General Lesser Public
 * License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public License
 * along with this file.  If not, see <http://www.gnu.org/licenses/>.
 * ************************************************************************* */
/* ************************************************************************* */
/*  Detection and version checking                                           */
/* ************************************************************************* */
/* This macro is taken from the GNU C library.
 * Actually, some other compilers define the GCC-specific macros too, but as
 * they provide the same features (XXX: sure, ICC?), we shouldn't care. */

#if defined(__GNUC_PREREQ)
# undef __GNUC_PREREQ
#endif
#if defined(__GNUC__) && defined(__GNUC_MINOR__)
# define __GNUC_PREREQ(_MAJ, _MIN) \
	((__GNUC__ << 16) + __GNUC_MINOR__ >= ((_MAJ) << 16) + (_MIN))
#else
# define __GNUC_PREREQ(_MAJ, _MIN) 0
#endif
/* ************************************************************************* */
/*  Inline assembly                                                          */
/* ************************************************************************* */
/* Check if GCC extensions are on. */

#if defined(__GNUC_ASM)
# undef __GNUC_ASM
#endif
#if __GNUC_PREREQ(2, 0) && !defined(__STRICT_ANSI__)
# define __GNUC_ASM 1 /* TODO: check this */
# define __asm __asm__

#elif __GNUC_PREREQ(3, 1) && !defined(__STRICT_ANSI__)
# define __GNUC_ASM 1
# define __asm asm

/* TODO: is it possible to make use of `__extension__`? */

#else
# define __GNUC_ASM 0
#endif
/* ************************************************************************* */
/*  Attributes                                                               */
/* ************************************************************************* */
/* A lot of attributes come from GCC, so you guessed it, there is going to be
 * a lot. */

#if __GNUC_PREREQ(1, 0)
# define __inline       __attribute__((always_inline, unused))
# define __pure         __attribute__((pure))
# define __wur          __attribute__((warn_unused_result))
# define __malloc       __attribute__((malloc))
# define __deprecated   __attribute__((deprecated))
# define __noreturn     __attribute__((noreturn))
# define __nothrow      __attribute__((nothrow))
# define __unroll_loops __attribute__((optimize("unroll-loops")))

# define __nonnull(_INDEX, _NAME) __attribute__((nonnull(_INDEX)))
# define __printf_format(_FORMAT_INDEX, _ARGS_INDEX) \
	__attribute__((format(printf, _FORMAT_INDEX, _ARGS_INDEX)))
#endif
/* ************************************************************************* */
/*  Utilities                                                                */
/* ************************************************************************* */
/* Optimize the conditions for a likely or unlikely condition. */

#if __GNUC_PREREQ(2, 96)
# define   likely(_COND) __builtin_expect(!!(_COND), 1)
# define unlikely(_COND) __builtin_expect(!!(_COND), 0)
#endif
/* ************************************************************************* */
/*  SuperH CPU architecture-guessing                                         */
/* ************************************************************************* */
/* Try to guess the CPU from the vague GCC macros. */

#if __GNUC_PREREQ(1, 0)
/* Detect the CPU type.
 * TODO: _SH2E, _SH2A, _SH2AFPU
 * FIXME: 'opcode not valid for this cpu variant'
 *        (invalid _SH3DSP detection) */
# if defined(__sh1__) || defined(__SH1__)
#  define _SH1
# endif
# if defined(__sh2__) || defined(__SH2__)
#  define _SH2
# endif
# if defined(__sh3__) || defined(__SH3__)
#  define _SH3
# endif
# if defined(__sh4__) || defined(__SH4__) || defined(__SH4_NOFPU__)
#  if defined(__SH4_NOFPU__)
#   define _SH4ALDSP
#  elif defined(__SH4A__)
#   define _SH4A
#  else
#   define _SH4
#  endif
# endif
# if defined(__sh5__) || defined(__SH5__)
#  define _SH5
# endif

/* SuperH family detection. */

# if defined(__sh__) || defined(__SH__) \
	|| defined(_SH1) \
	|| defined(_SH2) || defined(_SH2E) || defined(_SH2A) \
	|| defined(_SH2AFPU) || defined(_SH2DSP) \
	|| defined(_SH3) || defined(_SH3DSP) \
	|| defined(_SH4) || defined(_SH4A) || defined(_SH4ALDSP) \
	|| defined(_SH5)
#  define _SH
# endif
#endif
/* ************************************************************************* */
/*  SuperH DSP-C interface                                                   */
/* ************************************************************************* */
/* Then, try to check if the N1169 draft extension is enabled, so we can
 * use it as the fixed-point thingies. */

#if __GNUC_PREREQ(1, 0) && defined(_SH)
# if defined(__FRACT_FBIT__) && !defined(__STRICT_ANSI__)
#  define _DSPC

#  define __X    /* not implemented */
#  define __Y    /* not implemented */
#  define __sat _Sat
#  define __circ /* not implemented */
# endif
#endif