1
# -*- coding: iso-8859-1 -*-
1
# -*- coding: utf-8 -*-
3
3
#-------------------------------------------------------------------------------
5
# This file is part of the Code_Saturne User Interface, element of the
6
# Code_Saturne CFD tool.
8
# Copyright (C) 1998-2009 EDF S.A., France
10
# contact: saturne-support@edf.fr
12
# The Code_Saturne User Interface is free software; you can redistribute it
13
# and/or modify it under the terms of the GNU General Public License
14
# as published by the Free Software Foundation; either version 2 of
15
# the License, or (at your option) any later version.
17
# The Code_Saturne User Interface is distributed in the hope that it will be
18
# useful, but WITHOUT ANY WARRANTY; without even the implied warranty
19
# of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20
# GNU General Public License for more details.
22
# You should have received a copy of the GNU General Public License
23
# along with the Code_Saturne Kernel; if not, write to the
24
# Free Software Foundation, Inc.,
25
# 51 Franklin St, Fifth Floor,
26
# Boston, MA 02110-1301 USA
5
# This file is part of Code_Saturne, a general-purpose CFD tool.
7
# Copyright (C) 1998-2011 EDF S.A.
9
# This program is free software; you can redistribute it and/or modify it under
10
# the terms of the GNU General Public License as published by the Free Software
11
# Foundation; either version 2 of the License, or (at your option) any later
14
# This program is distributed in the hope that it will be useful, but WITHOUT
15
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
16
# FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
19
# You should have received a copy of the GNU General Public License along with
20
# this program; if not, write to the Free Software Foundation, Inc., 51 Franklin
21
# Street, Fifth Floor, Boston, MA 02110-1301, USA.
28
23
#-------------------------------------------------------------------------------
31
26
This module contains the following classes and function:
32
27
- BatchRunningUserFilesDialogView
33
- BatchRunningPBSJobManagementDialogView
34
28
- BatchRunningAdvancedOptionsDialogView
312
264
model.setData(index, QVariant(item), Qt.DisplayRole)
315
class ResuDelegate(QItemDelegate):
316
def __init__(self, parent=None):
317
super(ResuDelegate, self).__init__(parent)
321
def createEditor(self, parent, option, index):
322
editor = QLineEdit(parent)
323
vd = RegExpValidator(editor, QRegExp("[_A-Za-z0-9\-\*\!\?\.]*"))
324
editor.setValidator(vd)
325
editor.setFrame(False)
326
self.connect(editor, SIGNAL("returnPressed()"), self.commitAndCloseEditor)
327
editor.setCursorPosition(0)
331
def commitAndCloseEditor(self):
332
editor = self.sender()
333
if isinstance(editor, QLineEdit):
334
self.emit(SIGNAL("commitData(QWidget*)"), editor)
335
self.emit(SIGNAL("closeEditor(QWidget*)"), editor)
338
def setEditorData(self, editor, index):
339
text = index.model().data(index, Qt.DisplayRole).toString()
343
def setModelData(self, editor, model, index):
344
if not editor.isModified():
349
if model.search(item):
350
model.removeRow(index.row())
351
title = self.tr("Warning")
352
msg = self.tr("%s is already in the list." % str(item))
353
QMessageBox.warning(self.parent, title, msg)
355
model.setData(index, QVariant(item), Qt.DisplayRole)
358
#-------------------------------------------------------------------------------
359
# Popup window class: Cluster job management
360
#-------------------------------------------------------------------------------
363
class BatchRunningPBSJobManagementDialogView(QDialog, Ui_BatchRunningPBSJobManagementDialogForm):
367
def __init__(self, parent, default):
371
QDialog.__init__(self, parent)
373
Ui_BatchRunningPBSJobManagementDialogForm.__init__(self)
376
self.setWindowTitle(self.tr("PBS job management"))
378
self.default = default
379
self.result = self.default.copy()
382
validatorJobName = RegExpValidator(self.lineEditJobName, QRegExp("[_A-Za-z0-9]*"))
383
validatorNodes = IntValidator(self.lineEditNodes, min=1)
384
validatorCPUNodes = IntValidator(self.lineEditCPUNodes, min=1, max=32)
385
validatorHours = IntValidator(self.lineEditHours, min=0, max=999)
386
validatorMinutes = IntValidator(self.lineEditMinutes, min=0, max=59)
387
validatorSeconds = IntValidator(self.lineEditSeconds, min=0, max=59)
389
self.lineEditJobName.setValidator(validatorJobName)
390
self.lineEditNodes.setValidator(validatorNodes)
391
self.lineEditCPUNodes.setValidator(validatorCPUNodes)
393
self.lineEditHours.setValidator(validatorHours)
394
self.lineEditMinutes.setValidator(validatorMinutes)
395
self.lineEditSeconds.setValidator(validatorSeconds)
398
self.job_name = self.default['PBS_JOB_NAME']
399
self.cluster_node = self.default['PBS_nodes']
400
self.cluster_ppn = self.default['PBS_ppn']
401
L = string.split(self.default['PBS_walltime'], ":")
406
self.lineEditJobName.setText(QString(self.job_name))
407
self.lineEditNodes.setText(QString(str(self.cluster_node)))
409
self.lineEditCPUNodes.setText(QString(str(self.cluster_ppn)))
410
self.lineEditHours.setText(QString(str(self.h_cput)))
411
self.lineEditMinutes.setText(QString(str(self.m_cput)))
412
self.lineEditSeconds.setText(QString(str(self.s_cput)))
415
def get_result(self):
417
Method to get the result
424
Method called when user clicks 'OK'
426
self.result['PBS_JOB_NAME'] = str(self.lineEditJobName.text())
427
if self.lineEditNodes.validator().state == QValidator.Acceptable:
428
self.result['PBS_nodes'] = str(self.lineEditNodes.text())
429
if self.lineEditCPUNodes.validator().state == QValidator.Acceptable:
430
self.result['PBS_ppn'] = str(self.lineEditCPUNodes.text())
431
if self.lineEditCPUNodes.validator().state == QValidator.Acceptable and \
432
self.lineEditMinutes.validator().state == QValidator.Acceptable and \
433
self.lineEditSeconds.validator().state == QValidator.Acceptable:
434
h_cput = str(self.lineEditHours.text())
435
m_cput = str(self.lineEditMinutes.text())
436
s_cput = str(self.lineEditSeconds.text())
437
self.result['PBS_walltime'] = h_cput + ":" + m_cput + ":" + s_cput
444
Method called when user clicks 'Cancel'
456
267
#-------------------------------------------------------------------------------
457
268
# Popup advanced options
458
269
#-------------------------------------------------------------------------------
472
283
self.setupUi(self)
474
285
self.setWindowTitle(self.tr("Advanced options"))
475
self.default = default
476
self.result = self.default.copy()
478
288
self.lineEdit.setReadOnly(True)
481
self.modelCSTMPPREFIX = ComboModel(self.comboBoxCSTMPPREFIX, 2, 1)
482
self.modelExecPrepro = ComboModel(self.comboBox, 2, 1)
483
self.modelExecPartit = ComboModel(self.comboBox_2, 2, 1)
484
self.modelExecKernel = ComboModel(self.comboBox_3, 2, 1)
485
self.modelArg_cs_verif = ComboModel(self.comboBox_5, 2, 1)
291
self.modelSCRATCHDIR = ComboModel(self.comboBoxSCRATCHDIR, 2, 1)
292
self.modelPartitType = ComboModel(self.comboBox_2, 4, 1)
486
293
self.modelCSOUT1 = ComboModel(self.comboBox_6, 2, 1)
487
294
self.modelCSOUT2 = ComboModel(self.comboBox_7, 3, 1)
490
self.modelCSTMPPREFIX.addItem(self.tr("automatic"), 'automatic')
491
self.modelCSTMPPREFIX.addItem(self.tr("prescribed"), 'prescribed')
493
self.modelExecPrepro.addItem(self.tr("Run the preprocessor"), 'yes')
494
self.modelExecPrepro.addItem(self.tr("Use existing DATA/preprocessor_output"), 'no')
496
self.modelExecPartit.addItem(self.tr("Run the partioner"), 'yes')
497
self.modelExecPartit.addItem(self.tr("Use existing domain_number_<p> file in DATA/PARTITION_OUTPUT/\n"\
498
"if present, unoptimized partition otherwise"), 'no')
500
self.modelExecKernel.addItem(self.tr("Setup data and run the calculation"), 'yes')
501
self.modelExecKernel.addItem(self.tr("Do not setup data and run the calculation"), 'no')
503
self.modelArg_cs_verif.addItem(self.tr("Off"), 'standard')
504
self.modelArg_cs_verif.addItem(self.tr("Mesh quality criteria"), 'mesh_quality')
506
self.modelCSOUT1.addItem(self.tr("to standard output"), 'standard')
297
self.modelSCRATCHDIR.addItem(self.tr("automatic"), 'automatic')
298
self.modelSCRATCHDIR.addItem(self.tr("prescribed"), 'prescribed')
300
self.modelPartitType.addItem(self.tr("Default"), 'default')
301
self.modelPartitType.addItem(self.tr("Scotch"), 'scotch')
302
self.modelPartitType.addItem(self.tr("Metis"), 'metis')
303
self.modelPartitType.addItem(self.tr("Morton curve (bounding box)"), 'morton sfc')
304
self.modelPartitType.addItem(self.tr("Morton curve (bounding cube)"), 'morton sfc cube')
305
self.modelPartitType.addItem(self.tr("Hilbert curve (bounding box)"), 'hilbert sfc')
306
self.modelPartitType.addItem(self.tr("Hilbert curve (bounding cube)"), 'hilbert sfc cube')
308
self.modelCSOUT1.addItem(self.tr("to standard output"), 'stdout')
507
309
self.modelCSOUT1.addItem(self.tr("to listing"), 'listing')
509
self.modelCSOUT2.addItem(self.tr("no output"), 'shunte')
510
self.modelCSOUT2.addItem(self.tr("to standard output"), 'standard')
511
self.modelCSOUT2.addItem(self.tr("to listing_n<N>"), 'listing')
514
self.connect(self.comboBoxCSTMPPREFIX, SIGNAL("activated(const QString&)"), self.slotCSTMPPREFIX)
311
self.modelCSOUT2.addItem(self.tr("no output"), 'null')
312
self.modelCSOUT2.addItem(self.tr("to standard output"), 'stdout')
313
self.modelCSOUT2.addItem(self.tr("to listing_n<p>"), 'listing')
316
partListVd = RegExpValidator(self.lineEdit_2, QRegExp("[0-9- ]*"))
317
self.lineEdit_2.setValidator(partListVd)
320
self.connect(self.comboBoxSCRATCHDIR, SIGNAL("activated(const QString&)"), self.slotSCRATCHDIR)
515
321
self.connect(self.toolButton, SIGNAL("clicked()"), self.slotSearchDirectory)
516
self.connect(self.comboBox, SIGNAL("activated(const QString&)"), self.slotExePrepro)
517
322
self.connect(self.comboBox_2, SIGNAL("activated(const QString&)"), self.slotExePartit)
518
self.connect(self.comboBox_3, SIGNAL("activated(const QString&)"), self.slotExeKernel)
519
323
self.connect(self.toolButton_2, SIGNAL("clicked()"), self.slotSearchFile)
520
324
self.connect(self.lineEdit_2, SIGNAL("textChanged(const QString &)"), self.slotPartitionList)
521
325
self.connect(self.lineEdit_3, SIGNAL("textChanged(const QString &)"), self.slotValgrind)
522
self.connect(self.lineEdit_4, SIGNAL("textChanged(const QString &)"), self.slotCs_lib_add)
523
self.connect(self.comboBox_5, SIGNAL("activated(const QString&)"), self.slotArgCsVerif)
524
self.connect(self.comboBox_6, SIGNAL("activated(const QString&)"), self.slotArgCsOutput)
525
self.connect(self.comboBox_7, SIGNAL("activated(const QString&)"), self.slotArgCsOutput)
326
self.connect(self.comboBox_6, SIGNAL("activated(const QString&)"), self.slotLogType)
327
self.connect(self.comboBox_7, SIGNAL("activated(const QString&)"), self.slotLogType)
527
329
# Previous values
528
self.dir_name = self.default['CS_TMP_PREFIX']
529
self.lineEdit.setText(QString(self.dir_name))
530
if self.dir_name == "":
330
self.scratchdir = self.parent.mdl.getString('scratchdir')
331
self.scratchdir_default = self.scratchdir
332
self.lineEdit.setText(QString(self.scratchdir))
333
if self.scratchdir == "":
531
334
self.lineEdit.setEnabled(False)
532
335
self.toolButton.setEnabled(False)
533
self.modelCSTMPPREFIX.setItem(str_model='automatic')
336
self.modelSCRATCHDIR.setItem(str_model='automatic')
535
338
self.lineEdit.setEnabled(True)
536
339
self.toolButton.setEnabled(True)
537
self.modelCSTMPPREFIX.setItem(str_model='prescribed')
539
self.exe_prepro = self.default['EXEC_PREPROCESS']
540
self.modelExecPrepro.setItem(str_model=self.exe_prepro)
542
self.exe_partit = self.default['EXEC_PARTITION']
543
self.modelExecPartit.setItem(str_model=self.exe_partit)
545
self.exe_kernel = self.default['EXEC_KERNEL']
546
self.modelExecKernel.setItem(str_model=self.exe_kernel)
548
self.partition_list = self.default['PARTITION_LIST']
340
self.modelSCRATCHDIR.setItem(str_model='prescribed')
342
self.partition_type = str(self.parent.mdl.getPartitionType())
343
self.modelPartitType.setItem(str_model=self.partition_type)
345
self.partition_list = self.parent.mdl.getString('partition_list')
549
346
self.lineEdit_2.setText(QString(self.partition_list))
551
self.valgrind = self.default['VALGRIND']
552
self.lineEdit_3.setText(QString(self.valgrind))
554
self.cs_lib_add = self.default['CS_LIB_ADD']
555
self.lineEdit_4.setText(QString(self.cs_lib_add))
558
self.setArgCsOutput()
348
self.valgrind = self.parent.mdl.getString('valgrind')
349
if self.valgrind != None:
350
self.lineEdit_3.setText(QString(self.valgrind))
561
355
@pyqtSignature("const QString &")
562
def slotCSTMPPREFIX(self, text):
564
Select mode for CS_TMP_PREFIX.
566
if self.modelCSTMPPREFIX.dicoV2M[str(text)] == 'prescribed':
567
self.dir_name = self.default['CS_TMP_PREFIX']
356
def slotSCRATCHDIR(self, text):
358
Select mode for SCRATCHDIR.
360
if self.modelSCRATCHDIR.dicoV2M[str(text)] == 'prescribed':
361
self.scratchdir = self.scratchdir_default
568
362
self.lineEdit.setEnabled(True)
569
363
self.toolButton.setEnabled(True)
570
364
setGreenColor(self.toolButton, True)
573
367
self.lineEdit.setEnabled(False)
574
368
self.toolButton.setEnabled(False)
575
369
setGreenColor(self.toolButton, False)
576
self.lineEdit.setText(QString(self.dir_name))
370
self.lineEdit.setText(QString(self.scratchdir))
579
373
@pyqtSignature("const QString &")
595
389
@pyqtSignature("const QString &")
596
def slotCs_lib_add(self, text):
598
Input for external libraries.
600
self.cs_lib_add = str(text)
603
@pyqtSignature("const QString &")
604
def slotExePrepro(self, text):
606
Preprocessor execution mode option.
608
self.exe_prepro = self.modelExecPrepro.dicoV2M[str(text)]
611
@pyqtSignature("const QString &")
612
390
def slotExePartit(self, text):
614
392
Partitioner execution mode option.
616
self.exe_partit = self.modelExecPartit.dicoV2M[str(text)]
619
@pyqtSignature("const QString &")
620
def slotExeKernel(self, text):
622
Kernel execution mode option.
624
self.exe_kernel = self.modelExecKernel.dicoV2M[str(text)]
627
def setArgCsVerif(self):
629
Put ARG_CS_VERIF option from "lance" file.
631
if self.default['ARG_CS_VERIF'] == '':
632
self.arg_cs_verif = 'standard'
634
if self.default['ARG_CS_VERIF'] == '--quality' or self.default['ARG_CS_VERIF'] == '-q':
635
self.arg_cs_verif = 'mesh_quality'
636
self.val_verif = '--quality'
637
self.modelArg_cs_verif.setItem(str_model=self.arg_cs_verif)
640
@pyqtSignature("const QString &")
641
def slotArgCsVerif(self, text):
643
Input ARG_CS_VERIF option.
646
self.arg_cs_verif = self.modelArg_cs_verif.dicoV2M[str(text)]
647
arg_verif = self.arg_cs_verif
649
if arg_verif == 'standard' : self.val_verif = ''
650
if arg_verif == 'mesh_quality' : self.val_verif = '--quality'
653
def setArgCsOutput(self):
655
Put ARG_CS_OUTPUT options from 'lancer' file.
657
self.val_output = self.default['ARG_CS_OUTPUT']
658
if self.default['ARG_CS_OUTPUT'] == '':
659
self.modelCSOUT1.setItem(str_model='listing')
660
self.modelCSOUT2.setItem(str_model='shunte')
662
list = self.default['ARG_CS_OUTPUT'].split()
665
for n in range(len(list)):
666
if list[n] == '--log':
668
if list[n+1] == '0': self.modelCSOUT1.setItem(str_model='standard')
669
if list[n+1] == '1': self.modelCSOUT1.setItem(str_model='listing')
670
if list[n] == '--logp':
672
if list[n+1] == '0': self.modelCSOUT2.setItem(str_model='standard')
673
if list[n+1] == '1': self.modelCSOUT2.setItem(str_model='listing')
674
if list[n+1] == '-1': self.modelCSOUT2.setItem(str_model='shunte')
675
if l1 == 0: self.modelCSOUT1.setItem(str_model='listing')
676
if l2 == 0: self.modelCSOUT2.setItem(str_model='shunte')
679
@pyqtSignature("const QString &")
680
def slotArgCsOutput(self, text):
682
Input ARG_CS_OUTPUT options.
687
arg_out1 = self.modelCSOUT1.dicoV2M[str(self.comboBox_6.currentText())]
688
arg_out2 = self.modelCSOUT2.dicoV2M[str(self.comboBox_7.currentText())]
689
if arg_out1 == 'listing': out1 = ''
690
if arg_out1 == 'standard': out1 = '--log 0'
691
if arg_out2 == 'shunte': out2 = ''
692
if arg_out2 == 'standard': out2 = '--logp 0'
693
if arg_out2 == 'listing': out2 = '--logp 1'
694
self.val_output = out1 + ' ' + out2
394
self.partition_type = self.modelPartitType.dicoV2M[str(text)]
397
def setLogType(self):
399
Set logging arguments.
401
self.log_type = self.parent.mdl.getLogType()
402
self.modelCSOUT1.setItem(str_model=self.log_type[0])
403
self.modelCSOUT2.setItem(str_model=self.log_type[1])
406
@pyqtSignature("const QString &")
407
def slotLogType(self, text):
409
Input logging options.
411
self.log_type = [self.modelCSOUT1.dicoV2M[str(self.comboBox_6.currentText())],
412
self.modelCSOUT2.dicoV2M[str(self.comboBox_7.currentText())]]
697
415
@pyqtSignature("")
802
519
self.setupUi(self)
805
RuncaseModel(self.case)
809
self.modelArchi = ComboModel(self.comboBoxArchi, 3, 1)
810
self.modelArchi.addItem(self.tr("Workstation"), 'station')
811
self.modelArchi.addItem(self.tr("Cluster with PBS queue system"), 'pbs')
812
self.modelArchi.addItem(self.tr("Cluster with LSF queue system"), 'lsf')
813
self.modelArchi.addItem(self.tr("Cluster with SGE queue system"), 'sge')
814
self.modelArchi.disableItem(str_model='lsf')
815
self.modelArchi.disableItem(str_model='sge')
523
self.mdl = ScriptRunningModel(self.case)
525
# Check if the script file name is already defined
527
if self.case['scripts_path']:
528
if not self.case['batch']:
529
if 'runcase' in os.listdir(self.case['scripts_path']):
530
self.case['batch'] = 'runcase'
532
self.case['batch_type'] = cs_batch_type
534
self.jmdl = BatchRunningModel(parent, self.case)
540
self.labelNProcs.hide()
541
self.spinBoxNProcs.hide()
543
self.class_list = None
547
if self.case['batch_type'] != None:
549
self.groupBoxArchi.setTitle("Job and script files")
550
self.labelBatch.show()
551
self.toolButtonSearchBatch.show()
553
validatorSimpleName = RegExpValidator(self.lineEditJobName,
554
QRegExp("[_A-Za-z0-9]*"))
555
self.lineEditJobName.setValidator(validatorSimpleName)
556
self.lineEditJobGroup.setValidator(validatorSimpleName)
557
self.pushButtonRunSubmit.setText("Submit job")
562
self.n_procs = int(self.mdl.getString('n_procs'))
819
self.connect(self.comboBoxArchi, SIGNAL("activated(const QString &)"), self.slotBatchCalculation)
820
self.connect(self.toolButtonSearch, SIGNAL("clicked()"), self.slotSearchBatchScriptFile)
821
self.connect(self.spinBoxProcs, SIGNAL("valueChanged(int)"), self.slotParallelComputing)
569
if self.case['batch_type'] != None:
570
self.connect(self.lineEditJobName, SIGNAL("textChanged(const QString &)"),
572
self.connect(self.spinBoxNodes, SIGNAL("valueChanged(int)"),
574
self.connect(self.spinBoxPpn, SIGNAL("valueChanged(int)"),
576
self.connect(self.spinBoxProcs, SIGNAL("valueChanged(int)"),
578
self.connect(self.spinBoxDays, SIGNAL("valueChanged(int)"),
579
self.slotJobWallTime)
580
self.connect(self.spinBoxHours, SIGNAL("valueChanged(int)"),
581
self.slotJobWallTime)
582
self.connect(self.spinBoxMinutes, SIGNAL("valueChanged(int)"),
583
self.slotJobWallTime)
584
self.connect(self.spinBoxSeconds, SIGNAL("valueChanged(int)"),
585
self.slotJobWallTime)
586
self.connect(self.comboBoxClass, SIGNAL("activated(const QString&)"),
588
self.connect(self.lineEditJobGroup, SIGNAL("textChanged(const QString &)"),
592
self.connect(self.spinBoxNProcs, SIGNAL("valueChanged(int)"), self.slotParallelComputing)
594
self.connect(self.toolButtonSearchBatch, SIGNAL("clicked()"), self.slotSearchBatchFile)
595
self.connect(self.comboBoxRunType, SIGNAL("activated(const QString&)"), self.slotArgRunType)
822
596
self.connect(self.toolButtonFiles, SIGNAL("clicked()"), self.slotUserFiles)
823
597
self.connect(self.toolButtonAdvanced, SIGNAL("clicked()"), self.slotAdvancedOptions)
824
self.connect(self.pushButtonRun, SIGNAL("clicked()"), self.slotBatchRunning)
598
self.connect(self.pushButtonRunSubmit, SIGNAL("clicked()"), self.slotBatchRunning)
602
self.modelArg_cs_verif = ComboModel(self.comboBoxRunType, 2, 1)
604
self.modelArg_cs_verif.addItem(self.tr("Import mesh / partition only"), 'none')
605
self.modelArg_cs_verif.addItem(self.tr("Mesh preprocessing"), 'mesh preprocess')
606
self.modelArg_cs_verif.addItem(self.tr("Mesh quality criteria"), 'mesh quality')
607
self.modelArg_cs_verif.addItem(self.tr("Standard"), 'standard')
608
self.modelArg_cs_verif.setItem(str_model=self.mdl.getRunType())
826
611
# initialize Widgets
828
if self.case['computer'] == "":
830
self.case['computer'] = key
831
self.modelArchi.setItem(str_model=key)
832
self.slotBatchCalculation(self.tr('Workstation'))
833
if self.case['scripts_path']:
834
if "runcase" in os.listdir(self.case['scripts_path']):
835
if key in self.case['batchScript']:
836
self.case['batchScript'][key] = "runcase"
837
self.displayBatchScriptInfo()
838
setGreenColor(self.toolButtonSearch, False)
613
# Check if the script file name is already defined
615
name = self.case['batch']
617
self.labelBatchName.setText(QString(name))
618
setGreenColor(self.toolButtonSearchBatch, False)
840
self.modelArchi.setItem(str_model=self.case['computer'])
841
self.slotBatchCalculation(self.modelArchi.dicoM2V[self.case['computer']])
620
setGreenColor(self.toolButtonSearchBatch, True)
622
if self.case['batch_type'] != None and self.case['batch']:
623
self.displayBatchInfo()
625
# Script info is based on the XML model
627
self.displayScriptInfo()
630
@pyqtSignature("const QString &")
631
def slotJobName(self, v):
633
Increment, decrement and colorize the input argument entry
635
if self.lineEditJobName.validator().state == QValidator.Acceptable:
636
self.jmdl.dictValues['job_name'] = str(v)
637
self.jmdl.updateBatchFile('job_name')
640
@pyqtSignature("int")
641
def slotJobNodes(self, v):
643
Increment, decrement and colorize the input argument entry
645
self.jmdl.dictValues['job_nodes'] = str(self.spinBoxNodes.text())
646
self.jmdl.updateBatchFile('job_nodes')
649
@pyqtSignature("int")
650
def slotJobPpn(self, v):
652
Increment, decrement and colorize the input argument entry
654
self.jmdl.dictValues['job_ppn'] = str(self.spinBoxPpn.text())
655
self.jmdl.updateBatchFile('job_ppn')
658
@pyqtSignature("int")
659
def slotJobProcs(self, v):
661
Increment, decrement and colorize the input argument entry
663
self.jmdl.dictValues['job_procs'] = str(self.spinBoxProcs.text())
664
self.jmdl.updateBatchFile('job_procs')
668
def slotJobWallTime(self):
670
h_cput = self.spinBoxDays.value()*24 + self.spinBoxHours.value()
671
m_cput = self.spinBoxMinutes.value()
672
s_cput = self.spinBoxSeconds.value()
673
self.jmdl.dictValues['job_walltime'] = h_cput*3600 + m_cput*60 + s_cput
674
self.jmdl.updateBatchFile('job_walltime')
680
self.jmdl.dictValues['job_class'] = str(self.comboBoxClass.currentText())
681
if len(self.jmdl.dictValues['job_class']) > 0:
682
self.jmdl.updateBatchFile('job_class')
685
@pyqtSignature("const QString &")
686
def slotJobGroup(self, v):
688
Increment, decrement and colorize the input argument entry
690
if self.lineEditJobName.validator().state == QValidator.Acceptable:
691
self.jmdl.dictValues['job_group'] = str(v)
692
self.jmdl.updateBatchFile('job_group')
695
@pyqtSignature("const QString &")
696
def slotArgRunType(self, text):
698
Input run type option.
700
self.run_type = self.modelArg_cs_verif.dicoV2M[str(text)]
701
self.mdl.setRunType(self.run_type)
844
704
@pyqtSignature("int")
847
707
Increment, decrement and colorize the input argument entry
849
self.mdl.dicoValues['NUMBER_OF_PROCESSORS'] = v
850
self.mdl.updateBatchScriptFile('NUMBER_OF_PROCESSORS')
854
def pbsJobManagement(self):
856
Get PBS card informations.
859
list = ['PBS_JOB_NAME', 'PBS_nodes', 'PBS_ppn', 'PBS_walltime']
861
default[opt] = self.mdl.dicoValues[opt]
862
log.debug("pbsJobManagement -> %s" % str(default))
864
dialog = BatchRunningPBSJobManagementDialogView(self, default)
867
result = dialog.get_result()
868
log.debug("pbsJobManagement -> %s" % str(result))
870
self.mdl.dicoValues[option] = result[option]
872
self.mdl.updateBatchScriptFile()
875
def lsfJobManagement(self):
877
Get LSF card informations
881
## default['job_name'] = self.mdl.dicoValues['PBS_JOB_NAME']
882
## default['NQS_cput'] =
883
## default['NQS_cpuT'] =
884
## windowTitle = self.tr("CaThy")
885
## dialog = LSFJobManagementDialog(self.myPage, title=t.CATHY, default=default)
887
## self.job_name = dialog.result['job_name']
888
## self.NQS_cpult = dialog.result['NQS_cput']
889
## self.NQS_cpulT = dialog.result['NQS_cpuT'] + dialog.result['NQS_cput']
891
## self.mdl.updateBatchScriptFile()
709
self.n_procs = int(v)
710
self.mdl.setString('n_procs', str(v))
894
713
@pyqtSignature("")
895
714
def slotUserFiles(self):
897
Input 'USER_INPUT_FILES' and 'USER_OUTPUT_FILES'
716
Input user data files
900
default['data_path'] = self.case['data_path']
901
default['data'] = string.split(self.mdl.dicoValues['USER_INPUT_FILES'])
902
default['results'] = string.split(self.mdl.dicoValues['USER_OUTPUT_FILES'])
718
default = self.mdl.getUserInputFiles()
903
719
log.debug("slotUserFiles -> %s" % str(default))
905
dialog = BatchRunningUserFilesDialogView(self, default)
721
dialog = BatchRunningUserFilesDialogView(self,
722
self.case['data_path'],
907
725
if dialog.exec_():
908
726
result = dialog.get_result()
909
727
log.debug("slotUserFiles -> %s" % str(result))
910
self.mdl.dicoValues['USER_INPUT_FILES'] = string.join(result['data'])
911
self.mdl.dicoValues['USER_OUTPUT_FILES'] = string.join(result['results'])
912
self.mdl.updateBatchScriptFile('USER_INPUT_FILES')
913
self.mdl.updateBatchScriptFile('USER_OUTPUT_FILES')
728
self.mdl.setUserInputFiles(result)
916
731
@pyqtSignature("")
942
747
Launch Code_Saturne batch running.
944
# Test 1: is the file saved?
946
751
if self.case['new'] == "yes" or self.case.isModified():
948
753
title = self.tr("Warning")
949
754
msg = self.tr("The current case must be saved before "\
950
"running a Code_Saturne batch job.")
951
QMessageBox.information(self, title, msg)
953
# if self.case.saved() == "no":
954
# self.case.xmlSaveDocument()
955
# self.mdl.dicoValues['PARAM'] = os.path.basename(self.case['xmlfile'])
956
# self.mdl.updateBatchScriptFile('PARAM')
958
# Test 2: have we a mesh?
960
if not GuiParam.matisse :
961
node_ecs = self.case.xmlGetNode('solution_domain')
962
if not node_ecs.xmlGetNode('meshes_list'):
963
if not node_ecs.xmlGetNode('meshes_list').xmlGetNodeList('mesh'):
964
title = self.tr("Warning")
965
msg = self.tr("You have to select a mesh.\n\n")
966
QMessageBox.information(self, title, msg)
969
# Test 3: have we a trouble with the mesh generation?
971
if GuiParam.matisse :
972
import Pages.Matisse as Matisse
973
if not Matisse.MatisseMeshRunning(self.case).ok :
755
"running the ") + self.tr(self.case['package']).code_name + self.tr(" script.")
756
QMessageBox.information(self, title, msg)
759
# Do we have a mesh ?
762
node_ecs = self.case.xmlGetNode('solution_domain')
763
if node_ecs.xmlGetNode('meshes_list'):
764
if node_ecs.xmlGetNode('meshes_list').xmlGetNodeList('mesh'):
766
if node_ecs.xmlGetNode('mesh_input', 'path'):
769
title = self.tr("Warning")
770
msg = self.tr("You have to select a mesh.\n\n")
771
QMessageBox.information(self, title, msg)
774
# Verify if boundary condition definitions exist
776
bd = LocalizationModel('BoundaryZone', self.case)
777
if not bd.getZones():
778
if self.case['no_boundary_conditions'] == False:
974
779
title = self.tr("Warning")
975
msg = self.tr("Mesh generation error.\nSee the file 'listsim'")
976
QMessageBox.information(self, title, msg)
979
# Test 4: verify if boundary definition exists
981
## if not GuiParam.matisse:
982
## from DefineBoundaryRegionsModel import DefBCModel
983
## groupList = DefBCModel(self.case).getListLabel()
985
## if self.case['no_boundary_conditions'] == False:
986
## title = self.tr("Warning")
987
## msg = self.tr("No boundary definition declared.\n\n")
988
## QMessageBox.warning(self, title, msg)
989
## self.case['no_boundary_conditions'] = True
991
if not GuiParam.matisse:
992
bd = LocalizationModel('BoundaryZone', self.case)
993
if not bd.getZones():
994
if self.case['no_boundary_conditions'] == False:
995
title = self.tr("Warning")
996
msg = self.tr("No boundary definition declared.\n\n")
997
QMessageBox.warning(self, title, msg)
998
self.case['no_boundary_conditions'] = True
1000
# Command line building
1002
key = self.case['computer']
1004
script = os.path.join(self.case['scripts_path'], self.case['batchScript'][key])
1005
batch1 = os.path.join(self.case['scripts_path'], "batch")
1006
batch2 = batch1 + '~'
1008
if key == 'station':
1010
os.rename(batch1, batch2)
1013
cmd = 'nice nohup ' + script + ' | tee ' + batch1 + ' &'
1014
# FIXME: Work in progress
1015
## dialog = CalculationDialog(self.master, title=t.BATCH, stbar=self.stbar,
1017
## cmd = 'nice nohup ' + script + 'dialog' + ' &'
1019
#cmd = 'qsub ' + script + ' ' + self.case['batchScript'][key] + ' &'
1020
cmd = 'qsub ' + script
1022
cmd = 'bsub ' + script + ' ' + self.case['batchScript'][key] + ' &'
780
msg = self.tr("No boundary definition declared.\n\n")
781
QMessageBox.warning(self, title, msg)
782
self.case['no_boundary_conditions'] = True
786
key = self.case['batch_type']
788
batch = os.path.join(self.case['scripts_path'], self.case['batch'])
791
cmd = 'nice nohup ' + batch + ' | tee ' + batch + '.log &'
792
elif key[0:3] == 'CCC':
793
cmd = 'qsub ' + batch
794
elif key[0:5] == 'LOADL':
795
cmd = 'llsubmit ' + batch
796
elif key[0:3] == 'LSF':
797
cmd = 'bsub < ' + batch + ' ' + self.case['batch'] + ' &'
798
elif key[0:3] == 'PBS' or key[0:3] == 'SGE':
799
cmd = 'qsub ' + batch
800
elif key[0:5] == 'SLURM':
801
cmd = 'sbatch ' + batch
1026
805
if self.case['salome']:
1027
import SalomeHandler
1028
SalomeHandler.runSolver(self.case, script)
806
from Pages import SalomeHandler
807
SalomeHandler.runSolver(self.case, batch)
1033
def displayBatchScriptInfo(self):
1035
Layout of the second part of this page.
1037
self.groupBoxBatch.show()
1039
self.labelJob.hide()
1040
self.toolButtonJob.hide()
1042
if hasattr(self, 'mdl'):
1044
self.mdl = BatchRunningModel(self.case)
1045
self.mdl.readBatchScriptFile()
1047
self.labelFilename.show()
1048
self.computer = self.modelArchi.dicoV2M[str(self.comboBoxArchi.currentText())]
1049
name = self.case['batchScript'][self.computer]
1050
self.labelFilename.setText(QString(name))
1052
if self.case['computer'] == 'station':
1053
if GuiParam.matisse :
1054
self.labelFiles.show()
1055
self.toolButtonFiles.show()
1056
self.labelProcs.hide()
1057
self.spinBoxProcs.hide()
1059
self.labelFiles.show()
1060
self.toolButtonFiles.show()
1061
self.labelProcs.show()
1062
self.spinBoxProcs.show()
1064
self.labelProcs.hide()
1065
self.spinBoxProcs.hide()
1066
self.labelJob.show()
1067
self.toolButtonJob.show()
1068
if self.case['computer'] == "pbs":
1069
self.connect(self.toolButtonJob, SIGNAL("clicked()"), self.pbsJobManagement)
1070
if self.case['computer'] == "lsf":
1071
self.connect(self.toolButtonJob, SIGNAL("clicked()"), self.lsfJobManagement)
1072
if self.case['computer'] == "sge":
1075
# self.lineBatch1.show()
1076
# self.labelAdvanced.show()
1077
# self.toolButtonAdvanced.show()
1079
dico = self.mdl.dicoValues
1081
if dico['NUMBER_OF_PROCESSORS'] == "":
1082
dico['NUMBER_OF_PROCESSORS'] = "1"
1083
if self.case['computer'] == 'station':
1084
self.spinBoxProcs.setValue(int(dico['NUMBER_OF_PROCESSORS']))
1086
self.mdl.updateBatchScriptFile()
1089
@pyqtSignature("const QString &")
1090
def slotBatchCalculation(self, text):
1092
1) Look if the batch script file name is allready known
1093
for the current computer
1094
2) Display the apropriate frame for the selected computer
1096
log.debug("slotBatchCalculation -> %s" % str(text))
1097
self.groupBoxBatch.hide()
1099
key = self.modelArchi.dicoV2M[str(text)]
1100
self.case['computer'] = key
1101
log.debug("slotBatchCalculation -> %s" % key)
1103
self.labelLauncher.setEnabled(True)
1105
if key in self.case['batchScript'] and self.case['batchScript'][key]:
1106
self.displayBatchScriptInfo()
1107
setGreenColor(self.toolButtonSearch, False)
1109
self.labelFilename.hide()
1110
setGreenColor(self.toolButtonSearch, True)
812
def getCommandOutput(self, cmd):
814
Run a command and return it's standard output.
816
p = subprocess.Popen(cmd,
818
stdout=subprocess.PIPE,
819
stderr=subprocess.PIPE)
822
l = p.stdout.readline()
823
lines.append(l.strip())
824
if len(l) == 0 and p.poll() != None:
826
output = p.communicate()
828
if p.returncode == 0:
832
def getClassList(self):
834
Layout of the second part of this page.
841
if self.case['batch_type'][0:3] == 'CCC':
842
output = self.getCommandOutput('class')
847
self.class_list.append(l.split(' ')[0])
849
elif self.case['batch_type'][0:5] == 'LOADL':
850
output = self.getCommandOutput('llclass')
855
elif ignore == False:
856
self.class_list.append(l.split(' ')[0])
858
elif self.case['batch_type'][0:3] == 'LSF':
859
output = self.getCommandOutput('bqueues')
865
self.class_list.append(l.split(' ')[0])
867
elif self.case['batch_type'][0:3] == 'PBS':
868
output = self.getCommandOutput('qstat -q')
873
elif ignore == False:
874
self.class_list.append(l.split(' ')[0])
876
elif self.case['batch_type'][0:3] == 'SGE':
877
output = self.getCommandOutput('qconf -sc')
880
self.class_list.append(l.split(' ')[0])
882
elif self.case['batch_type'][0:5] == 'SLURM':
883
output = self.getCommandOutput('sinfo -s')
888
name = l.split(' ')[0]
891
self.class_list.append(name)
897
def hideBatchInfo(self):
899
hide all batch info before displaying a selected subset
902
self.groupBoxJob.hide()
904
self.labelJobName.hide()
905
self.lineEditJobName.hide()
906
self.labelNodes.hide()
907
self.spinBoxNodes.hide()
909
self.spinBoxPpn.hide()
910
self.labelProcs.hide()
911
self.spinBoxProcs.hide()
912
self.labelClass.hide()
913
self.labelWTime.hide()
914
self.spinBoxDays.hide()
915
self.labelDays.hide()
916
self.spinBoxHours.hide()
917
self.labelHours.hide()
918
self.spinBoxMinutes.hide()
919
self.labelMinutes.hide()
920
self.spinBoxSeconds.hide()
921
self.labelSeconds.hide()
922
self.comboBoxClass.hide()
923
self.labelJobGroup.hide()
924
self.lineEditJobGroup.hide()
927
def displayBatchInfo(self):
929
Layout of the second part of this page.
932
self.job_name = self.jmdl.dictValues['job_name']
933
self.job_nodes = self.jmdl.dictValues['job_nodes']
934
self.job_ppn = self.jmdl.dictValues['job_ppn']
935
self.job_procs = self.jmdl.dictValues['job_procs']
936
self.job_walltime = self.jmdl.dictValues['job_walltime']
937
self.job_class = self.jmdl.dictValues['job_class']
938
self.job_group = self.jmdl.dictValues['job_group']
940
if self.job_name != None:
941
self.labelJobName.show()
942
self.lineEditJobName.setText(QString(self.job_name))
943
self.lineEditJobName.show()
945
if self.job_nodes != None:
946
self.labelNodes.show()
947
self.spinBoxNodes.setValue(int(self.job_nodes))
948
self.spinBoxNodes.show()
950
if self.job_ppn != None:
952
self.spinBoxPpn.setValue(int(self.job_ppn))
953
self.spinBoxPpn.show()
955
if self.job_procs != None:
956
self.labelProcs.show()
957
self.spinBoxProcs.setValue(int(self.job_procs))
958
self.spinBoxProcs.show()
960
if self.job_walltime != None:
961
seconds = self.job_walltime
962
minutes = seconds / 60
965
seconds = seconds % 60
966
minutes = minutes % 60
968
self.spinBoxDays.setValue(days)
969
self.spinBoxHours.setValue(hours)
970
self.spinBoxMinutes.setValue(minutes)
971
self.spinBoxSeconds.setValue(seconds)
972
self.labelWTime.show()
973
self.spinBoxDays.show()
974
self.labelDays.show()
975
self.spinBoxHours.show()
976
self.labelHours.show()
977
self.spinBoxMinutes.show()
978
self.labelMinutes.show()
979
self.spinBoxSeconds.show()
980
self.labelSeconds.show()
982
if self.job_class != None:
985
if self.class_list == None:
987
if len(self.class_list) > 0:
988
for c in self.class_list:
989
self.comboBoxClass.addItem(self.tr(c), QVariant(c))
992
self.comboBoxClass.addItem(self.tr(c), QVariant(c))
996
index = self.class_list.index(self.job_class)
997
self.comboBoxClass.setCurrentIndex(index)
999
if len(self.class_list) > 0:
1000
self.job_class = self.class_list[0]
1001
self.labelClass.show()
1002
self.comboBoxClass.show()
1004
if self.job_group != None:
1005
self.labelJobGroup.show()
1006
self.lineEditJobGroup.setText(QString(self.job_group))
1007
self.lineEditJobGroup.show()
1009
# Show Job management box
1011
if self.case['batch_type'][0:5] == 'LOADL':
1012
self.groupBoxJob.setTitle("Load Leveler job parameters")
1013
elif self.case['batch_type'][0:3] == 'LSF':
1014
self.groupBoxJob.setTitle("LSF job parameters")
1015
elif self.case['batch_type'][0:3] == 'PBS':
1016
self.groupBoxJob.setTitle("PBS job parameters")
1017
elif self.case['batch_type'][0:3] == 'SGE':
1018
self.groupBoxJob.setTitle("Sun Grid Engine job parameters")
1019
if self.case['batch_type'][0:5] == 'SLURM':
1020
self.groupBoxJob.setTitle("SLURM job parameters")
1022
self.groupBoxJob.setTitle("Batch job parameters")
1024
self.groupBoxJob.show()
1028
self.jmdl.updateBatchFile()
1031
def displayScriptInfo(self):
1033
Layout of the second part of this page.
1036
self.labelFiles.show()
1037
self.toolButtonFiles.show()
1039
if self.case['batch_type'] == None:
1040
self.labelNProcs.show()
1041
self.spinBoxNProcs.show()
1043
self.labelNProcs.hide()
1044
self.spinBoxNProcs.hide()
1046
if self.case['batch_type'] == None:
1047
self.spinBoxNProcs.setValue(self.n_procs)
1113
1052
@pyqtSignature("")
1114
def slotSearchBatchScriptFile(self):
1053
def slotSearchBatchFile(self):
1116
Open a FileDialog in order to search the batch script file
1055
Open a FileDialog in order to search the batch command file
1117
1056
in the system file.