1
2
3
4
5
6
7
8
9
10
11
12
13
14
15 """A user friendly command line interface to access all MadGraph5_aMC@NLO features.
16 Uses the cmd package for command interpretation and tab completion.
17 """
18
19 import os
20 import logging
21 import pydoc
22 import sys
23 import time
24 import optparse
25 import subprocess
26 import shutil
27 import copy
28 import multiprocessing
29 import signal
30 import tempfile
31 import itertools
32 import os
33 import cPickle
34
35
36 import madgraph
37 from madgraph import MG4DIR, MG5DIR, MadGraph5Error
38 import madgraph.interface.extended_cmd as cmd
39 import madgraph.interface.madgraph_interface as mg_interface
40 import madgraph.interface.madevent_interface as me_interface
41 import madgraph.interface.extended_cmd as extended_cmd
42 import madgraph.interface.amcatnlo_run_interface as run_interface
43 import madgraph.interface.launch_ext_program as launch_ext
44 import madgraph.interface.loop_interface as Loop_interface
45 import madgraph.fks.fks_common as fks_common
46 import madgraph.fks.fks_base as fks_base
47 import madgraph.fks.fks_helas_objects as fks_helas
48 import madgraph.iolibs.export_fks as export_fks
49 import madgraph.iolibs.export_v4 as export_v4
50 import madgraph.iolibs.helas_call_writers as helas_call_writers
51 import madgraph.loop.loop_base_objects as loop_base_objects
52 import madgraph.core.diagram_generation as diagram_generation
53 import madgraph.core.helas_objects as helas_objects
54
55 import madgraph.various.cluster as cluster
56 import madgraph.various.misc as misc
57 import madgraph.various.banner as banner_mod
58
59
60 pjoin = os.path.join
61
62
63 logger = logging.getLogger('cmdprint')
64 logger_stderr = logging.getLogger('fatalerror')
65
66
67 glob_directories_map = []
69
70 arglist = glob_directories_map[i]
71
72 curr_exporter = arglist[0]
73 mefile = arglist[1]
74 curr_fortran_model = arglist[2]
75 ime = arglist[3]
76 nme = arglist[4]
77 path = arglist[5]
78 olpopts = arglist[6]
79
80 infile = open(mefile,'rb')
81 me = cPickle.load(infile)
82 infile.close()
83
84 calls = curr_exporter.generate_directories_fks(me, curr_fortran_model, ime, nme, path, olpopts)
85 processes = me.born_me.get('processes')
86
87
88 max_loop_vertex_rank = -99
89 if me.virt_matrix_element:
90 max_loop_vertex_rank = me.virt_matrix_element.get_max_loop_vertex_rank()
91
92 return [calls, curr_exporter.fksdirs, max_loop_vertex_rank, curr_exporter.proc_characteristic, processes]
93
94
95 -class CheckFKS(mg_interface.CheckValidForCmd):
96
97
99 """ Check the arguments of the display diagrams command in the context
100 of the Loop interface."""
101
102 mg_interface.MadGraphCmd.check_display(self,args)
103
104 if args[0] in ['diagrams', 'processes'] and len(args)>=3 \
105 and args[1] not in ['born','loop','virt','real']:
106 raise self.InvalidCmd("Can only display born, loop (virt) or real diagrams, not %s."%args[1])
107
108 if len(args) > 1:
109 if args[1] == 'virt':
110 args[1] = 'loop'
111
117
125
127 """ check the validity of the line"""
128
129 self._export_format = 'NLO'
130 forbidden_formats = ['madevent', 'standalone']
131
132
133 if not hasattr(self, '_fks_multi_proc') or not self._fks_multi_proc:
134 text = 'No processes generated. Please generate a process first.'
135 raise self.InvalidCmd(text)
136
137 if not self._curr_model:
138 text = 'No model found. Please import a model first and then retry.'
139 raise self.InvalidCmd(text)
140
141 if args and args[0][0] != '-':
142 if args[0] in forbidden_formats:
143 text = 'You generated a NLO process, which cannot be exported in %s mode.\n' % args[0]
144 text+= 'Please use the command "output DIR_NAME".\n'
145 raise self.InvalidCmd(text)
146
147
148 path = args.pop(0)
149
150 if path == 'auto':
151 self.get_default_path()
152 elif path != 'auto':
153 self._export_dir = path
154 else:
155
156 self.get_default_path()
157
158 self._export_dir = os.path.realpath(self._export_dir)
159
160
162 """check the validity of the line. args are DIR and MODE
163 MODE being LO, NLO, aMC@NLO or aMC@LO. If no mode is passed, aMC@NLO is used"""
164
165
166
167 if not args:
168 if self._done_export:
169 args.append(self._done_export[0])
170 args.append('auto')
171
172 return
173 else:
174 self.help_launch()
175 raise self.InvalidCmd, \
176 'No default location available, please specify location.'
177
178 if len(args) > 2:
179 self.help_launch()
180 return self.InvalidCmd, 'Invalid Syntax: Too many argument'
181
182 elif len(args) == 2:
183 if not args[1] in ['LO', 'NLO', 'aMC@NLO', 'aMC@LO', 'auto']:
184 raise self.InvalidCmd, '%s is not a valid mode, please use "LO", "NLO", "aMC@NLO" or "aMC@LO"' % args[1]
185 else:
186
187 if args[0] in ['LO', 'NLO', 'aMC@NLO', 'aMC@LO', 'auto'] and self._done_export:
188 args.insert(0, self._done_export[0])
189 elif os.path.isdir(args[0]) or os.path.isdir(pjoin(MG5DIR, args[0]))\
190 or os.path.isdir(pjoin(MG4DIR, args[0])):
191 args.append('auto')
192 else:
193 self.help_launch()
194 raise self.InvalidCmd, '%s is not a valid process directory nor run mode' % args[0]
195
196 mode = args[1]
197
198
199 if os.path.isdir(args[0]):
200 path = os.path.realpath(args[0])
201 elif os.path.isdir(pjoin(MG5DIR,args[0])):
202 path = pjoin(MG5DIR,args[0])
203 elif MG4DIR and os.path.isdir(pjoin(MG4DIR,args[0])):
204 path = pjoin(MG4DIR,args[0])
205 else:
206 raise self.InvalidCmd, '%s is not a valid directory' % args[0]
207 args[0] = path
208
209
210 self._done_export = [path, mode]
211
212
213 if options['multicore'] and options['cluster']:
214 raise self.InvalidCmd, 'options -m (--multicore) and -c (--cluster)' + \
215 ' are not compatible. Please choose one.'
216 if mode == 'NLO' and options['reweightonly']:
217 raise self.InvalidCmd, 'option -r (--reweightonly) needs mode "aMC@NLO" or "aMC@LO"'
218
219
220 -class CheckFKSWeb(mg_interface.CheckValidForCmdWeb, CheckFKS):
222
224
226 """Complete the display command in the context of the FKS interface"""
227
228 args = self.split_arg(line[0:begidx])
229
230 if len(args) == 2 and args[1] in ['diagrams', 'processes']:
231 return self.list_completion(text, ['born', 'loop', 'virt', 'real'])
232 else:
233 return mg_interface.MadGraphCmd.complete_display(self, text, line,
234 begidx, endidx)
235
236
238 """Complete the output command in the context of the FKS interface"""
239
240 forbidden_names = ['MadGraphII', 'Template', 'pythia-pgs', 'CVS',
241 'Calculators', 'MadAnalysis', 'SimpleAnalysis',
242 'mg5', 'DECAY', 'EventConverter', 'Models',
243 'ExRootAnalysis', 'HELAS', 'Transfer_Fct', 'aloha',
244 'madgraph', 'bin', 'tests', 'input', 'vendor', 'models']
245
246
247 args = self.split_arg(line[0:begidx])
248 if len(args) >= 1:
249 if len(args) > 1 and args[1] == 'aloha':
250 try:
251 return self.aloha_complete_output(text, line, begidx, endidx)
252 except Exception, error:
253 print error
254
255 if args[-1].endswith(os.path.sep):
256 return [name for name in self.path_completion(text,
257 pjoin(*[a for a in args if a.endswith(os.path.sep)]),
258 only_dirs = True) if name not in forbidden_names]
259
260
261 content = [name for name in self.path_completion(text, '.', only_dirs = True) \
262 if name not in forbidden_names]
263 return self.list_completion(text, content)
264
265
267 """ complete the launch command"""
268 args = self.split_arg(line[0:begidx])
269
270
271 if args[-1].endswith(os.path.sep):
272 return self.path_completion(text,
273 pjoin(*[a for a in args if a.endswith(os.path.sep)]),
274 only_dirs = True)
275
276 if len(args) == 1:
277 out = {'Path from ./': self.path_completion(text, '.', only_dirs = True)}
278 if MG5DIR != os.path.realpath('.'):
279 out['Path from %s' % MG5DIR] = self.path_completion(text,
280 MG5DIR, only_dirs = True, relative=False)
281 if MG4DIR and MG4DIR != os.path.realpath('.') and MG4DIR != MG5DIR:
282 out['Path from %s' % MG4DIR] = self.path_completion(text,
283 MG4DIR, only_dirs = True, relative=False)
284
285 if len(args) == 2:
286 modes = ['aMC@NLO', 'NLO', 'aMC@LO', 'LO']
287 return self.list_completion(text, modes, line)
288
289
290 if len(args) >= 3:
291 out={}
292
293 if line[0:begidx].endswith('--laststep='):
294 opt = ['parton', 'pythia', 'pgs','delphes','auto']
295 out['Options'] = self.list_completion(text, opt, line)
296 else:
297
298 opt = ['-f', '-c', '-m', '-i', '-x', '-r', '-p', '-o', '-n', 'a',
299 '--force', '--cluster', '--multicore', '--interactive',
300 '--nocompile', '--reweightonly', '--parton', '--only_generation', '--name', '--appl_start_grid']
301 out['Options'] = self.list_completion(text, opt, line)
302
303
304 return self.deal_multiple_categories(out, formatting)
305
306 -class HelpFKS(mg_interface.HelpToCmd):
307
309 mg_interface.MadGraphCmd.help_display(self)
310 logger.info(" In aMC@NLO5, after display diagrams, the user can add the option")
311 logger.info(" \"born\", \"virt\" or \"real\" to display only the corresponding diagrams.")
312
316
317 -class aMCatNLOInterface(CheckFKS, CompleteFKS, HelpFKS, Loop_interface.CommonLoopInterface):
318
319 _fks_display_opts = ['real_diagrams', 'born_diagrams', 'virt_diagrams',
320 'real_processes', 'born_processes', 'virt_processes']
321
322 _nlo_modes_for_completion = ['all','real']
323
324 - def __init__(self, mgme_dir = '', *completekey, **stdin):
325 """ Special init tasks for the Loop Interface """
326 mg_interface.MadGraphCmd.__init__(self, mgme_dir = '', *completekey, **stdin)
327 self.setup()
328
330 """ Special tasks when switching to this interface """
331
332
333
334
335
336
337 self.history.clean(remove_bef_last='import',
338 to_keep=['set','load','import', 'define'])
339
340 self._done_export=False
341 self._curr_amps = diagram_generation.AmplitudeList()
342 self._curr_matrix_elements = helas_objects.HelasMultiProcess()
343 self._v4_export_formats = []
344 self._nlo_modes_for_completion = ['all','real']
345 self._export_formats = [ 'madevent', 'aloha' ]
346
347
348 self.validate_model(loop_type='real_init', stop=False)
349
350
351
352 self._cuttools_dir=str(pjoin(self._mgme_dir,'vendor','CutTools'))
353 if not os.path.isdir(pjoin(self._cuttools_dir, 'src','cts')):
354 logger.warning(('Warning: Directory %s is not a valid CutTools directory.'+\
355 'Using default CutTools instead.') % \
356 self._cuttools_dir)
357 self._cuttools_dir=str(pjoin(self._mgme_dir,'vendor','CutTools'))
358
359 self._iregi_dir=str(os.path.join(self._mgme_dir,'vendor','IREGI','src'))
360 if not os.path.isdir(self._iregi_dir):
361 logger.warning(('Warning: Directory %s is not a valid IREGI directory.'+\
362 'Using default IREGI instead.')%\
363 self._iregi_dir)
364 self._iregi_dir=str(os.path.join(self._mgme_dir,'vendor','IREGI','src'))
365
367
368 args = self.split_arg(line)
369
370 self.check_display(args)
371
372 if args[0] in ['diagrams', 'processes', 'diagrams_text']:
373 get_amps_dict = {'real': self._fks_multi_proc.get_real_amplitudes,
374 'born': self._fks_multi_proc.get_born_amplitudes,
375 'loop': self._fks_multi_proc.get_virt_amplitudes}
376 if args[0] == 'diagrams':
377 if len(args)>=2 and args[1] in get_amps_dict.keys():
378 get_amps = get_amps_dict[args[1]]
379 self._curr_amps = get_amps()
380
381 if args[1] == 'loop' and len(self._curr_amps) == 0:
382 raise self.InvalidCmd('No virtuals have been generated')
383 self.draw(' '.join(args[2:]),type = args[1])
384 else:
385 for diag_type, get_amps in get_amps_dict.items():
386 self._curr_amps = get_amps()
387 if self._curr_amps:
388 self.draw(' '.join(args[1:]), Dtype=diag_type)
389
390
391 self._curr_amps = diagram_generation.AmplitudeList()
392
393 if args[0] == 'diagrams_text':
394 if len(args)>=2 and args[1] in get_amps_dict.keys():
395 get_amps = get_amps_dict[args[1]]
396 self._curr_amps = get_amps()
397
398 if args[1] in ['virt', 'loop'] and len(self._curr_amps) == 0:
399 raise self.InvalidCmd('No virtuals have been generated')
400 text = "\n".join([amp.nice_string() for amp in self._curr_amps])
401 else:
402 text = 'Born diagrams:\n'
403 text += '\n'.join(amp.nice_string() for amp in get_amps_dict['born']())
404 text += '\n\nReal diagrams:'
405 text += '\n'.join(amp.nice_string() for amp in get_amps_dict['real']())
406 text += '\n\nLoop diagrams:\n'
407 text += '\n'.join(amp.nice_string() for amp in get_amps_dict['loop']())
408 pydoc.pager(text)
409
410
411 self._curr_amps = diagram_generation.AmplitudeList()
412
413 elif args[0] == 'processes':
414 if len(args)>=2 and args[1] in get_amps_dict.keys():
415 get_amps = get_amps_dict[args[1]]
416 self._curr_amps = get_amps()
417
418 if args[1] in ['virt', 'loop'] and len(self._curr_amps) == 0:
419 raise self.InvalidCmd('No virtuals have been generated')
420 print '\n'.join(amp.nice_string_processes() for amp in self._curr_amps)
421 else:
422 print 'Born processes:'
423 print '\n'.join(amp.nice_string_processes() for amp in get_amps_dict['born']())
424 print 'Real processes:'
425 print '\n'.join(amp.nice_string_processes() for amp in get_amps_dict['real']())
426 print 'Loop processes:'
427 print '\n'.join(amp.nice_string_processes() for amp in get_amps_dict['loop']())
428
429 self._curr_amps = diagram_generation.AmplitudeList()
430
431 else:
432 mg_interface.MadGraphCmd.do_display(self,line,output)
433
434 - def do_add(self, line, *args,**opt):
435
436 args = self.split_arg(line)
437
438 self.check_add(args)
439
440 if args[0] == 'model':
441 return self.add_model(args[1:])
442 elif args[0] != 'process':
443 raise self.InvalidCmd("The add command can only be used with process or model")
444 else:
445 line = ' '.join(args[1:])
446
447 proc_type=self.extract_process_type(line)
448 if proc_type[1] not in ['real', 'LOonly']:
449 run_interface.check_compiler(self.options, block=False)
450
451
452 geninfo = self._generate_info
453 self.validate_model(proc_type[1], coupling_type=proc_type[2])
454 self._generate_info = geninfo
455
456
457
458 collect_mirror_procs = False
459 ignore_six_quark_processes = self.options['ignore_six_quark_processes']
460 if ',' in line:
461 myprocdef, line = mg_interface.MadGraphCmd.extract_decay_chain_process(self,line)
462 if myprocdef.are_decays_perturbed():
463 raise MadGraph5Error("Decay processes cannot be perturbed")
464 else:
465 myprocdef = mg_interface.MadGraphCmd.extract_process(self,line)
466
467 self.proc_validity(myprocdef,'aMCatNLO_%s'%proc_type[1])
468
469
470
471
472
473 if myprocdef['orders'] and not all([o in myprocdef['orders'].keys() for o in myprocdef['model'].get_coupling_orders()]):
474 for o in myprocdef['model'].get_coupling_orders():
475 if o not in myprocdef['orders'].keys():
476 myprocdef['orders'][o] = 0
477 logger.warning(('%s order is missing in the process definition. It will be set to 0.\n' + \
478 'If this is not what you need, please regenerate with the correct orders.') % o)
479
480
481 if not myprocdef['orders']:
482
483
484 weighted = diagram_generation.MultiProcess.find_optimal_process_orders(myprocdef)
485 if not weighted:
486 raise MadGraph5Error,'\nProcess orders cannot be determined automatically. \n' + \
487 'Please specify them from the command line.'
488
489
490 qed, qcd = fks_common.get_qed_qcd_orders_from_weighted(len(myprocdef['legs']), weighted['WEIGHTED'])
491 if qed < 0 or qcd < 0:
492 raise MadGraph5Error,'\nAutomatic process-order determination lead to negative constraints:\n' + \
493 ('QED: %d, QCD: %d\n' % (qed, qcd)) + \
494 'Please specify the coupling orders from the command line.'
495 orders = {'QED': qed, 'QCD': qcd}
496
497 for o in myprocdef['model'].get_coupling_orders():
498 if o not in ['QED', 'QCD']:
499 orders[o] = 0
500
501 myprocdef.set('orders', orders)
502
503 logger.info(('Setting the born orders automatically in the process definition to %s.\n' + \
504 'If this is not what you need, please regenerate with the correct orders.'),
505 ' '.join(['%s<=%s' %(k,v) if v else '%s=%s' % (k,v) for k,v in myprocdef['orders'].items()]),
506 '$MG:BOLD')
507
508 myprocdef['born_orders'] = copy.copy(myprocdef['orders'])
509
510
511 myprocdef['split_orders'] += [o for o in myprocdef['model'].get('coupling_orders') \
512 if o not in myprocdef['split_orders']]
513
514
515 if not myprocdef['squared_orders']:
516 for ord, val in myprocdef['orders'].items():
517 myprocdef['squared_orders'][ord] = 2 * val
518
519
520 for pert in myprocdef['perturbation_couplings']:
521
522 if myprocdef['orders'].keys() != ['WEIGHTED']:
523 try:
524 myprocdef['orders'][pert] += 2
525 except KeyError:
526
527
528 myprocdef['orders'][pert] = 99
529 try:
530 myprocdef['squared_orders'][pert] += 2
531 except KeyError:
532 myprocdef['squared_orders'][pert] = 200
533
534
535 if 'WEIGHTED' in myprocdef['orders'].keys():
536 myprocdef['orders']['WEIGHTED'] += 1 * \
537 max([myprocdef.get('model').get('order_hierarchy')[ord] for \
538 ord in myprocdef['perturbation_couplings']])
539
540 myprocdef['squared_orders']['WEIGHTED'] += 2 * \
541 max([myprocdef.get('model').get('order_hierarchy')[ord] for \
542 ord in myprocdef['perturbation_couplings']])
543
544
545 myprocdef['perturbation_couplings'] = list(myprocdef['model']['coupling_orders'])
546
547
548 myprocdef['orders'] = {}
549 self._curr_proc_defs.append(myprocdef)
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568 if self.options['low_mem_multicore_nlo_generation']:
569 if self.options['nb_core']:
570 self.ncores_for_proc_gen = int(self.options['nb_core'])
571 else:
572 self.ncores_for_proc_gen = -1
573 else:
574 self.ncores_for_proc_gen = 0
575
576
577 fks_options = {'OLP': self.options['OLP'],
578 'ignore_six_quark_processes': self.options['ignore_six_quark_processes'],
579 'init_lep_split': self.options['include_lepton_initiated_processes'],
580 'ncores_for_proc_gen': self.ncores_for_proc_gen}
581 try:
582 self._fks_multi_proc.add(fks_base.FKSMultiProcess(myprocdef,fks_options))
583 except AttributeError:
584 self._fks_multi_proc = fks_base.FKSMultiProcess(myprocdef,fks_options)
585
586
588 """Main commands: Initialize a new Template or reinitialize one"""
589
590 args = self.split_arg(line)
591
592 self.check_output(args)
593
594 noclean = '-noclean' in args
595 force = '-f' in args
596 nojpeg = '-nojpeg' in args
597 main_file_name = ""
598 try:
599 main_file_name = args[args.index('-name') + 1]
600 except Exception:
601 pass
602
603
604 group_processes = False
605
606 if self._export_format in ['NLO']:
607 self._curr_exporter = export_v4.ExportV4Factory(self, noclean,
608 output_type='amcatnlo',group_subprocesses=group_processes)
609
610 self._curr_exporter.pass_information_from_cmd(self)
611
612
613 if not force and not noclean and os.path.isdir(self._export_dir)\
614 and self._export_format in ['NLO']:
615
616 logger.info('INFO: directory %s already exists.' % self._export_dir)
617 logger.info('If you continue this directory will be deleted and replaced.')
618 answer = self.ask('Do you want to continue?', 'y', ['y','n'],
619 timeout=self.options['timeout'])
620 if answer != 'y':
621 raise self.InvalidCmd('Stopped by user request')
622
623
624
625 if os.path.exists(self._export_dir):
626 shutil.rmtree(self._export_dir)
627
628
629 if self._export_format in ['NLO']:
630 self._curr_exporter.copy_fkstemplate()
631
632
633 self._done_export = False
634
635
636 self.export(nojpeg, main_file_name, group_processes=group_processes)
637
638
639 self._curr_exporter.pass_information_from_cmd(self)
640
641
642 self.finalize(nojpeg)
643
644
645 if self.options['OLP']!='MadLoop':
646 self._curr_exporter.generate_virtuals_from_OLP(
647 self.born_processes_for_olp,self._export_dir,self.options['OLP'])
648
649
650 self._done_export = (self._export_dir, self._export_format)
651
652
653 self._export_dir = None
654
655
656 - def export(self, nojpeg = False, main_file_name = "", group_processes=False):
728
729
730
731 ndiags, cpu_time = generate_matrix_elements(self, group=group_processes)
732 calls = 0
733
734 path = self._export_dir
735
736 if self._export_format in ['NLO']:
737 path = os.path.join(path, 'SubProcesses')
738
739
740 self._fks_directories = []
741 proc_charac = self._curr_exporter.proc_characteristic
742 for charac in ['has_isr', 'has_fsr', 'has_loops']:
743 proc_charac[charac] = self._curr_matrix_elements[charac]
744
745
746
747 global glob_directories_map
748 glob_directories_map = []
749
750
751 self.born_processes_for_olp = []
752 self.born_processes = []
753 for ime, me in \
754 enumerate(self._curr_matrix_elements.get('matrix_elements')):
755 if not self.options['low_mem_multicore_nlo_generation']:
756
757 calls = calls + \
758 self._curr_exporter.generate_directories_fks(me,
759 self._curr_helas_model,
760 ime, len(self._curr_matrix_elements.get('matrix_elements')),
761 path,self.options['OLP'])
762 self._fks_directories.extend(self._curr_exporter.fksdirs)
763 self.born_processes_for_olp.append(me.born_me.get('processes')[0])
764 self.born_processes.append(me.born_me.get('processes'))
765 else:
766 glob_directories_map.append(\
767 [self._curr_exporter, me, self._curr_helas_model,
768 ime, len(self._curr_matrix_elements.get('matrix_elements')),
769 path, self.options['OLP']])
770
771 if self.options['low_mem_multicore_nlo_generation']:
772
773 logger.info('Writing directories...')
774 original_sigint_handler = signal.signal(signal.SIGINT, signal.SIG_IGN)
775 if self.ncores_for_proc_gen < 0:
776 pool = multiprocessing.Pool(maxtasksperchild=1)
777 else:
778 pool = multiprocessing.Pool(processes=self.ncores_for_proc_gen,maxtasksperchild=1)
779 signal.signal(signal.SIGINT, original_sigint_handler)
780 try:
781
782
783 diroutputmap = pool.map_async(generate_directories_fks_async,
784 range(len(glob_directories_map))).get(9999999)
785 except KeyboardInterrupt:
786 pool.terminate()
787 raise KeyboardInterrupt
788
789 pool.close()
790 pool.join()
791
792
793 for mefile in self._curr_matrix_elements.get('matrix_elements'):
794 os.remove(mefile)
795
796 for charac in ['nexternal', 'ninitial', 'splitting_types']:
797 proc_charac[charac] = self._curr_exporter.proc_characteristic[charac]
798
799 proc_charac['nexternal'] = max([diroutput[3]['nexternal'] for diroutput in diroutputmap])
800 ninitial_set = set([diroutput[3]['ninitial'] for diroutput in diroutputmap])
801 if len(ninitial_set) != 1:
802 raise MadGraph5Error, ("Invalid ninitial values: %s" % ' ,'.join(list(ninitial_set)))
803 proc_charac['ninitial'] = list(ninitial_set)[0]
804
805 self.born_processes = []
806 self.born_processes_for_olp = []
807 max_loop_vertex_ranks = []
808
809
810 splitting_types = set(proc_charac['splitting_types'])
811 for diroutput in diroutputmap:
812 splitting_types = splitting_types.union(set(diroutput[3]['splitting_types']))
813 calls = calls + diroutput[0]
814 self._fks_directories.extend(diroutput[1])
815 max_loop_vertex_ranks.append(diroutput[2])
816 self.born_processes.extend(diroutput[4])
817 self.born_processes_for_olp.append(diroutput[4][0])
818
819
820 proc_charac['splitting_types'] = list(splitting_types)
821
822 else:
823 max_loop_vertex_ranks = [me.get_max_loop_vertex_rank() for \
824 me in self._curr_matrix_elements.get_virt_matrix_elements()]
825
826 card_path = os.path.join(path, os.path.pardir, 'SubProcesses', \
827 'procdef_mg5.dat')
828
829 if self.options['loop_optimized_output'] and \
830 len(max_loop_vertex_ranks) > 0:
831 self._curr_exporter.write_coef_specs_file(max_loop_vertex_ranks)
832 if self._generate_info:
833 self._curr_exporter.write_procdef_mg5(card_path,
834 self._curr_model['name'],
835 self._generate_info)
836 try:
837 cmd.Cmd.onecmd(self, 'history .')
838 except Exception:
839 logger.debug('fail to run command \"history cmd\"')
840 pass
841 subproc_path = os.path.join(path, os.path.pardir, 'SubProcesses', \
842 'initial_states_map.dat')
843 self._curr_exporter.write_init_map(subproc_path,
844 self._curr_matrix_elements.get('initial_states'))
845
846 cpu_time1 = time.time()
847
848
850 """Main commands: Ask for editing the parameters and then execute the code (NLO or aMC@(N)LO)
851 """
852 old_cwd = os.getcwd()
853 argss = self.split_arg(line)
854
855 (options, argss) = _launch_parser.parse_args(argss)
856 options = options.__dict__
857 self.check_launch(argss, options)
858 if not os.path.isdir(os.path.join(os.getcwd(), argss[0], 'Events')):
859 self.do_switch('ML5')
860 return mg_interface.MadGraphCmd.do_launch(self,line)
861
862
863
864
865 if options['interactive']:
866 if isinstance(self, extended_cmd.CmdShell):
867 ME = run_interface.aMCatNLOCmdShell(me_dir=argss[0], options=self.options)
868 else:
869 ME = run_interface.aMCatNLOCmd(me_dir=argss[0],options=self.options)
870 ME.pass_in_web_mode()
871
872 config_line = [l for l in self.history if l.strip().startswith('set')]
873 for line in config_line:
874 ME.exec_cmd(line)
875 stop = self.define_child_cmd_interface(ME)
876 return stop
877
878 ext_program = launch_ext.aMCatNLOLauncher(argss[0], self, run_mode=argss[1],
879 shell = isinstance(self, extended_cmd.CmdShell),
880 **options)
881 ext_program.run()
882
883
884
887
888 _launch_usage = "launch [DIRPATH] [MODE] [options]\n" + \
889 "-- execute the aMC@NLO output present in DIRPATH\n" + \
890 " By default DIRPATH is the latest created directory\n" + \
891 " MODE can be either LO, NLO, aMC@NLO or aMC@LO (if omitted, it is asked in a separate question)\n" + \
892 " If mode is set to LO/NLO, no event generation will be performed, but only the \n" + \
893 " computation of the total cross-section and the filling of parton-level histograms \n" + \
894 " specified in the DIRPATH/SubProcesses/madfks_plot.f file.\n" + \
895 " If mode is set to aMC@LO/aMC@NLO, after the cross-section computation, a .lhe \n" + \
896 " event file is generated which will be showered with the MonteCarlo specified \n" + \
897 " in the run_card.dat\n"
898
899 _launch_parser = misc.OptionParser(usage=_launch_usage)
900 _launch_parser.add_option("-f", "--force", default=False, action='store_true',
901 help="Use the card present in the directory for the launch, without editing them")
902 _launch_parser.add_option("-c", "--cluster", default=False, action='store_true',
903 help="Submit the jobs on the cluster")
904 _launch_parser.add_option("-i", "--interactive", default=False, action='store_true',
905 help="Use interactive consol")
906 _launch_parser.add_option("-m", "--multicore", default=False, action='store_true',
907 help="Submit the jobs on multicore mode")
908 _launch_parser.add_option("-x", "--nocompile", default=False, action='store_true',
909 help="Skip compilation. Ignored if no executable is found")
910 _launch_parser.add_option("-r", "--reweightonly", default=False, action='store_true',
911 help="Skip integration and event generation, just run reweight on the" + \
912 " latest generated event files (see list in SubProcesses/nevents_unweighted)")
913 _launch_parser.add_option("-p", "--parton", default=False, action='store_true',
914 help="Stop the run after the parton level file generation (you need " + \
915 "to shower the file in order to get physical results)")
916 _launch_parser.add_option("-o", "--only_generation", default=False, action='store_true',
917 help="Skip grid set up, just generate events starting from " + \
918 "the last available results")
919
920
921 _launch_parser.add_option("-n", "--name", default=False, dest='name',
922 help="Provide a name to the run")
923 _launch_parser.add_option("-a", "--appl_start_grid", default=False, dest='appl_start_grid',
924 help="For use with APPLgrid only: start from existing grids")
925 _launch_parser.add_option("-R", "--reweight", default=False, action='store_true',
926 help="Run the reweight module (reweighting by different model parameter")
927 _launch_parser.add_option("-M", "--madspin", default=False, action='store_true',
928 help="Run the madspin package")
929