]> git.proxmox.com Git - ceph.git/blame - ceph/src/boost/tools/build/src/build/ac.jam
add subtree-ish sources for 12.0.3
[ceph.git] / ceph / src / boost / tools / build / src / build / ac.jam
CommitLineData
7c673cae
FG
1# Copyright (c) 2010 Vladimir Prus.
2# Copyright (c) 2013 Steven Watanabe
3#
4# Use, modification and distribution is subject to the Boost Software
5# License Version 1.0. (See accompanying file LICENSE_1_0.txt or
6# http://www.boost.org/LICENSE_1_0.txt)
7
8import property-set ;
9import path ;
10import modules ;
11import "class" ;
12import errors ;
13import configure ;
14import project ;
15import virtual-target ;
16import generators ;
17import property ;
18import print ;
19import regex ;
20
21project.initialize $(__name__) ;
22.project = [ project.current ] ;
23project ac ;
24
25rule generate-include ( target : sources * : properties * )
26{
27 local header = [ property.select <include> : $(properties) ] ;
28 print.output $(target) ;
29 print.text "#include <$(header:G=)>\n" : true ;
30}
31
32rule generate-main ( target : sources * : properties * )
33{
34 print.output $(target) ;
35 print.text "int main() {}" : true ;
36}
37
38rule find-include-path ( properties : header : provided-path ? )
39{
40 if $(provided-path) && [ path.exists [ path.root $(header) $(provided-path) ] ]
41 {
42 return $(provided-path) ;
43 }
44 else
45 {
46 local a = [ class.new action : ac.generate-include : [ property-set.create <include>$(header) ] ] ;
47 # Create a new CPP target named after the header.
48 # Replace dots (".") in target basename for portability.
49 local basename = [ regex.replace $(header:D=) "[.]" "_" ] ;
50 local header-target = $(header:S=:B=$(basename)) ;
51 local cpp = [ class.new file-target $(header-target:S=.cpp) exact : CPP : $(.project) : $(a) ] ;
52 cpp = [ virtual-target.register $(cpp) ] ;
53 local result = [ generators.construct $(.project) $(header-target) : OBJ : $(properties) : $(cpp) : true ] ;
54 local jam-targets ;
55 for t in $(result[2-])
56 {
57 jam-targets += [ $(t).actualize ] ;
58 }
59 if [ UPDATE_NOW $(jam-targets) : [ modules.peek configure : .log-fd ]
60 : ignore-minus-n : ignore-minus-q ]
61 {
62 return %default ;
63 }
64 }
65}
66
67rule construct-library ( name : property-set : provided-path ? )
68{
69 property-set = [ $(property-set).refine [ property-set.create $(link-opt) ] ] ;
70 local lib-props = [ $(property-set).add-raw <name>$(name) <search>$(provided-path) ] ;
71 return [ generators.construct $(.project) lib-$(name)
72 : SEARCHED_LIB : $(lib-props) : : true ] ;
73}
74
75
76rule find-library ( properties : names + : provided-path ? )
77{
78 local result ;
79 if ! $(.main.cpp)
80 {
81 local a = [ class.new action : ac.generate-main :
82 [ property-set.empty ] ] ;
83 .main.cpp = [ virtual-target.register
84 [ class.new file-target main.cpp exact
85 : CPP : $(.project) : $(a) ] ] ;
86 }
87 if [ $(properties).get <link> ] = shared
88 {
89 link-opts = <link>shared <link>static ;
90 }
91 else
92 {
93 link-opts = <link>static <link>shared ;
94 }
95 while $(link-opts)
96 {
97 local names-iter = $(names) ;
98 properties = [ $(properties).refine [ property-set.create $(link-opts[1]) ] ] ;
99 while $(names-iter)
100 {
101 local name = $(names-iter[1]) ;
102 local lib = [ construct-library $(name) : $(properties) : $(provided-path) ] ;
103 local test = [ generators.construct $(.project) $(name) : EXE
104 : [ $(properties).add $(lib[1]) ] : $(.main.cpp) $(lib[2-])
105 : true ] ;
106 local jam-targets ;
107 for t in $(test[2-])
108 {
109 jam-targets += [ $(t).actualize ] ;
110 }
111 if [ UPDATE_NOW $(jam-targets) : [ modules.peek configure : .log-fd ]
112 : ignore-minus-n : ignore-minus-q ]
113 {
114 result = $(name) $(link-opts[1]) ;
115 names-iter = ; link-opts = ; # break
116 }
117 names-iter = $(names-iter[2-]) ;
118 }
119 link-opts = $(link-opts[2-]) ;
120 }
121 return $(result) ;
122}
123
124class ac-library : basic-target
125{
126 import errors ;
127 import indirect ;
128 import virtual-target ;
129 import ac ;
130 import configure ;
131 import config-cache ;
132
133 rule __init__ ( name : project : requirements * : include-path ? : library-path ? : library-name ? )
134 {
135 basic-target.__init__ $(name) : $(project) : : $(requirements) ;
136
137 reconfigure $(include-path) : $(library-path) : $(library-name) ;
138 }
139
140 rule set-header ( header )
141 {
142 self.header = $(header) ;
143 }
144
145 rule set-default-names ( names + )
146 {
147 self.default-names = $(names) ;
148 }
149
150 rule reconfigure ( include-path ? : library-path ? : library-name ? )
151 {
152 if $(include-path) || $(library-path) || $(library-name)
153 {
154 check-not-configured ;
155
156 self.include-path = $(include-path) ;
157 self.library-path = $(library-path) ;
158 self.library-name = $(library-name) ;
159 }
160 }
161
162 rule set-target ( target )
163 {
164 check-not-configured ;
165 self.target = $(target) ;
166 }
167
168 rule check-not-configured ( )
169 {
170 if $(self.include-path) || $(self.library-path) || $(self.library-name) || $(self.target)
171 {
172 errors.user-error [ name ] "is already configured" ;
173 }
174 }
175
176 rule construct ( name : sources * : property-set )
177 {
178 if $(self.target)
179 {
180 return [ $(self.target).generate $(property-set) ] ;
181 }
182 else
183 {
184 local use-environment ;
185 if ! $(self.library-name) && ! $(self.include-path) && ! $(self.library-path)
186 {
187 use-environment = true ;
188 }
189 local libnames = $(self.library-name) ;
190 if ! $(libnames) && $(use-environment)
191 {
192 libnames = [ modules.peek : $(name:U)_NAME ] ;
193 # Backward compatibility only.
194 libnames ?= [ modules.peek : $(name:U)_BINARY ] ;
195 }
196 libnames ?= $(self.default-names) ;
197
198 local include-path = $(self.include-path) ;
199 if ! $(include-path) && $(use-environment)
200 {
201 include-path = [ modules.peek : $(name:U)_INCLUDE ] ;
202 }
203
204 local library-path = $(self.library-path) ;
205 if ! $(library-path) && $(use-environment)
206 {
207 library-path = [ modules.peek : $(name:U)_LIBRARY_PATH ] ;
208 # Backwards compatibility only
209 library-path ?= [ modules.peek : $(name:U)_LIBPATH ] ;
210 }
211
212 local toolset = [ $(property-set).get <toolset> ] ;
213 local toolset-version-property = "<toolset-$(toolset):version>" ;
214 local relevant = [ property.select <target-os> <toolset>
215 $(toolset-version-property) <link> <address-model> <architecture> :
216 [ $(property-set).raw ] ] ;
217
218 local key = ac-library-$(name)-$(relevant:J=-) ;
219 local lookup = [ config-cache.get $(key) ] ;
220
221 if $(lookup)
222 {
223 if $(lookup) = missing
224 {
225 configure.log-library-search-result $(name) : "no (cached)" ;
226 return [ property-set.empty ] ;
227 }
228 else
229 {
230 local includes = $(lookup[1]) ;
231 if $(includes) = %default
232 {
233 includes = ;
234 }
235 local library = [ ac.construct-library $(lookup[2]) :
236 [ $(property-set).refine [ property-set.create $(lookup[3]) ] ] : $(library-path) ] ;
237 configure.log-library-search-result $(name) : "yes (cached)" ;
238 return [ $(library[1]).add-raw <include>$(includes) ] $(library[2-]) ;
239 }
240 }
241 else
242 {
243 local includes = [ ac.find-include-path $(property-set) : $(self.header) : $(include-path) ] ;
244 local library = [ ac.find-library $(property-set) : $(libnames) : $(library-path) ] ;
245 if $(includes) && $(library)
246 {
247 config-cache.set $(key) : $(includes) $(library) ;
248 if $(includes) = %default
249 {
250 includes = ;
251 }
252 library = [ ac.construct-library $(library[1]) :
253 [ $(property-set).refine [ property-set.create $(library[2]) ] ] : $(library-path) ] ;
254 configure.log-library-search-result $(name) : "yes" ;
255 return [ $(library[1]).add-raw <include>$(includes) ] $(library[2-]) ;
256 }
257 else
258 {
259 config-cache.set $(key) : missing ;
260 configure.log-library-search-result $(name) : "no" ;
261 return [ property-set.empty ] ;
262 }
263 }
264 }
265 }
266}
267
268class check-library-worker
269{
270 import property-set ;
271 import targets ;
272 import property ;
273
274 rule __init__ ( target : true-properties * : false-properties * )
275 {
276 self.target = $(target) ;
277 self.true-properties = $(true-properties) ;
278 self.false-properties = $(false-properties) ;
279 }
280
281 rule check ( properties * )
282 {
283 local choosen ;
284 local t = [ targets.current ] ;
285 local p = [ $(t).project ] ;
286 local ps = [ property-set.create $(properties) ] ;
287 ps = [ $(ps).propagated ] ;
288 local generated =
289 [ targets.generate-from-reference $(self.target) : $(p) : $(ps) ] ;
290 if $(generated[2])
291 {
292 choosen = $(self.true-properties) ;
293 }
294 else
295 {
296 choosen = $(self.false-properties) ;
297 }
298 return [ property.evaluate-conditionals-in-context $(choosen) :
299 $(properties) ] ;
300 }
301}
302
303rule check-library ( target : true-properties * : false-properties * )
304{
305 local instance = [ class.new check-library-worker $(target) :
306 $(true-properties) : $(false-properties) ] ;
307 return <conditional>@$(instance).check ;
308}