SConscript (8232:b28d06a175be) SConscript (8233:15b5ea80fd95)
1# -*- mode:python -*-
2
3# Copyright (c) 2004-2005 The Regents of The University of Michigan
4# All rights reserved.
5#
6# Redistribution and use in source and binary forms, with or without
7# modification, are permitted provided that the following conditions are
8# met: redistributions of source code must retain the above copyright

--- 42 unchanged lines hidden (view full) ---

51
52build_env = [(opt, env[opt]) for opt in export_vars]
53
54from m5.util import code_formatter
55
56########################################################################
57# Code for adding source files of various types
58#
1# -*- mode:python -*-
2
3# Copyright (c) 2004-2005 The Regents of The University of Michigan
4# All rights reserved.
5#
6# Redistribution and use in source and binary forms, with or without
7# modification, are permitted provided that the following conditions are
8# met: redistributions of source code must retain the above copyright

--- 42 unchanged lines hidden (view full) ---

51
52build_env = [(opt, env[opt]) for opt in export_vars]
53
54from m5.util import code_formatter
55
56########################################################################
57# Code for adding source files of various types
58#
59# When specifying a source file of some type, a set of guards can be
60# specified for that file. When get() is used to find the files, if
61# get specifies a set of filters, only files that match those filters
62# will be accepted (unspecified filters on files are assumed to be
63# false). Current filters are:
64# main -- specifies the m5 main() function
65# skip_lib -- do not put this file into the m5 library
66# <unittest> -- unit tests use filters based on the unit test name
67#
68# A parent can now be specified for a source file and default filter
69# values will be retrieved recursively from parents (children override
70# parents).
71#
59class SourceMeta(type):
72class SourceMeta(type):
73 '''Meta class for source files that keeps track of all files of a
74 particular type and has a get function for finding all functions
75 of a certain type that match a set of guards'''
60 def __init__(cls, name, bases, dict):
61 super(SourceMeta, cls).__init__(name, bases, dict)
62 cls.all = []
63
76 def __init__(cls, name, bases, dict):
77 super(SourceMeta, cls).__init__(name, bases, dict)
78 cls.all = []
79
64 def get(cls, **kwargs):
80 def get(cls, **guards):
81 '''Find all files that match the specified guards. If a source
82 file does not specify a flag, the default is False'''
65 for src in cls.all:
83 for src in cls.all:
66 for attr,value in kwargs.iteritems():
67 if getattr(src, attr) != value:
84 for flag,value in guards.iteritems():
85 # if the flag is found and has a different value, skip
86 # this file
87 if src.all_guards.get(flag, False) != value:
68 break
69 else:
70 yield src
71
72class SourceFile(object):
88 break
89 else:
90 yield src
91
92class SourceFile(object):
93 '''Base object that encapsulates the notion of a source file.
94 This includes, the source node, target node, various manipulations
95 of those. A source file also specifies a set of guards which
96 describing which builds the source file applies to. A parent can
97 also be specified to get default guards from'''
73 __metaclass__ = SourceMeta
98 __metaclass__ = SourceMeta
74 def __init__(self, source):
99 def __init__(self, source, parent=None, **guards):
100 self.guards = guards
101 self.parent = parent
102
75 tnode = source
76 if not isinstance(source, SCons.Node.FS.File):
77 tnode = File(source)
78
79 self.tnode = tnode
80 self.snode = tnode.srcnode()
103 tnode = source
104 if not isinstance(source, SCons.Node.FS.File):
105 tnode = File(source)
106
107 self.tnode = tnode
108 self.snode = tnode.srcnode()
81 self.filename = str(tnode)
82 self.dirname = dirname(self.filename)
83 self.basename = basename(self.filename)
84 index = self.basename.rfind('.')
85 if index <= 0:
86 # dot files aren't extensions
87 self.extname = self.basename, None
88 else:
89 self.extname = self.basename[:index], self.basename[index+1:]
90
91 for base in type(self).__mro__:
92 if issubclass(base, SourceFile):
93 base.all.append(self)
94
109
110 for base in type(self).__mro__:
111 if issubclass(base, SourceFile):
112 base.all.append(self)
113
114 @property
115 def filename(self):
116 return str(self.tnode)
117
118 @property
119 def dirname(self):
120 return dirname(self.filename)
121
122 @property
123 def basename(self):
124 return basename(self.filename)
125
126 @property
127 def extname(self):
128 index = self.basename.rfind('.')
129 if index <= 0:
130 # dot files aren't extensions
131 return self.basename, None
132
133 return self.basename[:index], self.basename[index+1:]
134
135 @property
136 def all_guards(self):
137 '''find all guards for this object getting default values
138 recursively from its parents'''
139 guards = {}
140 if self.parent:
141 guards.update(self.parent.guards)
142 guards.update(self.guards)
143 return guards
144
95 def __lt__(self, other): return self.filename < other.filename
96 def __le__(self, other): return self.filename <= other.filename
97 def __gt__(self, other): return self.filename > other.filename
98 def __ge__(self, other): return self.filename >= other.filename
99 def __eq__(self, other): return self.filename == other.filename
100 def __ne__(self, other): return self.filename != other.filename
101
102class Source(SourceFile):
103 '''Add a c/c++ source file to the build'''
145 def __lt__(self, other): return self.filename < other.filename
146 def __le__(self, other): return self.filename <= other.filename
147 def __gt__(self, other): return self.filename > other.filename
148 def __ge__(self, other): return self.filename >= other.filename
149 def __eq__(self, other): return self.filename == other.filename
150 def __ne__(self, other): return self.filename != other.filename
151
152class Source(SourceFile):
153 '''Add a c/c++ source file to the build'''
104 def __init__(self, source, Werror=True, swig=False, bin_only=False,
105 skip_lib=False):
106 super(Source, self).__init__(source)
154 def __init__(self, source, Werror=True, swig=False, **guards):
155 '''specify the source file, and any guards'''
156 super(Source, self).__init__(source, **guards)
107
108 self.Werror = Werror
109 self.swig = swig
157
158 self.Werror = Werror
159 self.swig = swig
110 self.bin_only = bin_only
111 self.skip_lib = bin_only or skip_lib
112
113class PySource(SourceFile):
114 '''Add a python source file to the named package'''
115 invalid_sym_char = re.compile('[^A-z0-9_]')
116 modules = {}
117 tnodes = {}
118 symnames = {}
119
160
161class PySource(SourceFile):
162 '''Add a python source file to the named package'''
163 invalid_sym_char = re.compile('[^A-z0-9_]')
164 modules = {}
165 tnodes = {}
166 symnames = {}
167
120 def __init__(self, package, source):
121 super(PySource, self).__init__(source)
168 def __init__(self, package, source, **guards):
169 '''specify the python package, the source file, and any guards'''
170 super(PySource, self).__init__(source, **guards)
122
123 modname,ext = self.extname
124 assert ext == 'py'
125
126 if package:
127 path = package.split('.')
128 else:
129 path = []

--- 23 unchanged lines hidden (view full) ---

153
154class SimObject(PySource):
155 '''Add a SimObject python file as a python source object and add
156 it to a list of sim object modules'''
157
158 fixed = False
159 modnames = []
160
171
172 modname,ext = self.extname
173 assert ext == 'py'
174
175 if package:
176 path = package.split('.')
177 else:
178 path = []

--- 23 unchanged lines hidden (view full) ---

202
203class SimObject(PySource):
204 '''Add a SimObject python file as a python source object and add
205 it to a list of sim object modules'''
206
207 fixed = False
208 modnames = []
209
161 def __init__(self, source):
162 super(SimObject, self).__init__('m5.objects', source)
210 def __init__(self, source, **guards):
211 '''Specify the source file and any guards (automatically in
212 the m5.objects package)'''
213 super(SimObject, self).__init__('m5.objects', source, **guards)
163 if self.fixed:
164 raise AttributeError, "Too late to call SimObject now."
165
166 bisect.insort_right(SimObject.modnames, self.modname)
167
168class SwigSource(SourceFile):
169 '''Add a swig file to build'''
170
214 if self.fixed:
215 raise AttributeError, "Too late to call SimObject now."
216
217 bisect.insort_right(SimObject.modnames, self.modname)
218
219class SwigSource(SourceFile):
220 '''Add a swig file to build'''
221
171 def __init__(self, package, source):
172 super(SwigSource, self).__init__(source)
222 def __init__(self, package, source, **guards):
223 '''Specify the python package, the source file, and any guards'''
224 super(SwigSource, self).__init__(source, **guards)
173
174 modname,ext = self.extname
175 assert ext == 'i'
176
177 self.module = modname
178 cc_file = joinpath(self.dirname, modname + '_wrap.cc')
179 py_file = joinpath(self.dirname, modname + '.py')
180
225
226 modname,ext = self.extname
227 assert ext == 'i'
228
229 self.module = modname
230 cc_file = joinpath(self.dirname, modname + '_wrap.cc')
231 py_file = joinpath(self.dirname, modname + '.py')
232
181 self.cc_source = Source(cc_file, swig=True)
182 self.py_source = PySource(package, py_file)
233 self.cc_source = Source(cc_file, swig=True, parent=self)
234 self.py_source = PySource(package, py_file, parent=self)
183
184unit_tests = []
185def UnitTest(target, sources):
235
236unit_tests = []
237def UnitTest(target, sources):
238 '''Create a unit test, specify the target name and a source or
239 list of sources'''
186 if not isinstance(sources, (list, tuple)):
187 sources = [ sources ]
188
189 sources = [ Source(src, skip_lib=True) for src in sources ]
190 unit_tests.append((target, sources))
191
192# Children should have access
193Export('Source')

--- 636 unchanged lines hidden (view full) ---

830 else:
831 obj = env.SharedObject(source.tnode)
832
833 if extra_deps:
834 env.Depends(obj, extra_deps)
835
836 return obj
837
240 if not isinstance(sources, (list, tuple)):
241 sources = [ sources ]
242
243 sources = [ Source(src, skip_lib=True) for src in sources ]
244 unit_tests.append((target, sources))
245
246# Children should have access
247Export('Source')

--- 636 unchanged lines hidden (view full) ---

884 else:
885 obj = env.SharedObject(source.tnode)
886
887 if extra_deps:
888 env.Depends(obj, extra_deps)
889
890 return obj
891
838 static_objs = [ make_obj(s, True) for s in Source.get(skip_lib=False)]
839 shared_objs = [ make_obj(s, False) for s in Source.get(skip_lib=False)]
892 sources = Source.get(main=False, skip_lib=False)
893 static_objs = [ make_obj(s, True) for s in sources ]
894 shared_objs = [ make_obj(s, False) for s in sources ]
840
841 static_date = make_obj(date_source, static=True, extra_deps=static_objs)
842 static_objs.append(static_date)
843
844 shared_date = make_obj(date_source, static=False, extra_deps=shared_objs)
845 shared_objs.append(shared_date)
846
847 # First make a library of everything but main() so other programs can
848 # link against m5.
849 static_lib = new_env.StaticLibrary(libname, static_objs)
850 shared_lib = new_env.SharedLibrary(libname, shared_objs)
851
852 for target, sources in unit_tests:
853 objs = [ make_obj(s, static=True) for s in sources ]
854 new_env.Program("unittest/%s.%s" % (target, label), objs + static_objs)
855
856 # Now link a stub with main() and the static library.
895
896 static_date = make_obj(date_source, static=True, extra_deps=static_objs)
897 static_objs.append(static_date)
898
899 shared_date = make_obj(date_source, static=False, extra_deps=shared_objs)
900 shared_objs.append(shared_date)
901
902 # First make a library of everything but main() so other programs can
903 # link against m5.
904 static_lib = new_env.StaticLibrary(libname, static_objs)
905 shared_lib = new_env.SharedLibrary(libname, shared_objs)
906
907 for target, sources in unit_tests:
908 objs = [ make_obj(s, static=True) for s in sources ]
909 new_env.Program("unittest/%s.%s" % (target, label), objs + static_objs)
910
911 # Now link a stub with main() and the static library.
857 bin_objs = [make_obj(s, True) for s in Source.get(bin_only=True) ]
912 main_objs = [ make_obj(s, True) for s in Source.get(main=True) ]
913
858 progname = exename
859 if strip:
860 progname += '.unstripped'
861
914 progname = exename
915 if strip:
916 progname += '.unstripped'
917
862 targets = new_env.Program(progname, bin_objs + static_objs)
918 targets = new_env.Program(progname, main_objs + static_objs)
863
864 if strip:
865 if sys.platform == 'sunos5':
866 cmd = 'cp $SOURCE $TARGET; strip $TARGET'
867 else:
868 cmd = 'strip $SOURCE -o $TARGET'
869 targets = new_env.Command(exename, progname,
870 MakeAction(cmd, Transform("STRIP")))

--- 49 unchanged lines hidden ---
919
920 if strip:
921 if sys.platform == 'sunos5':
922 cmd = 'cp $SOURCE $TARGET; strip $TARGET'
923 else:
924 cmd = 'strip $SOURCE -o $TARGET'
925 targets = new_env.Command(exename, progname,
926 MakeAction(cmd, Transform("STRIP")))

--- 49 unchanged lines hidden ---