Imported Upstream version 0.9.1
[platform/upstream/iotivity.git] / build_common / iotivityconfig / compiler / configuration.py
1 # ------------------------------------------------------------------------
2 # Copyright 2015 Intel Corporation
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 class Configuration:
18     """Compiler-specific configuration abstract base class"""
19
20     def __init__(self, context):
21         """
22         Initialize the Configuration object
23
24         Arguments:
25         context -- the scons configure context
26         """
27
28         if type(self) is Configuration:
29             raise TypeError('abstract class cannot be instantiated')
30
31         self._context = context      # scons configure context
32         self._env     = context.env  # scons environment
33
34     def check_c99_flags(self):
35         """
36         Check if command line flag is required to enable C99
37         support.
38
39         Returns 1 if no flag is required, 0 if no flag was
40         found, and the actual flag if one was found.
41
42         CFLAGS will be updated with appropriate C99 flag,
43         accordingly.
44         """
45
46         return self._check_flags(self._c99_flags(),
47                                  self._c99_test_program(),
48                                  '.c',
49                                  'CFLAGS')
50
51     def check_cxx11_flags(self):
52         """
53         Check if command line flag is required to enable C++11
54         support.
55
56         Returns 1 if no flag is required, 0 if no flag was
57         found, and the actual flag if one was found.
58
59         CXXFLAGS will be updated with appropriate C++11 flag,
60         accordingly.
61         """
62
63         return self._check_flags(self._cxx11_flags(),
64                                  self._cxx11_test_program(),
65                                  '.cpp',
66                                  'CXXFLAGS')
67
68     def has_pthreads_support(self):
69         """
70         Check if PThreads are supported by this system
71
72         Returns 1 if this system DOES support pthreads, 0
73         otherwise
74         """
75
76         return self._context.TryCompile(self._pthreads_test_program(), '.c')
77
78     # --------------------------------------------------------------
79     # Check if flag is required to build the given test program.
80     #
81     # Arguments:
82     # test_flags     -- list of flags that may be needed to build
83     #                   test_program
84     # test_program   -- program used used to determine if one of the
85     #                   given flags is required to for a successful
86     #                   build
87     # test_extension -- file extension associated with the test
88     #                   program, e.g. '.cpp' for C++ and '.c' for C
89     # flags_key      -- key used to retrieve compiler flags that may
90     #                   be updated by this check from the SCons
91     #                   environment
92     # --------------------------------------------------------------
93     def _check_flags(self,
94                      test_flags,
95                      test_program,
96                      test_extension,
97                      flags_key):
98         # Check if no additional flags are required.
99         ret = self._context.TryCompile(test_program,
100                                        test_extension)
101
102         if ret is 0:
103             # Try flags known to enable compiler features needed by
104             # the test program.
105
106             last_flags = self._env[flags_key]
107             for flag in test_flags:
108                 self._env.Append(**{flags_key : flag})
109                 ret = self._context.TryCompile(test_program,
110                                                test_extension)
111
112                 if ret:
113                     # Found a flag!
114                     return flag
115                 else:
116                     # Restore original compiler flags for next flag
117                     # test.
118                     self._env.Replace(**{flags_key : last_flags})
119
120         return ret
121
122     # ------------------------------------------------------------
123     # Return test program to be used when checking for basic C99
124     # support.
125     #
126     # Subclasses should implement this template method or use the
127     # default test program found in the DefaultConfiguration class
128     # through composition.
129     # ------------------------------------------------------------
130     def _c99_test_program(self):
131         raise NotImplementedError('unimplemented method')
132
133     # --------------------------------------------------------------
134     # Get list of flags that could potentially enable C99 support.
135     #
136     # Subclasses should implement this template method if flags are
137     # needed to enable C99 support.
138     # --------------------------------------------------------------
139     def _c99_flags(self):
140         raise NotImplementedError('unimplemented method')
141
142     # ------------------------------------------------------------
143     # Return test program to be used when checking for basic C++11
144     # support.
145     #
146     # Subclasses should implement this template method or use the
147     # default test program found in the DefaultConfiguration class
148     # through composition.
149     # ------------------------------------------------------------
150     def _cxx11_test_program(self):
151         raise NotImplementedError('unimplemented method')
152
153     # --------------------------------------------------------------
154     # Get list of flags that could potentially enable C++11 support.
155     #
156     # Subclasses should implement this template method if flags are
157     # needed to enable C++11 support.
158     # --------------------------------------------------------------
159     def _cxx11_flags(self):
160         raise NotImplementedError('unimplemented method')
161
162     # --------------------------------------------------------------
163     # Return a test program to be used when checking for PThreads
164     # support
165     #
166     # --------------------------------------------------------------
167     def _pthreads_test_program(self):
168         return """
169 #include <unistd.h>
170 #include <pthread.h>
171 int main()
172 {
173     #ifndef _POSIX_THREADS
174     # error POSIX Threads support not available
175     #endif
176     return 0;
177 }
178 """