903a1c5038c80499c5bef7d969c8696856e995c3
[obnox/samba/samba-obnox.git] / buildtools / wafadmin / Tools / cc.py
1 #!/usr/bin/env python
2 # encoding: utf-8
3 # Thomas Nagy, 2006 (ita)
4
5 "Base for c programs/libraries"
6
7 import os
8 import TaskGen, Build, Utils, Task
9 from Logs import debug
10 import ccroot
11 from TaskGen import feature, before, extension, after
12
13 g_cc_flag_vars = [
14 'CCDEPS', 'FRAMEWORK', 'FRAMEWORKPATH',
15 'STATICLIB', 'LIB', 'LIBPATH', 'LINKFLAGS', 'RPATH',
16 'CCFLAGS', 'CPPPATH', 'CPPFLAGS', 'CCDEFINES']
17
18 EXT_CC = ['.c']
19
20 g_cc_type_vars = ['CCFLAGS', 'LINKFLAGS']
21
22 # TODO remove in waf 1.6
23 class cc_taskgen(ccroot.ccroot_abstract):
24         pass
25
26 @feature('cc')
27 @before('apply_type_vars')
28 @after('default_cc')
29 def init_cc(self):
30         self.p_flag_vars = set(self.p_flag_vars).union(g_cc_flag_vars)
31         self.p_type_vars = set(self.p_type_vars).union(g_cc_type_vars)
32
33         if not self.env['CC_NAME']:
34                 raise Utils.WafError("At least one compiler (gcc, ..) must be selected")
35
36 @feature('cc')
37 @after('apply_incpaths')
38 def apply_obj_vars_cc(self):
39         """after apply_incpaths for INC_PATHS"""
40         env = self.env
41         app = env.append_unique
42         cpppath_st = env['CPPPATH_ST']
43
44         # local flags come first
45         # set the user-defined includes paths
46         for i in env['INC_PATHS']:
47                 app('_CCINCFLAGS', cpppath_st % i.bldpath(env))
48                 app('_CCINCFLAGS', cpppath_st % i.srcpath(env))
49
50         # set the library include paths
51         for i in env['CPPPATH']:
52                 app('_CCINCFLAGS', cpppath_st % i)
53
54 @feature('cc')
55 @after('apply_lib_vars')
56 def apply_defines_cc(self):
57         """after uselib is set for CCDEFINES"""
58         self.defines = getattr(self, 'defines', [])
59         lst = self.to_list(self.defines) + self.to_list(self.env['CCDEFINES'])
60         milst = []
61
62         # now process the local defines
63         for defi in lst:
64                 if not defi in milst:
65                         milst.append(defi)
66
67         # CCDEFINES_
68         libs = self.to_list(self.uselib)
69         for l in libs:
70                 val = self.env['CCDEFINES_'+l]
71                 if val: milst += val
72         self.env['DEFLINES'] = ["%s %s" % (x[0], Utils.trimquotes('='.join(x[1:]))) for x in [y.split('=') for y in milst]]
73         y = self.env['CCDEFINES_ST']
74         self.env.append_unique('_CCDEFFLAGS', [y%x for x in milst])
75
76 @extension(EXT_CC)
77 def c_hook(self, node):
78         # create the compilation task: cpp or cc
79         if getattr(self, 'obj_ext', None):
80                 obj_ext = self.obj_ext
81         else:
82                 obj_ext = '_%d.o' % self.idx
83
84         task = self.create_task('cc', node, node.change_ext(obj_ext))
85         try:
86                 self.compiled_tasks.append(task)
87         except AttributeError:
88                 raise Utils.WafError('Have you forgotten to set the feature "cc" on %s?' % str(self))
89         return task
90
91 cc_str = '${CC} ${CCFLAGS} ${CPPFLAGS} ${_CCINCFLAGS} ${_CCDEFFLAGS} ${CC_SRC_F}${SRC} ${CC_TGT_F}${TGT}'
92 cls = Task.simple_task_type('cc', cc_str, 'GREEN', ext_out='.o', ext_in='.c', shell=False)
93 cls.scan = ccroot.scan
94 cls.vars.append('CCDEPS')
95
96 link_str = '${LINK_CC} ${CCLNK_SRC_F}${SRC} ${CCLNK_TGT_F}${TGT[0].abspath(env)} ${LINKFLAGS}'
97 cls = Task.simple_task_type('cc_link', link_str, color='YELLOW', ext_in='.o', ext_out='.bin', shell=False)
98 cls.maxjobs = 1
99 cls.install = Utils.nada
100