3
# Copyright (c) 2009 Google Inc. All rights reserved.
4
# Use of this source code is governed by a BSD-style license that can be
5
# found in the LICENSE file.
10
This contains class definitions and supporting functions for generating
11
pieces of SCons files for the different types of GYP targets.
17
def WriteList(fp, list, prefix='',
21
fp.write(preamble or '')
22
fp.write((separator or ' ').join([prefix + l for l in list]))
23
fp.write(postamble or '')
26
class TargetBase(object):
28
Base class for a SCons representation of a GYP target.
33
def __init__(self, spec):
35
def full_product_name(self):
37
Returns the full name of the product being built:
39
* Uses 'product_name' if it's set, else prefix + 'target_name'.
40
* Prepends 'product_dir' if set.
41
* Appends SCons suffix variables for the target type (or
44
suffix = self.target_suffix
45
product_extension = self.spec.get('product_extension')
47
suffix = '.' + product_extension
48
prefix = self.spec.get('product_prefix', self.target_prefix)
49
name = self.spec['target_name']
50
name = prefix + self.spec.get('product_name', name) + suffix
51
product_dir = self.spec.get('product_dir')
53
name = os.path.join(product_dir, name)
55
name = os.path.join(self.out_dir, name)
58
def write_input_files(self, fp):
60
Writes the definition of the input files (sources).
62
sources = self.spec.get('sources')
64
fp.write('\ninput_files = []\n')
66
preamble = '\ninput_files = [\n '
68
WriteList(fp, map(repr, sources), preamble=preamble, postamble=postamble)
70
def builder_call(self):
72
Returns the actual SCons builder call to build this target.
74
name = self.full_product_name()
75
return 'env.%s(env.File(%r), input_files)' % (self.builder_name, name)
76
def write_target(self, fp, src_dir='', pre=''):
78
Writes the lines necessary to build this target.
81
fp.write('_outputs = %s\n' % self.builder_call())
82
fp.write('target_files.extend(_outputs)\n')
85
class NoneTarget(TargetBase):
87
A GYP target type of 'none', implicitly or explicitly.
89
def write_target(self, fp, pre=''):
90
fp.write('\ntarget_files.extend(input_files)\n')
93
class SettingsTarget(TargetBase):
95
A GYP target type of 'settings'.
100
compilable_sources_template = """
102
for infile in input_files:
103
if env.compilable(infile):
104
if (type(infile) == type('')
105
and (infile.startswith(%(src_dir)r)
106
or not os.path.isabs(env.subst(infile)))):
107
# Force files below the build directory by replacing all '..'
108
# elements in the path with '__':
109
base, ext = os.path.splitext(os.path.normpath(infile))
110
base = [d == '..' and '__' or d for d in base.split('/')]
111
base = os.path.join(*base)
112
object = '${OBJ_DIR}/${COMPONENT_NAME}/${TARGET_NAME}/' + base
113
if not infile.startswith(%(src_dir)r):
114
infile = %(src_dir)r + infile
115
infile = env.%(name)s(object, infile)[0]
117
infile = env.%(name)s(infile)[0]
118
_result.append(infile)
119
input_files = _result
122
class CompilableSourcesTargetBase(TargetBase):
124
An abstract base class for targets that compile their source files.
126
We explicitly transform compilable files into object files,
127
even though SCons could infer that for us, because we want
128
to control where the object file ends up. (The implicit rules
129
in SCons always put the object file next to the source file.)
131
intermediate_builder_name = None
132
def write_target(self, fp, src_dir='', pre=''):
133
if self.intermediate_builder_name is None:
134
raise NotImplementedError
135
if src_dir and not src_dir.endswith('/'):
139
'name': self.intermediate_builder_name,
141
fp.write(compilable_sources_template % variables)
142
super(CompilableSourcesTargetBase, self).write_target(fp)
145
class ProgramTarget(CompilableSourcesTargetBase):
147
A GYP target type of 'executable'.
149
builder_name = 'GypProgram'
150
intermediate_builder_name = 'StaticObject'
151
target_prefix = '${PROGPREFIX}'
152
target_suffix = '${PROGSUFFIX}'
153
out_dir = '${TOP_BUILDDIR}'
156
class StaticLibraryTarget(CompilableSourcesTargetBase):
158
A GYP target type of 'static_library'.
160
builder_name = 'GypStaticLibrary'
161
intermediate_builder_name = 'StaticObject'
162
target_prefix = '${LIBPREFIX}'
163
target_suffix = '${LIBSUFFIX}'
164
out_dir = '${LIB_DIR}'
167
class SharedLibraryTarget(CompilableSourcesTargetBase):
169
A GYP target type of 'shared_library'.
171
builder_name = 'GypSharedLibrary'
172
intermediate_builder_name = 'SharedObject'
173
target_prefix = '${SHLIBPREFIX}'
174
target_suffix = '${SHLIBSUFFIX}'
175
out_dir = '${LIB_DIR}'
178
class LoadableModuleTarget(CompilableSourcesTargetBase):
180
A GYP target type of 'loadable_module'.
182
builder_name = 'GypLoadableModule'
183
intermediate_builder_name = 'SharedObject'
184
target_prefix = '${SHLIBPREFIX}'
185
target_suffix = '${SHLIBSUFFIX}'
186
out_dir = '${TOP_BUILDDIR}'
192
'settings' : SettingsTarget,
193
'executable' : ProgramTarget,
194
'static_library' : StaticLibraryTarget,
195
'shared_library' : SharedLibraryTarget,
196
'loadable_module' : LoadableModuleTarget,
200
return TargetMap[spec.get('type')](spec)