8 Remove from the arguments the presence of the profiler and its output in
9 order to relaunch the script w/o infinite loops.
11 >>> getArgsWithoutoProfilerInfo(['--profilerName', 'igprof', 'myopts.py'])
14 >>> getArgsWithoutoProfilerInfo(['--profilerName=igprof', 'myopts.py'])
17 >>> getArgsWithoutoProfilerInfo(['--profilerName', 'igprof', '--profilerExtraOptions', 'a b c', 'myopts.py'])
20 >>> getArgsWithoutoProfilerInfo(['--profilerName', 'igprof', '--options', 'a b c', 'myopts.py'])
21 ['--options', 'a b c', 'myopts.py']
27 if o.startswith(
'--profile'):
36 Convert the given path to a real path if the pointed file exists, otherwise
39 path = os.path.normpath(os.path.expandvars(path))
40 if os.path.exists(path):
41 path = os.path.realpath(path)
45 _qmt_tmp_opt_files = []
48 Given a .qmt file, return the command line arguments of the corresponding
51 from xml.etree
import ElementTree
as ET
52 global _qmt_tmp_opt_files
54 qmt = ET.parse(qmtfile)
55 args = [a.text
for a
in qmt.findall(
"argument[@name='args']//text")]
56 options = qmt.find(
"argument[@name='options']/text")
58 if options
is not None:
59 from tempfile
import NamedTemporaryFile
61 if re.search(
r"from\s+Gaudi.Configuration\s+import\s+\*"
62 r"|from\s+Configurables\s+import", options.text):
63 tmp_opts = NamedTemporaryFile(suffix=
'.py')
65 tmp_opts = NamedTemporaryFile(suffix=
'.opts')
66 tmp_opts.write(options.text)
68 args.append(tmp_opts.name)
69 _qmt_tmp_opt_files.append(tmp_opts)
73 qmtfile = os.path.abspath(qmtfile)
74 if 'qmtest' in qmtfile.split(os.path.sep):
77 while os.path.basename(testdir) !=
'qmtest':
78 testdir = os.path.dirname(testdir)
84 args =
map(rationalizepath, args)
90 if __name__ ==
"__main__":
92 if os.environ.get(
'LC_ALL') !=
'C':
93 print '# setting LC_ALL to "C"'
94 os.environ[
'LC_ALL'] =
'C'
96 from GaudiKernel
import ROOT6WorkAroundEnabled
99 from ctypes
import cdll
100 cdll.LoadLibrary(
'libCling.so')
101 except (ImportError, OSError):
104 from optparse
import OptionParser
105 parser = OptionParser(usage =
"%prog [options] <opts_file> ...")
106 parser.add_option(
"-n",
"--dry-run", action=
"store_true",
107 help=
"do not run the application, just parse option files")
108 parser.add_option(
"-p",
"--pickle-output", action=
"store", type=
"string",
110 help=
"DEPRECATED: use '--output file.pkl' instead. Write "
111 "the parsed options as a pickle file (static option "
113 parser.add_option(
"-v",
"--verbose", action=
"store_true",
114 help=
"print the parsed options")
115 parser.add_option(
"--old-opts", action=
"store_true",
116 help=
"format printed options in old option files style")
117 parser.add_option(
"--all-opts", action=
"store_true",
118 help=
"print all the option (even if equal to default)")
124 parser.add_option(
"--ncpus", action=
"store", type=
"int", default=0,
125 help=
"start the application in parallel mode using NCPUS processes. "
126 "0 => serial mode (default), -1 => use all CPUs")
129 """Add the option line to a list together with its position in the
132 parser.values.options.append((len(parser.largs), value))
133 parser.add_option(
"--option", action=
"callback", callback=option_cb,
134 type =
"string", nargs = 1,
135 help=
"add a single line (Python) option to the configuration. "
136 "All options lines are executed, one after the other, in "
138 parser.add_option(
"--no-conf-user-apply", action=
"store_true",
139 help=
"disable the automatic application of configurable "
140 "users (for backward compatibility)")
141 parser.add_option(
"--old-conf-user-apply", action=
"store_true",
142 help=
"use the old logic when applying ConfigurableUsers "
143 "(with bug #103803) [default]")
144 parser.add_option(
"--new-conf-user-apply", action=
"store_false",
145 dest=
"old_conf_user_apply",
146 help=
"use the new (correct) logic when applying "
147 "ConfigurableUsers (fixed bug #103803), can be "
148 "turned on also with the environment variable "
149 "GAUDI_FIXED_APPLY_CONF")
150 parser.add_option(
"-o",
"--output", action =
"store", type =
"string",
151 help =
"dump the configuration to a file. The format of "
152 "the options is determined by the extension of the "
153 "file name: .pkl = pickle, .py = python, .opts = "
154 "old style options. The python format cannot be "
155 "used to run the application and it contains the "
156 "same dictionary printed with -v")
157 parser.add_option(
"--post-option", action=
"append", type=
"string",
159 help=
"Python options to be executed after the ConfigurableUser "
161 "All options lines are executed, one after the other, in "
163 parser.add_option(
"--debug", action=
"store_true",
164 help=
"enable some debug print-out")
165 parser.add_option(
"--printsequence", action=
"store_true",
166 help=
"print the sequence")
167 if not sys.platform.startswith(
"win"):
169 parser.add_option(
"-T",
"--tcmalloc", action=
"store_true",
170 help=
"Use the Google malloc replacement. The environment "
171 "variable TCMALLOCLIB can be used to specify a different "
172 "name for the library (the default is libtcmalloc.so)")
173 parser.add_option(
"--preload", action=
"append",
174 help=
"Allow pre-loading of special libraries (e.g. Google "
175 "profiling libraries).")
178 parser.add_option(
"--profilerName", type=
"string",
179 help=
"Select one profiler among: igprofPerf, igprofMem and valgrind<toolname>")
182 parser.add_option(
"--profilerOutput", type=
"string",
183 help=
"Specify the name of the output file for the profiler output")
186 parser.add_option(
"--profilerExtraOptions", type=
"string",
187 help=
"Specify additional options for the profiler. The '--' string should be expressed as '__' (--my-opt becomes __my-opt)")
189 parser.set_defaults(options = [],
193 profilerExtraOptions =
'',
197 old_conf_user_apply=
'GAUDI_FIXED_APPLY_CONF' not in os.environ)
201 for a
in sys.argv[1:]:
202 if a.endswith(
'.qmt')
and os.path.exists(a):
206 if argv != sys.argv[1:]:
207 print '# Running', sys.argv[0],
'with arguments', argv
209 opts, args = parser.parse_args(args=argv)
215 from multiprocessing
import cpu_count
216 sys_cpus = cpu_count()
217 if opts.ncpus > sys_cpus:
218 s =
"Invalid value : --ncpus : only %i cpus available" % sys_cpus
220 elif opts.ncpus < -1 :
221 s =
"Invalid value : --ncpus must be integer >= -1"
231 if opts.old_opts: prefix =
"// "
235 level = logging.DEBUG
237 root_logger = logging.getLogger()
241 opts.preload.insert(0, os.environ.get(
"TCMALLOCLIB",
"libtcmalloc.so"))
244 preload = os.environ.get(
"LD_PRELOAD",
"")
246 preload = preload.replace(
" ",
":").split(
":")
249 for libname
in set(preload).intersection(opts.preload):
250 logging.warning(
"Ignoring preload of library %s because it is "
251 "already in LD_PRELOAD.", libname)
253 for libname
in opts.preload
254 if libname
not in set(preload)]
257 preload =
":".join(preload)
258 os.environ[
"LD_PRELOAD"] = preload
259 logging.info(
"Restarting with LD_PRELOAD='%s'", preload)
262 args = [ a
for a
in sys.argv
if a !=
'-T' and not '--tcmalloc'.startswith(a) ]
263 os.execv(sys.executable, [sys.executable] + args)
266 if opts.profilerName:
267 profilerName = opts.profilerName
268 profilerExecName =
""
269 profilerOutput = opts.profilerOutput
or (profilerName +
".output")
274 igprofPerfOptions =
"-d -pp -z -o igprof.pp.gz".split()
277 if profilerName ==
"igprof":
278 if not opts.profilerOutput:
279 profilerOutput +=
".profile.gz"
280 profilerOptions =
"-d -z -o %s" % profilerOutput
281 profilerExecName =
"igprof"
283 elif profilerName ==
"igprofPerf":
284 if not opts.profilerOutput:
285 profilerOutput +=
".pp.gz"
286 profilerOptions =
"-d -pp -z -o %s" % profilerOutput
287 profilerExecName =
"igprof"
289 elif profilerName ==
"igprofMem":
290 if not opts.profilerOutput:
291 profilerOutput +=
".mp.gz"
292 profilerOptions =
"-d -mp -z -o %s" % profilerOutput
293 profilerExecName =
"igprof"
295 elif "valgrind" in profilerName:
297 if not opts.profilerOutput:
298 profilerOutput +=
".log"
299 toolname = profilerName.replace(
'valgrind',
'')
300 outoption =
"--log-file"
301 if toolname
in (
"massif",
"callgrind",
"cachegrind"):
302 outoption =
"--%s-out-file" % toolname
303 profilerOptions =
"--tool=%s %s=%s" % (toolname, outoption, profilerOutput)
304 profilerExecName =
"valgrind"
307 root_logger.warning(
"Profiler %s not recognized!" % profilerName)
310 if opts.profilerExtraOptions!=
"":
311 profilerExtraOptions = opts.profilerExtraOptions
312 profilerExtraOptions = profilerExtraOptions.replace(
"__",
"--")
313 profilerOptions +=
" %s" % profilerExtraOptions
316 import distutils.spawn
317 profilerPath = distutils.spawn.find_executable(profilerExecName)
319 root_logger.error(
"Cannot locate profiler %s" % profilerExecName)
322 root_logger.info(
"------ Profiling options are on ------ \n"\
324 " o Options: '%s'.\n"\
325 " o Output: %s" % (profilerExecName, profilerOptions, profilerOutput))
328 profilerOptions +=
" python"
331 arglist = [profilerPath] + profilerOptions.split() + args
332 arglist = [ a
for a
in arglist
if a!=
'' ]
336 os.execv(profilerPath, arglist)
340 if opts.pickle_output:
342 root_logger.error(
"Conflicting options: use only --pickle-output or --output")
345 root_logger.warning(
"--pickle-output is deprecated, use --output instead")
346 opts.output = opts.pickle_output
354 options = [
"importOptions(%r)" % f
for f
in args ]
357 optlines = list(opts.options)
359 for pos, l
in optlines:
360 options.insert(pos,l)
368 sys.modules[
"GaudiPython"] =
FakeModule(RuntimeError(
"GaudiPython cannot be used in option files"))
374 exec
"from Gaudi.Configuration import *" in g, l
379 import GaudiKernel.Proxy.Configurable
380 if opts.no_conf_user_apply:
381 logging.info(
"Disabling automatic apply of ConfigurableUser")
383 GaudiKernel.Proxy.Configurable._appliedConfigurableUsers_ =
True
386 if opts.old_conf_user_apply:
387 from GaudiKernel.Proxy.Configurable
import applyConfigurableUsers_old
as applyConfigurableUsers
389 from GaudiKernel.Proxy.Configurable
import applyConfigurableUsers
393 if opts.post_options:
396 exec
"from Gaudi.Configuration import *" in g, l
397 for o
in opts.post_options:
402 c.printconfig(opts.old_opts, opts.all_opts)
404 c.writeconfig(opts.output, opts.all_opts)
406 c.printsequence = opts.printsequence
407 if opts.printsequence:
409 logging.warning(
"--printsequence not supported with --ncpus: ignored")
411 logging.warning(
"--printsequence not supported with --dry-run: ignored")
414 del sys.modules[
"GaudiPython"]
418 sys.exit(c.run(opts.ncpus))