]> git.uio.no Git - u/mrichter/AliRoot.git/blob - Vc/include/Vc/support.h
update to Vc 0.7.3-dev
[u/mrichter/AliRoot.git] / Vc / include / Vc / support.h
1 /*  This file is part of the Vc library.
2
3     Copyright (C) 2010-2012 Matthias Kretz <kretz@kde.org>
4
5     Vc is free software: you can redistribute it and/or modify
6     it under the terms of the GNU Lesser General Public License as
7     published by the Free Software Foundation, either version 3 of
8     the License, or (at your option) any later version.
9
10     Vc is distributed in the hope that it will be useful, but
11     WITHOUT ANY WARRANTY; without even the implied warranty of
12     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13     GNU Lesser General Public License for more details.
14
15     You should have received a copy of the GNU Lesser General Public
16     License along with Vc.  If not, see <http://www.gnu.org/licenses/>.
17
18 */
19
20 #ifndef VC_COMMON_SUPPORT_H
21 #define VC_COMMON_SUPPORT_H
22
23 #ifndef VC_GLOBAL_H
24 #error "Vc/global.h must be included first!"
25 #endif
26
27 #include <Vc/cpuid.h>
28
29 #if defined(VC_GCC) && VC_GCC >= 0x40400
30 #define VC_TARGET_NO_SIMD __attribute__((target("no-sse2,no-avx")))
31 #else
32 #define VC_TARGET_NO_SIMD
33 #endif
34
35 namespace AliRoot {
36 namespace Vc
37 {
38
39 /**
40  * \name Micro-Architecture Feature Tests
41  */
42 //@{
43 /**
44  * \ingroup Utilities
45  * \headerfile support.h <Vc/support.h>
46  * Determines the extra instructions supported by the current CPU.
47  *
48  * \return A combination of flags from Vc::ExtraInstructions that the current CPU supports.
49  */
50 VC_TARGET_NO_SIMD
51 unsigned int extraInstructionsSupported();
52
53 /**
54  * \ingroup Utilities
55  * \headerfile support.h <Vc/support.h>
56  *
57  * Tests whether the given implementation is supported by the system the code is executing on.
58  *
59  * \return \c true if the OS and hardware support execution of instructions defined by \p impl.
60  * \return \c false otherwise
61  *
62  * \param impl The SIMD target to test for.
63  */
64 VC_TARGET_NO_SIMD
65 bool isImplementationSupported(Vc::Implementation impl);
66
67 /**
68  * \internal
69  * \ingroup Utilities
70  * \headerfile support.h <Vc/support.h>
71  *
72  * Tests whether the given implementation is supported by the system the code is executing on.
73  *
74  * \code
75  * if (!isImplementationSupported<Vc::CurrentImplementation>()) {
76  *   std::cerr << "This code was compiled with features that this system does not support.\n";
77  *   return EXIT_FAILURE;
78  * }
79  * \endcode
80  *
81  * \return \c true if the OS and hardware support execution of instructions defined by \p impl.
82  * \return \c false otherwise
83  *
84  * \tparam Impl The SIMD target to test for.
85  */
86 template<typename Impl>
87 VC_TARGET_NO_SIMD
88 static inline bool isImplementationSupported()
89 {
90     return isImplementationSupported(static_cast<Vc::Implementation>(Impl::Implementation)) &&
91         (extraInstructionsSupported() & Impl::ExtraInstructions) == Impl::ExtraInstructions;
92 }
93
94 /**
95  * \ingroup Utilities
96  * \headerfile support.h <Vc/support.h>
97  *
98  * Determines the best supported implementation for the current system.
99  *
100  * \return The enum value for the best implementation.
101  */
102 VC_TARGET_NO_SIMD
103 Vc::Implementation bestImplementationSupported();
104
105 #ifndef VC_COMPILE_LIB
106 /**
107  * \ingroup Utilities
108  * \headerfile support.h <Vc/support.h>
109  *
110  * Tests that the CPU and Operating System support the vector unit which was compiled for. This
111  * function should be called before any other Vc functionality is used. It checks whether the program
112  * will work. If this function returns \c false then the program should exit with a useful error
113  * message before the OS has to kill it because of an invalid instruction exception.
114  *
115  * If the program continues and makes use of any vector features not supported by
116  * hard- or software then the program will crash.
117  *
118  * Example:
119  * \code
120  * int main()
121  * {
122  *   if (!Vc::currentImplementationSupported()) {
123  *     std::cerr << "CPU or OS requirements not met for the compiled in vector unit!\n";
124  *     exit -1;
125  *   }
126  *   ...
127  * }
128  * \endcode
129  *
130  * \return \c true if the OS and hardware support execution of the currently selected SIMD
131  *                 instructions.
132  * \return \c false otherwise
133  */
134 VC_TARGET_NO_SIMD
135 #ifndef DOXYGEN
136 static
137 #endif
138 inline bool currentImplementationSupported()
139 {
140     return isImplementationSupported<Vc::CurrentImplementation>();
141 }
142 #endif // VC_COMPILE_LIB
143 //@}
144
145 } // namespace Vc
146 } // namespace AliRoot
147
148 #undef VC_TARGET_NO_SIMD
149
150 #endif // VC_COMMON_SUPPORT_H