def install_step(self): """Install CUDA using Perl install script.""" # define how to run the installer # script has /usr/bin/perl hardcoded, but we want to have control over which perl is being used if LooseVersion(self.version) <= LooseVersion("5"): install_interpreter = "perl" install_script = "install-linux.pl" self.cfg.update('installopts', '--prefix=%s' % self.installdir) elif LooseVersion(self.version) > LooseVersion("5") and LooseVersion(self.version) < LooseVersion("10.1"): install_interpreter = "perl" install_script = "cuda-installer.pl" # note: also including samples (via "-samplespath=%(installdir)s -samples") would require libglut self.cfg.update('installopts', "-verbose -silent -toolkitpath=%s -toolkit" % self.installdir) else: install_interpreter = "" install_script = "./cuda-installer" # note: also including samples (via "-samplespath=%(installdir)s -samples") would require libglut self.cfg.update('installopts', "--silent --toolkit --toolkitpath=%s --defaultroot=%s" % ( self.installdir, self.installdir)) cmd = "%(preinstallopts)s %(interpreter)s %(script)s %(installopts)s" % { 'preinstallopts': self.cfg['preinstallopts'], 'interpreter': install_interpreter, 'script': install_script, 'installopts': self.cfg['installopts'] } # prepare for running install script autonomously qanda = {} stdqa = { # this question is only asked if CUDA tools are already available system-wide r"Would you like to remove all CUDA files under .*? (yes/no/abort): ": "no", } noqanda = [ r"^Configuring", r"Installation Complete", r"Verifying archive integrity.*", r"^Uncompressing NVIDIA CUDA", r".* -> .*", ] # patch install script to handle Q&A autonomously if install_interpreter == "perl": patch_perl_script_autoflush(os.path.join(self.builddir, install_script)) # make sure $DISPLAY is not defined, which may lead to (weird) problems # this is workaround for not being able to specify --nox11 to the Perl install scripts if 'DISPLAY' in os.environ: os.environ.pop('DISPLAY') # overriding maxhits default value to 300 (300s wait for nothing to change in the output without seeing a known # question) run_cmd_qa(cmd, qanda, std_qa=stdqa, no_qa=noqanda, log_all=True, simple=True, maxhits=300) # check if there are patches to apply if len(self.src) > 1: for patch in self.src[1:]: self.log.debug("Running patch %s", patch['name']) run_cmd("/bin/sh " + patch['path'] + " --accept-eula --silent --installdir=" + self.installdir)
def configure_step(self): """Custom configuration procedure for Doris.""" fftw = get_software_root('FFTW') if fftw is None: raise EasyBuildError("Required dependency FFTW is missing") # create installation directory (and /bin subdirectory) early, make sure it doesn't get removed later self.make_installdir() mkdir(os.path.join(self.installdir, 'bin')) self.cfg['keeppreviousinstall'] = True # configure/build/install should be done from 'src' subdirectory change_dir(os.path.join(self.cfg['start_dir'], 'src')) qa = { "===> Press enter to continue.": '', "===> What is your C++ compiler? [g++]": os.getenv('CXX'), "===> Do you have the FFTW library (y/n)? [n]": 'y', "===> What is the path to the FFTW library (libfftw3f.a or libfftw3f.so)? []": os.path.join(fftw, 'lib'), "===> What is the path to the FFTW include file (fftw3.h)? []": os.path.join(fftw, 'include'), "===> Do you have the VECLIB library (y/n)? [n]": 'n', "===> Do you have the LAPACK library (y/n)? [n]": 'y', "===> What is the path to the LAPACK library liblapack.a? []": os.getenv('LAPACK_LIB_DIR'), "===> Are you working on a Little Endian (X86 PC, Intel) machine (y/n)? [y]": 'y', "===> Installation of Doris in directory: /usr/local/bin (y/n)? [y]": 'n', "===> Enter installation directory (use absolute path):": os.path.join(self.installdir, 'bin'), "===> Press enter to continue (CTRL-C to exit).": '', } std_qa = { "===> Do you want to compile a more verbose DEBUG version \(y/n\)\? \[n\](.|\n)*expected results\)": 'n', } run_cmd_qa('./configure', qa, std_qa=std_qa, log_all=True, simple=True)
def configure_step(self): """Configure Qt using interactive `configure` script.""" self.cfg.update('configopts', '-release') platform = None comp_fam = self.toolchain.comp_family() if self.cfg['platform']: platform = self.cfg['platform'] # if no platform is specified, try to derive it based on compiler in toolchain elif comp_fam in [toolchain.GCC]: #@UndefinedVariable platform = 'linux-g++-64' elif comp_fam in [toolchain.INTELCOMP]: #@UndefinedVariable platform = 'linux-icc-64' if platform: self.cfg.update('configopts', "-platform %s" % platform) else: raise EasyBuildError("Don't know which platform to set based on compiler family.") cmd = "%s ./configure --prefix=%s %s" % (self.cfg['preconfigopts'], self.installdir, self.cfg['configopts']) qa = { "Type 'o' if you want to use the Open Source Edition.": 'o', "Do you accept the terms of either license?": 'yes', } no_qa = [ "for .*pro", r"%s.*" % os.getenv('CXX', '').replace('+', '\\+'), # need to escape + in 'g++' "Reading .*", "WARNING .*", "Project MESSAGE:.*", "rm -f .*", 'Creating qmake...', ] run_cmd_qa(cmd, qa, no_qa=no_qa, log_all=True, simple=True, maxhits=120)
def build_step(self): """Build OpenFOAM using make after sourcing script to set environment.""" precmd = "source %s" % os.path.join(self.builddir, self.openfoamdir, "etc", "bashrc") # make directly in install directory cmd_tmpl = "%(precmd)s && %(prebuildopts)s %(makecmd)s" % { 'precmd': precmd, 'prebuildopts': self.cfg['prebuildopts'], 'makecmd': os.path.join(self.builddir, self.openfoamdir, '%s'), } if 'extend' in self.name.lower() and LooseVersion(self.version) >= LooseVersion('3.0'): qa = { "Proceed without compiling ParaView [Y/n]": 'Y', "Proceed without compiling cudaSolvers? [Y/n]": 'Y', } noqa = [ ".* -o .*", "checking .*", "warning.*", "configure: creating.*", "%s .*" % os.environ['CC'], "wmake .*", "Making dependency list for source file.*", "\s*\^\s*", # warning indicator "Cleaning .*", ] run_cmd_qa(cmd_tmpl % 'Allwmake.firstInstall', qa, no_qa=noqa, log_all=True, simple=True) else: run_cmd(cmd_tmpl % 'Allwmake', log_all=True, simple=True, log_output=True)
def install_step(self): """Install Mathematica using install script.""" # make sure $DISPLAY is not set (to avoid that installer uses GUI) orig_display = os.environ.pop('DISPLAY', None) cmd = "./%s_%s_LINUX.sh" % (self.name, self.version) shortver = '.'.join(self.version.split('.')[:2]) qa_install_path = "/usr/local/Wolfram/%s/%s" % (self.name, shortver) qa = { r"Enter the installation directory, or press ENTER to select %s: >" % qa_install_path: self.installdir, r"Create directory (y/n)? >": 'y', r"Should the installer attempt to make this change (y/n)? >": 'n', r"or press ENTER to select /usr/local/bin: >": os.path.join(self.installdir, "bin"), } no_qa = [ "Now installing.*\n\n.*\[.*\].*", ] run_cmd_qa(cmd, qa, no_qa=no_qa, log_all=True, simple=True, maxhits=200) # add license server configuration file # some relevant documentation at http://reference.wolfram.com/mathematica/tutorial/ConfigurationFiles.html mathpass_path = os.path.join(self.installdir, 'Configuration', 'Licensing', 'mathpass') try: # append to file, to avoid overwriting anything that might be there f = open(mathpass_path, "a") f.write("!%s\n" % self.cfg['license_server']) f.close() f = open(mathpass_path, "r") mathpass_txt = f.read() f.close() self.log.info("Updated license file %s: %s" % (mathpass_path, mathpass_txt)) except IOError, err: raise EasyBuildError("Failed to update %s with license server info: %s", mathpass_path, err)
def install_step(self): """Interactive install of Maple.""" cmd = "%s/Maple%sLinuxX86_64Installer.bin" % (self.builddir, self.cfg['version']) qa = { 'PRESS <ENTER> TO CONTINUE:': '', 'DO YOU ACCEPT THE TERMS OF THIS LICENSE AGREEMENT? (Y/N):': 'Y', 'ENTER AN ABSOLUTE PATH, OR PRESS <ENTER> TO ACCEPT THE DEFAULT :': self.installdir, 'IS THIS CORRECT? (Y/N):': 'Y', 'Do you wish to have a shortcut installed on your desktop? ->1- Yes 2- No ENTER THE NUMBER FOR YOUR CHOICE, OR PRESS <ENTER> TO ACCEPT THE DEFAULT::': '2', '->1- Single User License 2- Network License ENTER THE NUMBER FOR YOUR CHOICE, OR PRESS <ENTER> TO ACCEPT THE DEFAULT::': '2', 'PRESS <ENTER> TO EXIT THE INSTALLER:': '', 'License server (DEFAULT: ):': self.cfg['license_server'], 'Port number (optional) (DEFAULT: ):': '', '->1- Configure toolbox for Matlab 2- Do not configure at this time ENTER THE NUMBER FOR YOUR CHOICE, OR PRESS <ENTER> TO ACCEPT THE DEFAULT::': '2' } no_qa = ['Graphical installers are not supported by the VM. The console mode will be used instead...', 'Extracting the JRE from the installer archive...', 'Launching installer...', "Configuring the installer for this system's environment...", 'Unpacking the JRE...', '\[[-|]*'] run_cmd_qa(cmd, qa, no_qa=no_qa, log_all=True, simple=True)
def build_step(self): """Build WIEN2k by running siteconfig_lapw script again.""" self.log.debug('%s part II (build_step)' % self.cfgscript) cmd = "./%s" % self.cfgscript qanda = { 'L Perl path (if not in /usr/bin/perl) Q Quit Selection:': 'R', 'A Compile all programs S Select program Q Quit Selection:': 'A', 'Press RETURN to continue': '\nQ', # also answer on first qanda pattern with 'Q' to quit ' Please enter the full path of the perl program: ':'', } no_qa = [ "%s[ \t]*.*" % os.getenv('MPIF90'), "%s[ \t]*.*" % os.getenv('F90'), "%s[ \t]*.*" % os.getenv('CC'), "mv[ \t]*.*", ".*SRC_.*", ".*: warning .*", ".*Stop.", "Compile time errors (if any) were:", "Please enter the full path of the perl program:", ] self.log.debug("no_qa for %s: %s" % (cmd, no_qa)) run_cmd_qa(cmd, qanda, no_qa=no_qa, log_all=True, simple=True)
def install_step(self): """Custom install procedure for SAS.""" qa = { "SAS Home:": self.installdir, "Install SAS Software (default: Yes):": '', "Configure SAS Software (default: Yes):": '', "SAS Installation Data File:": '', "Press Enter to continue:": '', "Configure as a Unicode server (default: No):": 'N', "SAS/ACCESS Interface to MySQL (default: Yes):": 'N', "SAS/ACCESS Interface to Oracle (default: Yes):": 'N', "SAS/ACCESS Interface to Sybase (default: Yes):": 'N', "SAS/ACCESS Interface to SAP ASE (default: Yes):": 'N', "Use PAM Authentication (default: No):": 'N', "Port Number:": '', "Configure SAS Studio Basic (default: Yes):": 'N', "Press Enter to finish:": '', } std_qa = { "Incomplete Deployment\s*(.*[^:])+Selection:": '2', # 2: Ignore previous deployment and start again "Select a language(.*[^:]\s*\n)+Selection:": '', "Select Deployment Task\s*(.*[^:]\s*\n)+Selection:": '', "Specify SAS Home\s*(.*[^:]\s*\n)+Selection:": '2', # Create a new SAS Home "Select Deployment Type\s*(.*[^:]\n)+Selection:": '2', # 2: Install SAS Foundation "Select Products to Install\s*(.*[^:]\n)+Selection:": '1', # SAS Foundation "Product\s*(.*[^:]\n)+Selections:": '', "Select Language Support\s*(.*[^:]\n)+Selections:": '', "Select Regional Settings\s*(.*[^:]\n)+Selection:": '', "Select Support Option\s*(.*[^:]\n)+Selection:": '2', # 2: Do Not Send } no_qa = [ "\.\.\.$", ] run_cmd_qa("./setup.sh -console", qa, no_qa=no_qa, std_qa=std_qa, log_all=True, simple=True)
def install_step(self): """Custom install procedure for RepeatMasker.""" super(EB_RepeatMasker, self).install_step() # check for required dependencies perl_root = get_software_root('Perl') if perl_root: perl = os.path.join(perl_root, 'bin', 'perl') else: raise EasyBuildError("Missing required dependency: Perl") trf_root = get_software_root('TRF') if trf_root: trf = os.path.join(trf_root, 'trf') else: raise EasyBuildError("Missing required dependency: TRF") # determine which search engine to use # see also http://www.repeatmasker.org/RMDownload.html cand_search_engines = ['CrossMatch', 'RMBlast', 'WUBlast', 'HMMER'] search_engine = None for dep in cand_search_engines: if get_software_root(dep): if search_engine is None: search_engine = dep else: raise EasyBuildError("Found multiple candidate search engines: %s and %s", search_engine, dep) if search_engine is None: raise EasyBuildError("No search engine found, one of these must be included as dependency: %s", ' '.join(cand_search_engines)) change_dir(self.installdir) patch_perl_script_autoflush('configure') search_engine_map = { 'CrossMatch': '1', 'RMBlast': '2', 'WUBlast': '3', 'HMMER': '4', } search_engine_bindir = os.path.join(get_software_root(search_engine), 'bin') cmd = "perl ./configure" qa = { '<PRESS ENTER TO CONTINUE>': '', # select search engine 'Enter Selection:': search_engine_map[search_engine], } std_qa = { r'\*\*PERL PROGRAM\*\*\n([^*]*\n)+Enter path.*': perl, r'\*\*REPEATMASKER INSTALLATION DIRECTORY\*\*\n([^*]*\n)+Enter path.*': self.installdir, r'\*\*TRF PROGRAM\*\*\n([^*]*\n)+Enter path.*': trf, # search engine installation path (location of /bin subdirectory) # also enter 'Y' to confirm + '5' ("Done") to complete selection process for search engine r'\*\*.* INSTALLATION PATH\*\*\n([^*]*\n)+Enter path.*': search_engine_bindir + '\nY\n5', } run_cmd_qa(cmd, qa, std_qa=std_qa, log_all=True, simple=True, log_ok=True)
def build_step(self): """Build Geant4.""" if LooseVersion(self.version) >= LooseVersion("9.4"): super(EB_Geant4, self).build_step() else: pwd = self.cfg['start_dir'] cmd = "%s/Configure -build" % pwd run_cmd_qa(cmd, self.qanda, no_qa=self.noqanda, log_all=True, simple=True)
def install_step(self): """Install by running install script.""" altver = '-'.join(self.version.split('.')) cmd = "./install-%s-%s%s.sh -accept" % (self.name.lower(), altver, self.cfg['versionsuffix']) qa = {'The directory will be created if it does not already exist. >': self.installdir} run_cmd_qa(cmd, qa, log_all=True, simple=True)
def install_step(self): """ Custom install procedure for Molpro. For source install: * put license token in place in $installdir/.token * run 'make tuning' * install with 'make install' For binary install: * run interactive installer """ if self.cfg['precompiled_binaries']: """Build by running the command with the inputfiles""" try: os.chdir(self.cfg['start_dir']) except OSError as err: raise EasyBuildError("Failed to move (back) to %s: %s", self.cfg['start_dir'], err) for src in self.src: if LooseVersion(self.version) >= LooseVersion('2015'): # install dir must be non-existent shutil.rmtree(self.installdir) cmd = "./{0} -batch -prefix {1}".format(src['name'], self.installdir) else: cmd = "./{0} -batch -instbin {1}/bin -instlib {1}/lib".format(src['name'], self.installdir) # questions whose text must match exactly as asked qa = { "Please give your username for accessing molpro\n": '', "Please give your password for accessing molpro\n": '', } # questions whose text may be matched as a regular expression stdqa = { r"Enter installation directory for executable files \[.*\]\n": os.path.join(self.installdir, 'bin'), r"Enter installation directory for library files \[.*\]\n": os.path.join(self.installdir, 'lib'), r"directory .* does not exist, try to create [Y]/n\n": '', } run_cmd_qa(cmd, qa=qa, std_qa=stdqa, log_all=True, simple=True) else: if os.path.isfile(self.license_token): run_cmd("make tuning") super(EB_Molpro, self).install_step() # put original LAUNCHER definition back in place in bin/molpro that got installed, # since the value used during installation point to temporary files molpro_path = os.path.join(self.full_prefix, 'bin', 'molpro') apply_regex_substitutions(molpro_path, [(r"^(LAUNCHER\s*=\s*).*$", r"\1 %s" % self.orig_launcher)]) if self.cleanup_token_symlink: try: os.remove(self.license_token) self.log.debug("Symlink to license token %s removed", self.license_token) except OSError as err: raise EasyBuildError("Failed to remove %s: %s", self.license_token, err)
def install_step(self): cmd = "./install.sh" qanda = { 'Please enter the BiSearch root directory: ': self.installdir, 'Please enter the path of c++ compiler [/usr/bin/g++]: ': os.getenv('CXX') } no_qa = [r'Compiling components\s*\.*'] run_cmd_qa(cmd, qanda, no_qa=no_qa, log_all=True, simple=True)
def test_dry_run(self): """Test use of functions under (extended) dry run.""" build_options = { 'extended_dry_run': True, 'silent': False, } init_config(build_options=build_options) self.mock_stdout(True) run_cmd("somecommand foo 123 bar") txt = self.get_stdout() self.mock_stdout(False) expected_regex = re.compile('\n'.join([ r" running command \"somecommand foo 123 bar\"", r" \(in .*\)", ])) self.assertTrue(expected_regex.match(txt), "Pattern %s matches with: %s" % (expected_regex.pattern, txt)) # check disabling 'verbose' self.mock_stdout(True) run_cmd("somecommand foo 123 bar", verbose=False) txt = self.get_stdout() self.mock_stdout(False) self.assertEqual(txt, '') # check forced run outfile = os.path.join(self.test_prefix, 'cmd.out') self.assertFalse(os.path.exists(outfile)) self.mock_stdout(True) run_cmd("echo 'This is always echoed' > %s" % outfile, force_in_dry_run=True) txt = self.get_stdout() self.mock_stdout(False) # nothing printed to stdout, but command was run self.assertEqual(txt, '') self.assertTrue(os.path.exists(outfile)) self.assertEqual(read_file(outfile), "This is always echoed\n") # Q&A commands self.mock_stdout(True) run_cmd_qa("some_qa_cmd", {'question1': 'answer1'}) txt = self.get_stdout() self.mock_stdout(False) expected_regex = re.compile('\n'.join([ r" running interactive command \"some_qa_cmd\"", r" \(in .*\)", ])) self.assertTrue(expected_regex.match(txt), "Pattern %s matches with: %s" % (expected_regex.pattern, txt))
def extract_step(self): """Unpack WIEN2k sources using gunzip and provided expand_lapw script.""" super(EB_WIEN2k, self).extract_step() cmd = "gunzip *gz" run_cmd(cmd, log_all=True, simple=True) cmd = "./expand_lapw" qanda = {'continue (y/n)': 'y'} no_qa = [ 'tar -xf.*', '.*copied and linked.*', ] run_cmd_qa(cmd, qanda, no_qa=no_qa, log_all=True, simple=True)
def configure_step(self): """Configure Qt using interactive `configure` script.""" self.cfg.update('configopts', '-release') platform = None comp_fam = self.toolchain.comp_family() if self.cfg['platform']: platform = self.cfg['platform'] # if no platform is specified, try to derive it based on compiler in toolchain elif comp_fam in [toolchain.GCC]: #@UndefinedVariable platform = 'linux-g++-64' elif comp_fam in [toolchain.INTELCOMP]: #@UndefinedVariable if LooseVersion(self.version) >= LooseVersion('4'): platform = 'linux-icc-64' else: platform = 'linux-icc' # fix -fPIC flag (-KPIC is not correct for recent Intel compilers) qmake_conf = os.path.join('mkspecs', platform, 'qmake.conf') apply_regex_substitutions(qmake_conf, [('-KPIC', '-fPIC')]) if platform: self.cfg.update('configopts', "-platform %s" % platform) else: raise EasyBuildError("Don't know which platform to set based on compiler family.") # configure Qt such that xmlpatterns is also installed # -xmlpatterns is not a known configure option for Qt 5.x, but there xmlpatterns support is enabled by default if LooseVersion(self.version) >= LooseVersion('4') and LooseVersion(self.version) < LooseVersion('5'): self.cfg.update('configopts', '-xmlpatterns') cmd = "%s ./configure -prefix %s %s" % (self.cfg['preconfigopts'], self.installdir, self.cfg['configopts']) qa = { "Type 'o' if you want to use the Open Source Edition.": 'o', "Do you accept the terms of either license?": 'yes', "Which edition of Qt do you want to use?": 'o', } no_qa = [ "for .*pro", r"%s.*" % os.getenv('CXX', '').replace('+', '\\+'), # need to escape + in 'g++' "Reading .*", "WARNING .*", "Project MESSAGE:.*", "rm -f .*", 'Creating qmake...', 'Checking for .*...', ] run_cmd_qa(cmd, qa, no_qa=no_qa, log_all=True, simple=True, maxhits=120)
def test_run_cmd_qa_trace(self): """Test run_cmd under --trace""" # replace log.experimental with log.warning to allow experimental code easybuild.tools.utilities._log.experimental = easybuild.tools.utilities._log.warning init_config(build_options={'trace': True}) self.mock_stdout(True) self.mock_stderr(True) (out, ec) = run_cmd_qa("echo 'n: '; read n; seq 1 $n", {'n: ': '5'}) stdout = self.get_stdout() stderr = self.get_stderr() self.mock_stdout(False) self.mock_stderr(False) self.assertEqual(stderr, '') pattern = "^ >> running interactive command:\n" pattern += "\t\[started at: .*\]\n" pattern += "\t\[output logged in .*\]\n" pattern += "\techo \'n: \'; read n; seq 1 \$n\n" pattern += ' >> interactive command completed: exit 0, ran in .*' self.assertTrue(re.search(pattern, stdout), "Pattern '%s' found in: %s" % (pattern, stdout)) # trace output can be disabled on a per-command basis self.mock_stdout(True) self.mock_stderr(True) (out, ec) = run_cmd("echo hello", trace=False) stdout = self.get_stdout() stderr = self.get_stderr() self.mock_stdout(False) self.mock_stderr(False) self.assertEqual(stdout, '') self.assertEqual(stderr, '')
def test_run_cmd_qa(self): """Basic test for run_cmd_qa function.""" (out, ec) = run_cmd_qa("echo question; read x; echo $x", {"question": "answer"}) self.assertEqual(out, "question\nanswer\n") # no reason echo hello could fail self.assertEqual(ec, 0)
def post_install_step(self): """Activate installation by using activation key, if provided.""" if self.cfg['activation_key']: # activation key is printed by using '$ActivationKey' in Mathematica, so no reason to keep it 'secret' self.log.info("Activating installation using provided activation key '%s'." % self.cfg['activation_key']) qa = { r"(enter return to skip Web Activation):": self.cfg['activation_key'], r"In[1]:= ": 'Quit[]', } noqa = [ '^%s %s .*' % (self.name, self.version), '^Copyright.*', ] run_cmd_qa(os.path.join(self.installdir, 'bin', 'math'), qa, no_qa=noqa) else: self.log.info("No activation key provided, so skipping activation of the installation.")
def install_step(self): """Install FDTD Solutions using install.sh script.""" cmd = "./install.sh" acceptq = ''.join([ "If you accept the terms above, type ACCEPT, otherwise press <enter> ", "to cancel the install [REJECT]:" ]) qa = { acceptq: "ACCEPT", "Please select an option from the list [1]:": '1', "Please enter the install directory [/opt/lumerical/fdtd]:": self.installdir, } no_qa = [ ] std_qa = { "Press <enter> to continue.*": '' } run_cmd_qa(cmd, qa, no_qa=no_qa, std_qa=std_qa, log_all=True, simple=True)
def configure_step(self): """Custom configuration procedure for HEALPix.""" cfitsio = get_software_root('CFITSIO') if not cfitsio: raise EasyBuildError("Failed to determine root for CFITSIO, module not loaded?") self.comp_fam = self.toolchain.comp_family() if self.comp_fam == toolchain.INTELCOMP: #@UndefinedVariable cxx_config = '4' # linux_icc elif self.comp_fam == toolchain.GCC: #@UndefinedVariable cxx_config = '2' # generic_gcc else: raise EasyBuildError("Don't know how which C++ configuration for the used toolchain.") cmd = "./configure -L" qa = { "Should I attempt to create these directories (Y\|n)?": 'Y', "full name of cfitsio library (libcfitsio.a):": '', "Do you want this modification to be done (y\|N)?": 'y', "enter suffix for directories ():": '', # configure for C (2), Fortran (3), C++ (4), then exit (0) "Enter your choice (configuration of packages can be done in any order):": ['2', '3', '4', '0'], } std_qa = { r"C compiler you want to use \(\S*\):": os.environ['CC'], r"enter name of your F90 compiler \(\S*\):": os.environ['F90'], r"enter name of your C compiler \(\S*\):": os.environ['CC'], r"options for C compiler \([^)]*\):": os.environ['CFLAGS'], r"enter compilation/optimisation flags for C compiler \([^)]*\):": os.environ['CFLAGS'], r"compilation flags for %s compiler \([^:]*\):" % os.environ['F90']: '', r"enter optimisation flags for %s compiler \([^)]*\):" % os.environ['F90']: os.environ['F90FLAGS'], r"location of cfitsio library \(\S*\):": os.path.join(cfitsio, 'lib'), r"cfitsio header fitsio.h \(\S*\):": os.path.join(cfitsio, 'include'), r"enter command for library archiving \([^)]*\):": '', r"archive creation \(and indexing\) command \([^)]*\):": '', r"A static library is produced by default. Do you also want a shared library.*": 'y', r"Available configurations for C\+\+ compilation are:[\s\n\S]*Choose one number:": cxx_config, r"PGPLOT.[\s\n]*Do you want to enable this option \?[\s\n]*\([^)]*\) \(y\|N\)": 'N', r"the parallel implementation[\s\n]*Enter choice.*": '1', } run_cmd_qa(cmd, qa, std_qa=std_qa, log_all=True, simple=True, log_ok=True)
def test_run_cmd_qa_log_all(self): """Test run_cmd_qa with log_output enabled""" (out, ec) = run_cmd_qa("echo 'n: '; read n; seq 1 $n", {'n: ': '5'}, log_all=True) self.assertEqual(ec, 0) self.assertEquals(out, "n: \n1\n2\n3\n4\n5\n") run_cmd_logs = glob.glob(os.path.join(self.test_prefix, '*', 'easybuild-run_cmd_qa*.log')) self.assertEqual(len(run_cmd_logs), 1) run_cmd_log_txt = read_file(run_cmd_logs[0]) extra_pref = "# output for interactive command: echo 'n: '; read n; seq 1 $n\n\n" self.assertEquals(run_cmd_log_txt, extra_pref + "n: \n1\n2\n3\n4\n5\n")
def test_run_cmd_qa_answers(self): """Test providing list of answers in run_cmd_qa.""" cmd = "echo question; read x; echo $x; " * 2 qa = {"question": ["answer1", "answer2"]} (out, ec) = run_cmd_qa(cmd, qa) self.assertEqual(out, "question\nanswer1\nquestion\nanswer2\n") self.assertEqual(ec, 0) (out, ec) = run_cmd_qa(cmd, {}, std_qa=qa) self.assertEqual(out, "question\nanswer1\nquestion\nanswer2\n") self.assertEqual(ec, 0) self.assertErrorRegex(EasyBuildError, "Invalid type for answer", run_cmd_qa, cmd, {'q': 1}) # test cycling of answers cmd = cmd * 2 (out, ec) = run_cmd_qa(cmd, {}, std_qa=qa) self.assertEqual(out, "question\nanswer1\nquestion\nanswer2\n" * 2) self.assertEqual(ec, 0)
def install_step(self): """Custom install procedure for Stata.""" change_dir(self.installdir) cmd = os.path.join(self.cfg['start_dir'], 'install') std_qa = { "Do you wish to continue\?\s*\(y/n or q to quit\)": 'y', "Are you sure you want to install into .*\?\s*\(y/n or q\)": 'y', "Okay to proceed\s*\(y/n or q to quit\)": 'y', } no_qa = [ "About to proceed with installation:", "uncompressing files", "extracting files", "setting permissions", ] run_cmd_qa(cmd, {}, no_qa=no_qa, std_qa=std_qa, log_all=True, simple=True) print_msg("Note: you need to manually run ./stinit in %s to initialise the license for Stata!" % self.installdir)
def install_step(self): """Custom install procedure for Samcef.""" # e.g.: 17.0-03 => 17, 17.0, 170 maj_ver = self.version.split('.')[0] main_ver = self.version.split('-')[0] flat_ver = ''.join(main_ver.split('.')) qa = { "Default language ? (E=English, F=French, default E): ": 'E', "Default Postscript printer ? (default: none): ": '', "Type RETURN to continue": '', } no_qa = [] std_qa = { r"Installation for:.*[\s\n]*Continue \? \(y/n, default y\):": 'y', r" 1 Install Samcef %s \(%s\)[\s\n]*.*[\s\n]*Install type .*" % (maj_ver, main_ver): '1', r"Install SHORT INTEGERS VERSION \(i4\)[\s\na-zA-Z0-9().-]*Continue \? \(y/n, default y\):": 'n', r"Install LONG INTEGERS VERSION \(i8\)[\s\na-zA-Z0-9().-]*Continue \? \(y/n, default y\):": 'y', r"Pathname of install directory \(.*\):": self.installdir, r"Directory .* exists, use it \? \(y/n, default y\):": 'y', r"Installation directory\s*:.*[\s\n]*.*[\s\n]*Continue \? \(y/n, default:y\):": 'y', # option '2' is SAMCEF + object libraries r"Selection size: 0[\s\n]*Your selection:": '2', # 'i' for install after making a selection r"Selection size: [1-9][0-9]*[\s\n]*Your selection:": 'i', r"Prerequisite OK[\s\n]*Continue \? \(y/n, default y\):": 'y', r"Samcef users can modify these values.*[\s\n]*Continue \? \(y/n, default y\):": 'y', r"What is the hostname of your license server \( without at sign @ \) \? ": 'localhost', r"Confirm .* as the LMS Samtech Licence server \? \(y/n, default n\): ": 'y', r"2 Floating RLM license[\s\n]*Type a value \(1/2, default 1 \)": '2', } # e.g., v170_inst.csh install_script = './v%s_inst.csh' % flat_ver # make sure script is executable (unpack with 7z doesn't preserve permissions) adjust_permissions(install_script, stat.S_IXUSR, add=True) run_cmd_qa(install_script, qa, no_qa=no_qa, std_qa=std_qa, log_all=True, simple=True)
def install_step(self): """Install CUDA using Perl install script.""" # define how to run the installer # script has /usr/bin/perl hardcoded, but we want to have control over which perl is being used if LooseVersion(self.version) <= LooseVersion("5"): install_script = "install-linux.pl" install_script_path = os.path.join(self.builddir, install_script) cmd = "perl ./%s --prefix=%s %s" % (install_script, self.installdir, self.cfg['installopts']) else: # the following would require to include "osdependencies = 'libglut'" because of samples # installparams = "-samplespath=%(x)s/samples/ -toolkitpath=%(x)s -samples -toolkit" % {'x': self.installdir} install_script = "cuda-installer.pl" installparams = "-toolkitpath=%s -toolkit" % self.installdir cmd = "perl ./%s -verbose -silent %s %s" % (install_script, installparams, self.cfg['installopts']) # prepare for running install script autonomously qanda = {} stdqa = { # this question is only asked if CUDA tools are already available system-wide r"Would you like to remove all CUDA files under .*? (yes/no/abort): ": "no", } noqanda = [ r"^Configuring", r"Installation Complete", r"Verifying archive integrity.*", r"^Uncompressing NVIDIA CUDA", r".* -> .*", ] # patch install script to handle Q&A autonomously patch_perl_script_autoflush(os.path.join(self.builddir, install_script)) # make sure $DISPLAY is not defined, which may lead to (weird) problems # this is workaround for not being able to specify --nox11 to the Perl install scripts if 'DISPLAY' in os.environ: os.environ.pop('DISPLAY') #overriding maxhits default value to 300 (300s wait for nothing to change in the output without seeing a known question) run_cmd_qa(cmd, qanda, std_qa=stdqa, no_qa=noqanda, log_all=True, simple=True, maxhits=300)
def install_step(self): """Interactive install of Modeller.""" if self.cfg['key'] is None: raise EasyBuildError("Easyconfig parameter 'key' is not defined") cmd = "%s/Install" % self.cfg['start_dir'] # by default modeller tries to install to $HOME/bin/modeller9.13 # get this path to use it in the question/answer default_install_path = "[%s]:" % os.path.join(os.path.expanduser('~'), 'bin', 'modeller%s' % self.cfg['version']) qa = { # installer will autodetect the right arch. [3] = x86_64 'Select the type of your computer from the list above [3]:': '', default_install_path: self.installdir, 'http://salilab.org/modeller/registration.html:': self.cfg["key"], 'Press <Enter> to begin the installation:': '', 'Press <Enter> to continue:': '' } run_cmd_qa(cmd, qa, log_all=True, simple=True)
def build_step(self): """Build OpenFOAM using make after sourcing script to set environment.""" precmd = "source %s" % os.path.join(self.builddir, self.openfoamdir, "etc", "bashrc") # make directly in install directory cmd_tmpl = "%(precmd)s && %(prebuildopts)s %(makecmd)s" % { 'precmd': precmd, 'prebuildopts': self.cfg['prebuildopts'], 'makecmd': os.path.join(self.builddir, self.openfoamdir, '%s'), } if 'extend' in self.name.lower() and LooseVersion( self.version) >= LooseVersion('3.0'): qa = { "Proceed without compiling ParaView [Y/n]": 'Y', "Proceed without compiling cudaSolvers? [Y/n]": 'Y', } noqa = [ ".* -o .*", "checking .*", "warning.*", "configure: creating.*", "%s .*" % os.environ['CC'], "wmake .*", "Making dependency list for source file.*", "\s*\^\s*", # warning indicator "Cleaning .*", ] run_cmd_qa(cmd_tmpl % 'Allwmake.firstInstall', qa, no_qa=noqa, log_all=True, simple=True) else: run_cmd(cmd_tmpl % 'Allwmake', log_all=True, simple=True, log_output=True)
def install_step(self): """Install Mathematica using install script.""" # make sure $DISPLAY is not set (to avoid that installer uses GUI) orig_display = os.environ.pop('DISPLAY', None) cmd = "./%s_%s_LINUX.sh" % (self.name, self.version) shortver = '.'.join(self.version.split('.')[:2]) qa_install_path = "/usr/local/Wolfram/%s/%s" % (self.name, shortver) qa = { r"Enter the installation directory, or press ENTER to select %s: >" % qa_install_path: self.installdir, r"Create directory (y/n)? >": 'y', r"or press ENTER to select /usr/local/bin: >": os.path.join(self.installdir, "bin"), } no_qa = [ "Now installing.*\n\n.*\[.*\].*", ] run_cmd_qa(cmd, qa, no_qa=no_qa, log_all=True, simple=True) # add license server configuration file # some relevant documentation at http://reference.wolfram.com/mathematica/tutorial/ConfigurationFiles.html mathpass_path = os.path.join(self.installdir, 'Configuration', 'Licensing', 'mathpass') try: # append to file, to avoid overwriting anything that might be there f = open(mathpass_path, "a") f.write("!%s\n" % self.cfg['license_server']) f.close() f = open(mathpass_path, "r") mathpass_txt = f.read() f.close() self.log.info("Updated license file %s: %s" % (mathpass_path, mathpass_txt)) except IOError, err: self.log.error("Failed to update %s with license server info: %s" % (mathpass_path, err))
def build_step(self): """Build WIEN2k by running siteconfig_lapw script again.""" self.log.debug('%s part II (build_step)' % self.cfgscript) cmd = "./%s" % self.cfgscript qanda = { 'Press RETURN to continue': '\nQ', # also answer on first qanda pattern with 'Q' to quit 'Please enter the full path of the perl program: ': self.perlbin, } if LooseVersion(self.version) < LooseVersion("17"): qanda.update({ 'L Perl path (if not in /usr/bin/perl) Q Quit Selection:': 'R', 'A Compile all programs S Select program Q Quit Selection:': 'A', }) else: qanda.update({ 'program Q Quit Selection:': 'A', 'Path Q Quit Selection:': 'R', }) no_qa = [ "%s[ \t]*.*" % os.getenv('MPIF90'), "%s[ \t]*.*" % os.getenv('F90'), "%s[ \t]*.*" % os.getenv('CC'), "mv[ \t]*.*", ".*SRC_.*", ".*: warning .*", ".*Stop.", "Compile time errors (if any) were:", ] self.log.debug("no_qa for %s: %s" % (cmd, no_qa)) run_cmd_qa(cmd, qanda, no_qa=no_qa, log_all=True, simple=True)
def test_run_cmd_qa_log_all(self): """Test run_cmd_qa with log_output enabled""" (out, ec) = run_cmd_qa("echo 'n: '; read n; seq 1 $n", {'n: ': '5'}, log_all=True) self.assertEqual(ec, 0) self.assertEqual(out, "n: \n1\n2\n3\n4\n5\n") run_cmd_logs = glob.glob( os.path.join(self.test_prefix, '*', 'easybuild-run_cmd_qa*.log')) self.assertEqual(len(run_cmd_logs), 1) run_cmd_log_txt = read_file(run_cmd_logs[0]) extra_pref = "# output for interactive command: echo 'n: '; read n; seq 1 $n\n\n" self.assertEqual(run_cmd_log_txt, extra_pref + "n: \n1\n2\n3\n4\n5\n")
def build_step(self): """Build OpenFOAM using make after sourcing script to set environment.""" precmd = "source %s" % os.path.join(self.builddir, self.openfoamdir, "etc", "bashrc") if 'extend' not in self.name.lower() and LooseVersion(self.version) >= LooseVersion('4.0'): cleancmd = "cd $WM_PROJECT_DIR && wcleanPlatform -all && cd -" else: cleancmd = "wcleanAll" # make directly in install directory cmd_tmpl = "%(precmd)s && %(cleancmd)s && %(prebuildopts)s %(makecmd)s" % { 'precmd': precmd, 'cleancmd': cleancmd, 'prebuildopts': self.cfg['prebuildopts'], 'makecmd': os.path.join(self.builddir, self.openfoamdir, '%s'), } if 'extend' in self.name.lower() and LooseVersion(self.version) >= LooseVersion('3.0'): qa = { "Proceed without compiling ParaView [Y/n]": 'Y', "Proceed without compiling cudaSolvers? [Y/n]": 'Y', } noqa = [ ".* -o .*", "checking .*", "warning.*", "configure: creating.*", "%s .*" % os.environ['CC'], "wmake .*", "Making dependency list for source file.*", r"\s*\^\s*", # warning indicator "Cleaning .*", ] run_cmd_qa(cmd_tmpl % 'Allwmake.firstInstall', qa, no_qa=noqa, log_all=True, simple=True) else: cmd = 'Allwmake' if LooseVersion(self.version) >= LooseVersion('1606'): # use Allwmake -log option if possible since this can be useful during builds, but also afterwards cmd += ' -log' run_cmd(cmd_tmpl % cmd, log_all=True, simple=True, log_output=True)
def install_step(self): """Interactive install of Maple.""" cmd = "%s/Maple%sLinuxX86_64Installer.bin" % (self.builddir, self.cfg['version']) qa = { 'PRESS <ENTER> TO CONTINUE:': '', 'DO YOU ACCEPT THE TERMS OF THIS LICENSE AGREEMENT? (Y/N):': 'Y', 'ENTER AN ABSOLUTE PATH, OR PRESS <ENTER> TO ACCEPT THE DEFAULT :': self.installdir, 'IS THIS CORRECT? (Y/N):': 'Y', 'Do you wish to have a shortcut installed on your desktop? ->1- Yes 2- No ENTER THE NUMBER FOR YOUR CHOICE, OR PRESS <ENTER> TO ACCEPT THE DEFAULT::': '2', '->1- Single User License 2- Network License ENTER THE NUMBER FOR YOUR CHOICE, OR PRESS <ENTER> TO ACCEPT THE DEFAULT::': '2', 'PRESS <ENTER> TO EXIT THE INSTALLER:': '', 'License server (DEFAULT: ):': self.cfg['license_server'], 'Port number (optional) (DEFAULT: ):': '', '->1- Configure toolbox for Matlab 2- Do not configure at this time ENTER THE NUMBER FOR YOUR CHOICE, OR PRESS <ENTER> TO ACCEPT THE DEFAULT::': '2' } no_qa = [ 'Graphical installers are not supported by the VM. The console mode will be used instead...', 'Extracting the JRE from the installer archive...', 'Launching installer...', "Configuring the installer for this system's environment...", 'Unpacking the JRE...', '\[[-|]*' ] run_cmd_qa(cmd, qa, no_qa=no_qa, log_all=True, simple=True)
def install_step(self): """ Custom install procedure for Molpro. For source install: * put license token in place in $installdir/.token * run 'make tuning' * install with 'make install' For binary install: * run interactive installer """ if self.cfg['precompiled_binaries']: """Build by running the command with the inputfiles""" try: os.chdir(self.cfg['start_dir']) except OSError, err: raise EasyBuildError("Failed to move (back) to %s: %s", self.cfg['start_dir'], err) for src in self.src: if LooseVersion(self.version) >= LooseVersion('2015'): # install dir must be non-existent shutil.rmtree(self.installdir) cmd = "./{0} -batch -prefix {1}".format(src['name'], self.installdir) else: cmd = "./{0} -batch -instbin {1}/bin -instlib {1}/lib".format(src['name'], self.installdir) # questions whose text must match exactly as asked qa = { "Please give your username for accessing molpro\n": '', "Please give your password for accessing molpro\n": '', } # questions whose text may be matched as a regular expression stdqa = { r"Enter installation directory for executable files \[.*\]\n": os.path.join(self.installdir, 'bin'), r"Enter installation directory for library files \[.*\]\n": os.path.join(self.installdir, 'lib'), r"directory .* does not exist, try to create [Y]/n\n": '', } run_cmd_qa(cmd, qa=qa, std_qa=stdqa, log_all=True, simple=True)
def configure_step(self): """Custom configuration procedure for HEALPix.""" cfitsio = get_software_root('CFITSIO') if not cfitsio: raise EasyBuildError("Failed to determine root for CFITSIO, module not loaded?") cmd = "./configure -L" qa = { r"Should I attempt to create these directories (Y\|n)?": 'Y', "full name of cfitsio library (libcfitsio.a):": '', r"Do you want this modification to be done (y\|N)?": 'y', "enter suffix for directories ():": '', # configure for C (2), Fortran (3), C++ (4), then exit (0) "Enter your choice (configuration of packages can be done in any order):": ['2', '3', '4', '0'], } std_qa = { r"C compiler you want to use \(\S*\):": os.environ['CC'], r"enter name of your F90 compiler \(\S*\):": os.environ['F90'], r"enter name of your C compiler \(\S*\):": os.environ['CC'], r"options for C compiler \([^)]*\):": os.environ['CFLAGS'], r"enter compilation/optimisation flags for C compiler \([^)]*\):": os.environ['CFLAGS'], r"compilation flags for %s compiler \([^:]*\):" % os.environ['F90']: '', r"enter optimisation flags for %s compiler \([^)]*\):" % os.environ['F90']: os.environ['F90FLAGS'], r"location of cfitsio library \(\S*\):": os.path.join(cfitsio, 'lib'), r"cfitsio header fitsio.h \(\S*\):": os.path.join(cfitsio, 'include'), r"enter command for library archiving \([^)]*\):": '', r"archive creation \(and indexing\) command \([^)]*\):": '', r"A static library is produced by default. Do you also want a shared library.*": 'y', r"Available configurations for C\+\+ compilation are:[\s\n\S]*" + r"(?P<nr>[0-9]+): %s[\s\n\S]*Choose one number:" % self.target_string: '%(nr)s', r"PGPLOT.[\s\n]*Do you want to enable this option \?[\s\n]*\([^)]*\) \(y\|N\)": 'N', r"the parallel implementation[\s\n]*Enter choice.*": '1', r"do you want the HEALPix/C library to include CFITSIO-related functions \? \(Y\|n\):": 'Y', r"\(recommended if the Healpix-F90 library is to be linked to external codes\) \(Y\|n\):": 'Y', # PIC -> Y r"Do you rather want a shared/dynamic library.*": 'n', # shared instead static? -> N } run_cmd_qa(cmd, qa, std_qa=std_qa, log_all=True, simple=True, log_ok=True)
def install_step(self): """Install FDTD Solutions using install.sh script.""" cmd = "./install.sh" acceptq = ''.join([ "If you accept the terms above, type ACCEPT, otherwise press <enter> ", "to cancel the install [REJECT]:" ]) qa = { acceptq: "ACCEPT", "Please select an option from the list [1]:": '1', "Please enter the install directory [/opt/lumerical/fdtd]:": self.installdir, } no_qa = [] std_qa = {"Press <enter> to continue.*": ''} run_cmd_qa(cmd, qa, no_qa=no_qa, std_qa=std_qa, log_all=True, simple=True)
def test_run_cmd_qa_buffering(self): """Test whether run_cmd_qa uses unbuffered output.""" # command that generates a lot of output before waiting for input # note: bug being fixed can be reproduced reliably using 1000, but not with too high values like 100000! cmd = 'for x in $(seq 1000); do echo "This is a number you can pick: $x"; done; ' cmd += 'echo "Pick a number: "; read number; echo "Picked number: $number"' (out, ec) = run_cmd_qa(cmd, {'Pick a number: ': '42'}, log_all=True, maxhits=5) regex = re.compile("Picked number: 42$") self.assertTrue(regex.search(out), "Pattern '%s' found in: %s" % (regex.pattern, out))
def install_step(self): """Interactive install of Modeller.""" if self.cfg['key'] is None: raise EasyBuildError("Easyconfig parameter 'key' is not defined") cmd = "%s/Install" % self.cfg['start_dir'] # by default modeller tries to install to $HOME/bin/modeller9.13 # get this path to use it in the question/answer default_install_path = "[%s]:" % os.path.join( os.path.expanduser('~'), 'bin', 'modeller%s' % self.cfg['version']) qa = { # installer will autodetect the right arch. [3] = x86_64 'Select the type of your computer from the list above [3]:': '', default_install_path: self.installdir, 'http://salilab.org/modeller/registration.html:': self.cfg["key"], 'Press <Enter> to begin the installation:': '', 'Press <Enter> to continue:': '' } run_cmd_qa(cmd, qa, log_all=True, simple=True)
class EB_CPLEX(Binary): """ Support for installing CPLEX. Version 12.2 has a self-extracting binary with a Java installer """ def __init__(self, *args, **kwargs): """Initialize CPLEX-specific variables.""" super(EB_CPLEX, self).__init__(*args, **kwargs) self.bindir = 'UNKNOWN' def install_step(self): """CPLEX has an interactive installer, so use Q&A""" tmpdir = os.path.join(self.builddir, 'tmp') stagedir = os.path.join(self.builddir, 'staged') try: os.chdir(self.builddir) os.makedirs(tmpdir) os.makedirs(stagedir) except OSError, err: raise EasyBuildError("Failed to prepare for installation: %s", err) env.setvar('IATEMPDIR', tmpdir) dst = os.path.join(self.builddir, self.src[0]['name']) cmd = "%s -i console" % dst qanda = { "PRESS <ENTER> TO CONTINUE:": '', 'Press Enter to continue viewing the license agreement, or enter' \ ' "1" to accept the agreement, "2" to decline it, "3" to print it,' \ ' or "99" to go back to the previous screen.:': '1', 'ENTER AN ABSOLUTE PATH, OR PRESS <ENTER> TO ACCEPT THE DEFAULT :': self.installdir, 'IS THIS CORRECT? (Y/N):': 'y', 'PRESS <ENTER> TO INSTALL:': '', "PRESS <ENTER> TO EXIT THE INSTALLER:": '', "CHOOSE LOCALE BY NUMBER:": '', "Choose Instance Management Option:": '', } noqanda = [r'Installing\.\.\..*\n.*------.*\n\n.*============.*\n.*$'] run_cmd_qa(cmd, qanda, no_qa=noqanda, log_all=True, simple=True) try: os.chmod( self.installdir, stat.S_IRWXU | stat.S_IXOTH | stat.S_IXGRP | stat.S_IROTH | stat.S_IRGRP) except OSError, err: raise EasyBuildError("Can't set permissions on %s: %s", self.installdir, err)
def install_step(self): """Custom install procedure for SAS.""" qa = { "SAS Home:": self.installdir, "Install SAS Software (default: Yes):": '', "Configure SAS Software (default: Yes):": '', "SAS Installation Data File:": self.license_file, "Press Enter to continue:": '', "Configure as a Unicode server (default: No):": 'N', "SAS/ACCESS Interface to MySQL (default: Yes):": 'N', "SAS/ACCESS Interface to Oracle (default: Yes):": 'N', "SAS/ACCESS Interface to Sybase (default: Yes):": 'N', "SAS/ACCESS Interface to SAP ASE (default: Yes):": 'N', "Use PAM Authentication (default: No):": 'N', "Port Number:": '', "Configure SAS Studio Basic (default: Yes):": 'N', "Press Enter to finish:": '', "Global Standards Library:": os.path.join(self.installdir, 'cstGlobalLibrary'), "Sample Library:": os.path.join(self.installdir, 'cstSampleLibrary'), } std_qa = { r"Incomplete Deployment\s*(.*[^:])+Selection:": '2', # 2: Ignore previous deployment and start again r"Select a language(.*[^:]\s*\n)+Selection:": '', r"Select Deployment Task\s*(.*[^:]\s*\n)+Selection:": '', r"Specify SAS Home\s*(.*[^:]\s*\n)+Selection:": '2', # Create a new SAS Home r"Select Deployment Type\s*(.*[^:]\n)+Selection:": '2', # 2: Install SAS Foundation r"Select Products to Install\s*(.*[^:]\n)+Selection:": '1', # SAS Foundation r"Product\s*(.*[^:]\n)+Selections:": '', r"Select Language Support\s*(.*[^:]\n)+Selections:": '', r"Select Regional Settings\s*(.*[^:]\n)+Selection:": '', r"Select Support Option\s*(.*[^:]\n)+Selection:": '2', # 2: Do Not Send r"Select SAS Foundation Products(.*[^:]\s*\n)+Selection:": '', } no_qa = [ r"\.\.\.$", ] run_cmd_qa("./setup.sh -console", qa, no_qa=no_qa, std_qa=std_qa, log_all=True, simple=True)
def install_step(self): """CPLEX has an interactive installer, so use Q&A""" tmpdir = os.path.join(self.builddir, 'tmp') stagedir = os.path.join(self.builddir, 'staged') try: os.chdir(self.builddir) os.makedirs(tmpdir) os.makedirs(stagedir) except OSError as err: raise EasyBuildError("Failed to prepare for installation: %s", err) env.setvar('IATEMPDIR', tmpdir) dst = os.path.join(self.builddir, self.src[0]['name']) cmd = "%s -i console" % dst qanda = { "PRESS <ENTER> TO CONTINUE:": '', 'Press Enter to continue viewing the license agreement, or enter' \ ' "1" to accept the agreement, "2" to decline it, "3" to print it,' \ ' or "99" to go back to the previous screen.:': '1', 'ENTER AN ABSOLUTE PATH, OR PRESS <ENTER> TO ACCEPT THE DEFAULT :': self.installdir, 'IS THIS CORRECT? (Y/N):': 'y', 'PRESS <ENTER> TO INSTALL:': '', "PRESS <ENTER> TO EXIT THE INSTALLER:": '', "CHOOSE LOCALE BY NUMBER:": '', "Choose Instance Management Option:": '', } noqanda = [r'Installing\.\.\..*\n.*------.*\n\n.*============.*\n.*$'] run_cmd_qa(cmd, qanda, no_qa=noqanda, log_all=True, simple=True) try: os.chmod(self.installdir, stat.S_IRWXU | stat.S_IXOTH | stat.S_IXGRP | stat.S_IROTH | stat.S_IRGRP) except OSError as err: raise EasyBuildError("Can't set permissions on %s: %s", self.installdir, err)
def post_install_step(self): """Activate installation by using activation key, if provided.""" if self.cfg['activation_key']: # activation key is printed by using '$ActivationKey' in Mathematica, so no reason to keep it 'secret' self.log.info( "Activating installation using provided activation key '%s'." % self.cfg['activation_key']) qa = { r"(enter return to skip Web Activation):": self.cfg['activation_key'], r"In[1]:= ": 'Quit[]', } noqa = [ '^%s %s .*' % (self.name, self.version), '^Copyright.*', ] run_cmd_qa(os.path.join(self.installdir, 'bin', 'math'), qa, no_qa=noqa) else: self.log.info( "No activation key provided, so skipping activation of the installation." )
def run_cmd_qa(cmd, qa, no_qa=None, log_ok=True, log_all=False, simple=False, regexp=True, std_qa=None, path=None): """Legacy wrapper/placeholder for run.run_cmd_qa""" return run.run_cmd_qa(cmd, qa, no_qa=no_qa, log_ok=log_ok, log_all=log_all, simple=simple, regexp=regexp, std_qa=std_qa, path=path)
def test_run_cmd_negative_exit_code(self): """Test run_cmd function with command that has negative exit code.""" # define signal handler to call in case run_cmd takes too long def handler(signum, _): raise RuntimeError("Signal handler called with signal %s" % signum) # set the signal handler and a 3-second alarm signal.signal(signal.SIGALRM, handler) signal.alarm(3) (_, ec) = run_cmd("kill -9 $$", log_ok=False) self.assertEqual(ec, -9) # reset the alarm signal.alarm(0) signal.alarm(3) (_, ec) = run_cmd_qa("kill -9 $$", {}, log_ok=False) self.assertEqual(ec, -9) # disable the alarm signal.alarm(0)
def configure_step(self): """Configure build: - set some magic environment variables - run configure script - adjust configure.wrf file if needed """ # netCDF dependency set_netcdf_env_vars(self.log) self.netcdf_mod_cmds = get_netcdf_module_set_cmds(self.log) # HDF5 (optional) dependency hdf5 = get_software_root('HDF5') if hdf5: # check if this is parallel HDF5 phdf5_bins = ['h5pcc', 'ph5diff'] parallel_hdf5 = True for f in phdf5_bins: if not os.path.exists(os.path.join(hdf5, 'bin', f)): parallel_hdf5 = False break if not (hdf5 or parallel_hdf5): self.log.error("Parallel HDF5 module not loaded?") else: env.setvar('PHDF5', hdf5) else: self.log.info("HDF5 module not loaded, assuming that's OK...") # JasPer dependency check + setting env vars jasper = get_software_root('JasPer') if jasper: jasperlibdir = os.path.join(jasper, "lib") env.setvar('JASPERINC', os.path.join(jasper, "include")) env.setvar('JASPERLIB', jasperlibdir) else: if os.getenv('JASPERINC') or os.getenv('JASPERLIB'): self.log.error( "JasPer module not loaded, but JASPERINC and/or JASPERLIB still set?" ) else: self.log.info( "JasPer module not loaded, assuming that's OK...") # enable support for large file support in netCDF env.setvar('WRFIO_NCD_LARGE_FILE_SUPPORT', '1') # patch arch/Config_new.pl script, so that run_cmd_qa receives all output to answer questions patch_perl_script_autoflush(os.path.join("arch", "Config_new.pl")) # determine build type option to look for build_type_option = None self.comp_fam = self.toolchain.comp_family() if self.comp_fam == toolchain.INTELCOMP: #@UndefinedVariable build_type_option = "Linux x86_64 i486 i586 i686, ifort compiler with icc" elif self.comp_fam == toolchain.GCC: #@UndefinedVariable build_type_option = "x86_64 Linux, gfortran compiler with gcc" else: self.log.error( "Don't know how to figure out build type to select.") # fetch selected build type (and make sure it makes sense) known_build_types = ['serial', 'smpar', 'dmpar', 'dm+sm'] self.parallel_build_types = ["dmpar", "smpar", "dm+sm"] bt = self.cfg['buildtype'] if not bt in known_build_types: self.log.error( "Unknown build type: '%s'. Supported build types: %s" % (bt, known_build_types)) # fetch option number based on build type option and selected build type build_type_question = "\s*(?P<nr>[0-9]+).\s*%s\s*\(%s\)" % ( build_type_option, bt) # run configure script cmd = "./configure" qa = { # named group in match will be used to construct answer "Compile for nesting? (1=basic, 2=preset moves, 3=vortex following) [default 1]:": "1", "Compile for nesting? (0=no nesting, 1=basic, 2=preset moves, 3=vortex following) [default 0]:": "0" } no_qa = [ "testing for fseeko and fseeko64", r"If you wish to change the default options, edit the file:[\s\n]*arch/configure_new.defaults" ] std_qa = { # named group in match will be used to construct answer r"%s.*\n(.*\n)*Enter selection\s*\[[0-9]+-[0-9]+\]\s*:" % build_type_question: "%(nr)s", } run_cmd_qa(cmd, qa, no_qa=no_qa, std_qa=std_qa, log_all=True, simple=True) cfgfile = 'configure.wrf' # make sure correct compilers are being used comps = { 'SCC': os.getenv('CC'), 'SFC': os.getenv('F90'), 'CCOMP': os.getenv('CC'), 'DM_FC': os.getenv('MPIF90'), 'DM_CC': "%s -DMPI2_SUPPORT" % os.getenv('MPICC'), } for line in fileinput.input(cfgfile, inplace=1, backup='.orig.comps'): for (k, v) in comps.items(): line = re.sub(r"^(%s\s*=\s*).*$" % k, r"\1 %s" % v, line) sys.stdout.write(line) # rewrite optimization options if desired if self.cfg['rewriteopts']: # replace default -O3 option in configure.wrf with CFLAGS/FFLAGS from environment self.log.info("Rewriting optimization options in %s" % cfgfile) # set extra flags for Intel compilers # see http://software.intel.com/en-us/forums/showthread.php?t=72109&p=1#146748 if self.comp_fam == toolchain.INTELCOMP: #@UndefinedVariable # -O3 -heap-arrays is required to resolve compilation error for envvar in ['CFLAGS', 'FFLAGS']: val = os.getenv(envvar) if '-O3' in val: env.setvar(envvar, '%s -heap-arrays' % val) self.log.info("Updated %s to '%s'" % (envvar, os.getenv(envvar))) # replace -O3 with desired optimization options for line in fileinput.input(cfgfile, inplace=1, backup='.orig.rewriteopts'): line = re.sub(r"^(FCOPTIM.*)(\s-O3)(\s.*)$", r"\1 %s \3" % os.getenv('FFLAGS'), line) line = re.sub(r"^(CFLAGS_LOCAL.*)(\s-O3)(\s.*)$", r"\1 %s \3" % os.getenv('CFLAGS'), line) sys.stdout.write(line)
def configure_step(self): """Custom configuration procedure for HEALPix.""" cfitsio = get_software_root('CFITSIO') if not cfitsio: raise EasyBuildError( "Failed to determine root for CFITSIO, module not loaded?") self.comp_fam = self.toolchain.comp_family() if self.comp_fam == toolchain.INTELCOMP: #@UndefinedVariable cxx_config = '4' # linux_icc elif self.comp_fam == toolchain.GCC: #@UndefinedVariable cxx_config = '2' # generic_gcc else: raise EasyBuildError( "Don't know how which C++ configuration for the used toolchain." ) cmd = "./configure -L" qa = { "Should I attempt to create these directories (Y\|n)?": 'Y', "full name of cfitsio library (libcfitsio.a):": '', "Do you want this modification to be done (y\|N)?": 'y', "enter suffix for directories ():": '', # configure for C (2), Fortran (3), C++ (4), then exit (0) "Enter your choice (configuration of packages can be done in any order):": ['2', '3', '4', '0'], } std_qa = { r"C compiler you want to use \(\S*\):": os.environ['CC'], r"enter name of your F90 compiler \(\S*\):": os.environ['F90'], r"enter name of your C compiler \(\S*\):": os.environ['CC'], r"options for C compiler \([^)]*\):": os.environ['CFLAGS'], r"enter compilation/optimisation flags for C compiler \([^)]*\):": os.environ['CFLAGS'], r"compilation flags for %s compiler \([^:]*\):" % os.environ['F90']: '', r"enter optimisation flags for %s compiler \([^)]*\):" % os.environ['F90']: os.environ['F90FLAGS'], r"location of cfitsio library \(\S*\):": os.path.join(cfitsio, 'lib'), r"cfitsio header fitsio.h \(\S*\):": os.path.join(cfitsio, 'include'), r"enter command for library archiving \([^)]*\):": '', r"archive creation \(and indexing\) command \([^)]*\):": '', r"A static library is produced by default. Do you also want a shared library.*": 'y', r"Available configurations for C\+\+ compilation are:[\s\n\S]*Choose one number:": cxx_config, r"PGPLOT.[\s\n]*Do you want to enable this option \?[\s\n]*\([^)]*\) \(y\|N\)": 'N', r"the parallel implementation[\s\n]*Enter choice.*": '1', } run_cmd_qa(cmd, qa, std_qa=std_qa, log_all=True, simple=True, log_ok=True)
def configure_step(self): """Custom configuration procedure for ALADIN.""" # unset $LIBRARY_PATH set by modules of dependencies, because it may screw up linking if 'LIBRARY_PATH' in os.environ: self.log.debug("Unsetting $LIBRARY_PATH (was: %s)" % os.environ['LIBRARY_PATH']) self.orig_library_path = os.environ.pop('LIBRARY_PATH') # build auxiliary libraries auxlibs_dir = None my_gnu = None if self.toolchain.comp_family() == toolchain.GCC: my_gnu = 'y' # gfortran for var in ['CFLAGS', 'CXXFLAGS', 'F90FLAGS', 'FFLAGS']: flags = os.getenv(var) env.setvar(var, "%s -fdefault-real-8 -fdefault-double-8" % flags) self.log.info("Updated %s to '%s'" % (var, os.getenv(var))) elif self.toolchain.comp_family() == toolchain.INTELCOMP: my_gnu = 'i' # icc/ifort else: raise EasyBuildError("Don't know how to set 'my_gnu' variable in auxlibs build script.") self.log.info("my_gnu set to '%s'" % my_gnu) tmp_installroot = tempfile.mkdtemp(prefix='aladin_auxlibs_') try: cwd = os.getcwd() os.chdir(self.builddir) builddirs = os.listdir(self.builddir) auxlibs_dir = [x for x in builddirs if x.startswith('auxlibs_installer')][0] os.chdir(auxlibs_dir) auto_driver = 'driver_automatic' for line in fileinput.input(auto_driver, inplace=1, backup='.orig.eb'): line = re.sub(r"^(my_gnu\s*=\s*).*$", r"\1%s" % my_gnu, line) line = re.sub(r"^(my_r32\s*=\s*).*$", r"\1n", line) # always 64-bit real precision line = re.sub(r"^(my_readonly\s*=\s*).*$", r"\1y", line) # make libs read-only after build line = re.sub(r"^(my_installroot\s*=\s*).*$", r"\1%s" % tmp_installroot, line) sys.stdout.write(line) run_cmd("./%s" % auto_driver) os.chdir(cwd) except OSError as err: raise EasyBuildError("Failed to build ALADIN: %s", err) # build gmkpack, update PATH and set GMKROOT # we build gmkpack here because a config file is generated in the gmkpack isntall path try: gmkpack_dir = [x for x in builddirs if x.startswith('gmkpack')][0] os.chdir(os.path.join(self.builddir, gmkpack_dir)) qa = { 'Do you want to run the configuration file maker assistant now (y) or later [n] ?': 'n', } run_cmd_qa("./build_gmkpack", qa) os.chdir(cwd) paths = os.getenv('PATH').split(':') paths.append(os.path.join(self.builddir, gmkpack_dir, 'util')) env.setvar('PATH', ':'.join(paths)) env.setvar('GMKROOT', os.path.join(self.builddir, gmkpack_dir)) except OSError as err: raise EasyBuildError("Failed to build gmkpack: %s", err) # generate gmkpack configuration file self.conf_file = 'ALADIN_%s' % self.version self.conf_filepath = os.path.join(self.builddir, 'gmkpack_support', 'arch', '%s.x' % self.conf_file) try: if os.path.exists(self.conf_filepath): os.remove(self.conf_filepath) self.log.info("Removed existing gmpack config file %s" % self.conf_filepath) archdir = os.path.dirname(self.conf_filepath) if not os.path.exists(archdir): mkdir(archdir, parents=True) except OSError as err: raise EasyBuildError("Failed to remove existing file %s: %s", self.conf_filepath, err) mpich = 'n' known_mpi_libs = [toolchain.MPICH, toolchain.MPICH2, toolchain.INTELMPI] if self.toolchain.options.get('usempi', None) and self.toolchain.mpi_family() in known_mpi_libs: mpich = 'y' qpref = 'Please type the ABSOLUTE name of ' qsuff = ', or ignore (environment variables allowed) :' qsuff2 = ', or ignore : (environment variables allowed) :' comp_fam = self.toolchain.comp_family() if comp_fam == toolchain.GCC: gribdir = 'GNU' elif comp_fam == toolchain.INTELCOMP: gribdir = 'INTEL' else: raise EasyBuildError("Don't know which grib lib dir to use for compiler %s", comp_fam) aux_lib_gribex = os.path.join(tmp_installroot, gribdir, 'lib', 'libgribex.a') aux_lib_ibm = os.path.join(tmp_installroot, gribdir, 'lib', 'libibmdummy.a') grib_api_lib = os.path.join(get_software_root('grib_api'), 'lib', 'libgrib_api.a') grib_api_f90_lib = os.path.join(get_software_root('grib_api'), 'lib', 'libgrib_api_f90.a') grib_api_inc = os.path.join(get_software_root('grib_api'), 'include') jasperlib = os.path.join(get_software_root('JasPer'), 'lib', 'libjasper.a') mpilib = os.path.join(os.getenv('MPI_LIB_DIR'), os.getenv('MPI_LIB_SHARED')) # netCDF netcdf = get_software_root('netCDF') netcdf_fortran = get_software_root('netCDF-Fortran') if netcdf: netcdfinc = os.path.join(netcdf, 'include') if netcdf_fortran: netcdflib = os.path.join(netcdf_fortran, get_software_libdir('netCDF-Fortran'), 'libnetcdff.a') else: netcdflib = os.path.join(netcdf, get_software_libdir('netCDF'), 'libnetcdff.a') if not os.path.exists(netcdflib): raise EasyBuildError("%s does not exist", netcdflib) else: raise EasyBuildError("netCDF(-Fortran) not available") ldpaths = [ldflag[2:] for ldflag in os.getenv('LDFLAGS').split(' ')] # LDFLAGS have form '-L/path/to' lapacklibs = [] for lib in os.getenv('LAPACK_STATIC_LIBS').split(','): libpaths = [os.path.join(ldpath, lib) for ldpath in ldpaths] lapacklibs.append([libpath for libpath in libpaths if os.path.exists(libpath)][0]) lapacklib = ' '.join(lapacklibs) blaslibs = [] for lib in os.getenv('BLAS_STATIC_LIBS').split(','): libpaths = [os.path.join(ldpath, lib) for ldpath in ldpaths] blaslibs.append([libpath for libpath in libpaths if os.path.exists(libpath)][0]) blaslib = ' '.join(blaslibs) qa = { 'Do you want to run the configuration file maker assistant now (y) or later [n] ?': 'y', 'Do you want to setup your configuration file for MPICH (y/n) [n] ?': mpich, 'Please type the directory name where to find a dummy file mpif.h or ignore :': os.getenv('MPI_INC_DIR'), '%sthe library gribex or emos%s' % (qpref, qsuff2): aux_lib_gribex, '%sthe library ibm%s' % (qpref, qsuff): aux_lib_ibm, '%sthe library grib_api%s' % (qpref, qsuff): grib_api_lib, '%sthe library grib_api_f90%s' % (qpref, qsuff): grib_api_f90_lib, '%sthe JPEG auxilary library if enabled by Grib_api%s' % (qpref, qsuff2): jasperlib, '%sthe library netcdf%s' % (qpref, qsuff): netcdflib, '%sthe library lapack%s' % (qpref, qsuff): lapacklib, '%sthe library blas%s' % (qpref, qsuff): blaslib, '%sthe library mpi%s' % (qpref, qsuff): mpilib, '%sa MPI dummy library for serial executions, or ignore :' % qpref: '', 'Please type the directory name where to find grib_api headers, or ignore :': grib_api_inc, 'Please type the directory name where to find fortint.h or ignore :': '', 'Please type the directory name where to find netcdf headers, or ignore :': netcdfinc, 'Do you want to define CANARI (y/n) [y] ?': 'y', 'Please type the name of the script file used to generate a preprocessed blacklist file, or ignore :': '', 'Please type the name of the script file used to recover local libraries (gget), or ignore :': '', 'Please type the options to tune the gnu compilers, or ignore :': os.getenv('F90FLAGS'), } f90_seq = os.getenv('F90_SEQ') if not f90_seq: # F90_SEQ is only defined when usempi is enabled f90_seq = os.getenv('F90') stdqa = OrderedDict([ (r'Confirm library .* is .*', 'y'), # this one needs to be tried first! (r'.*fortran 90 compiler name .*\s*:\n\(suggestions\s*: .*\)', f90_seq), (r'.*fortran 90 compiler interfaced with .*\s*:\n\(suggestions\s*: .*\)', f90_seq), (r'Please type the ABSOLUTE name of .*library.*, or ignore\s*[:]*\s*[\n]*.*', ''), (r'Please .* to save this draft configuration file :\n.*', '%s.x' % self.conf_file), ]) no_qa = [ ".*ignored.", ] env.setvar('GMKTMP', self.builddir) env.setvar('GMKFILE', self.conf_file) run_cmd_qa("gmkfilemaker", qa, std_qa=stdqa, no_qa=no_qa) # set environment variables for installation dirs env.setvar('ROOTPACK', os.path.join(self.installdir, 'rootpack')) env.setvar('ROOTBIN', os.path.join(self.installdir, 'rootpack')) env.setvar('HOMEPACK', os.path.join(self.installdir, 'pack')) env.setvar('HOMEBIN', os.path.join(self.installdir, 'pack')) # patch config file to include right Fortran compiler flags regex_subs = [(r"^(FRTFLAGS\s*=.*)$", r"\1 %s" % os.getenv('FFLAGS'))] apply_regex_substitutions(self.conf_filepath, regex_subs)
def install_step(self): """Custom install procedure for RepeatModeler.""" super(EB_RepeatModeler, self).install_step() # Required dependencies, and bin path relative to software root required_deps = { 'CD-HIT': 'bin', 'Kent_tools': 'bin', 'Perl': os.path.join('bin', 'perl'), 'RECON': 'bin', 'RepeatMasker': '', 'RepeatScout': '', 'TRF': os.path.join('bin', 'trf'), } # Search engines, and bin path relative to software root search_engines = { 'ABBlast': 'bin', 'RMBlast': 'bin', 'WUBlast': 'bin', } # Optional dependencies for LTR pipeline, and bin path relative to software root optional_LTR_deps = { 'GenomeTools': 'bin', 'LTR_retriever': '', 'MAFFT': 'bin', 'TWL-NINJA': 'bin', } for dep, path in required_deps.items(): required_deps[dep] = get_dep_path(dep, path, log=self.log, optional=False) for dep, path in search_engines.items(): search_engines[dep] = get_dep_path(dep, path, log=self.log, optional=True) for dep, path in optional_LTR_deps.items(): optional_LTR_deps[dep] = get_dep_path(dep, path, log=self.log, optional=True) # Check at least one search engine is present, and not both ABBlast/WUBlast if not any(search_engines.values()): raise EasyBuildError("At least one search engine must be specified: RMBlast, ABBlast, WUBlast") elif search_engines['ABBlast'] and search_engines['WUBlast']: raise EasyBuildError("Cannot specify both ABBlast and WUBlast") # Check if all LTR Pipeline dependencies present if all(optional_LTR_deps.values()): self.log.info("All LTR pipeline dependencies found, enabling LTR support") with_LTR = 'y' else: self.log.info("Not all LTR pipeline dependencies found, disabling LTR support") with_LTR = 'n' # Map search engine to configuration option search_engine_map = { 'ABBlast': '2', 'RMBlast': '1', 'WUBlast': '2', } # List of search engines to use (mapped) mapped_engines = [search_engine_map[k] for k, v in search_engines.items() if v] + ['3'] change_dir(self.installdir) # Fix perl shebang in configure script (#!/usr/local/bin/perl) orig_fix_perl_shebang_for = self.cfg['fix_perl_shebang_for'] self.cfg['fix_perl_shebang_for'] = [os.path.join(self.installdir, 'configure')] self.fix_shebang() self.cfg['fix_perl_shebang_for'] = orig_fix_perl_shebang_for patch_perl_script_autoflush('configure') qa = { '<PRESS ENTER TO CONTINUE>': '', } std_qa = { r'\*\*PERL INSTALLATION PATH\*\*\n\n[^*]*\n+Enter path.*:\s*': required_deps['Perl'], r'UCSCTOOLS_DIR.*:\s*': required_deps['Kent_tools'], r'LTR_RETRIEVER_DIR.*:\s*': optional_LTR_deps['LTR_retriever'], r'RMBLAST_DIR.*:\s*': search_engines['RMBlast'], r'ABBLAST_DIR.*:\s*': search_engines['ABBlast'] or search_engines['WUBlast'], # Configure first engine r'.*(\[ Un\-configured \]\n.*){2}\n.*\n+Enter Selection\:\s*': mapped_engines[0], # Configure second engine if multiple specified, otherwise skip r'.*(\[ Un\-configured \]\n.*\[ Configured \]|\[ Configured \]\n.*\[ Un-configured \])' r'\n\n.*\n+Enter Selection\:\s*': mapped_engines[1], # All engines configured r'.*(\[ Configured \]\n.*){2}\n.*\n+Enter Selection\:\s*': '3', # LTR r'LTR.*\[optional](.*\n)*of analysis \[y] or n\?\:\s*': with_LTR, } cmdopts = ' ' + ' '.join([ '-trf_prgm "%(TRF)s"', '-repeatmasker_dir "%(RepeatMasker)s"', '-rscout_dir "%(RepeatScout)s"', '-recon_dir "%(RECON)s"', '-ucsctools_dir "%(Kent_tools)s"', '-cdhit_dir "%(CD-HIT)s"', ]) % required_deps if with_LTR: cmdopts += ' ' + ' '.join([ '-mafft_dir "%(MAFFT)s"', '-genometools_dir "%(GenomeTools)s"', '-ltr_retriever_dir "%(LTR_retriever)s"', '-ninja_dir "%(TWL-NINJA)s"', ]) % optional_LTR_deps cmd = "perl ./configure" + cmdopts run_cmd_qa(cmd, qa, std_qa=std_qa, log_all=True, simple=True, log_ok=True, maxhits=100)
class EB_ALADIN(EasyBlock): """Support for building/installing ALADIN.""" def __init__(self, *args, **kwargs): """Initialisation of custom class variables for ALADIN.""" super(EB_ALADIN, self).__init__(*args, **kwargs) self.conf_file = None self.conf_filepath = None self.rootpack_dir = 'UNKNOWN' self.orig_library_path = None @staticmethod def extra_options(): """Custom easyconfig parameters for ALADIN.""" extra_vars = { 'optional_extra_param': ['default value', "short description", CUSTOM], } return EasyBlock.extra_options(extra_vars) def configure_step(self): """Custom configuration procedure for ALADIN.""" # unset $LIBRARY_PATH set by modules of dependencies, because it may screw up linking if 'LIBRARY_PATH' in os.environ: self.log.debug("Unsetting $LIBRARY_PATH (was: %s)" % os.environ['LIBRARY_PATH']) self.orig_library_path = os.environ.pop('LIBRARY_PATH') # build auxiliary libraries auxlibs_dir = None my_gnu = None if self.toolchain.comp_family() == toolchain.GCC: my_gnu = 'y' # gfortran for var in ['CFLAGS', 'CXXFLAGS', 'F90FLAGS', 'FFLAGS']: flags = os.getenv(var) env.setvar(var, "%s -fdefault-real-8 -fdefault-double-8" % flags) self.log.info("Updated %s to '%s'" % (var, os.getenv(var))) elif self.toolchain.comp_family() == toolchain.INTELCOMP: my_gnu = 'i' # icc/ifort else: raise EasyBuildError( "Don't know how to set 'my_gnu' variable in auxlibs build script." ) self.log.info("my_gnu set to '%s'" % my_gnu) tmp_installroot = tempfile.mkdtemp(prefix='aladin_auxlibs_') try: cwd = os.getcwd() os.chdir(self.builddir) builddirs = os.listdir(self.builddir) auxlibs_dir = [ x for x in builddirs if x.startswith('auxlibs_installer') ][0] os.chdir(auxlibs_dir) auto_driver = 'driver_automatic' for line in fileinput.input(auto_driver, inplace=1, backup='.orig.eb'): line = re.sub(r"^(my_gnu\s*=\s*).*$", r"\1%s" % my_gnu, line) line = re.sub(r"^(my_r32\s*=\s*).*$", r"\1n", line) # always 64-bit real precision line = re.sub(r"^(my_readonly\s*=\s*).*$", r"\1y", line) # make libs read-only after build line = re.sub(r"^(my_installroot\s*=\s*).*$", r"\1%s" % tmp_installroot, line) sys.stdout.write(line) run_cmd("./%s" % auto_driver) os.chdir(cwd) except OSError, err: raise EasyBuildError("Failed to build ALADIN: %s", err) # build gmkpack, update PATH and set GMKROOT # we build gmkpack here because a config file is generated in the gmkpack isntall path try: gmkpack_dir = [x for x in builddirs if x.startswith('gmkpack')][0] os.chdir(os.path.join(self.builddir, gmkpack_dir)) qa = { 'Do you want to run the configuration file maker assistant now (y) or later [n] ?': 'n', } run_cmd_qa("./build_gmkpack", qa) os.chdir(cwd) paths = os.getenv('PATH').split(':') paths.append(os.path.join(self.builddir, gmkpack_dir, 'util')) env.setvar('PATH', ':'.join(paths)) env.setvar('GMKROOT', os.path.join(self.builddir, gmkpack_dir)) except OSError, err: raise EasyBuildError("Failed to build gmkpack: %s", err)
def configure_step(self): """Configure build: - set some magic environment variables - run configure script - adjust configure.wrf file if needed """ wrfdir = os.path.join(self.builddir, self.wrfsubdir) # define $NETCDF* for netCDF dependency (used when creating WRF module file) set_netcdf_env_vars(self.log) # HDF5 (optional) dependency hdf5 = get_software_root('HDF5') if hdf5: env.setvar('HDF5', hdf5) # check if this is parallel HDF5 phdf5_bins = ['h5pcc', 'ph5diff'] parallel_hdf5 = True for f in phdf5_bins: if not os.path.exists(os.path.join(hdf5, 'bin', f)): parallel_hdf5 = False break if parallel_hdf5: env.setvar('PHDF5', hdf5) else: self.log.info( "Parallel HDF5 module not loaded, assuming that's OK...") else: self.log.info("HDF5 module not loaded, assuming that's OK...") # Parallel netCDF (optional) dependency pnetcdf = get_software_root('PnetCDF') if pnetcdf: env.setvar('PNETCDF', pnetcdf) # JasPer dependency check + setting env vars jasper = get_software_root('JasPer') if jasper: jasperlibdir = os.path.join(jasper, "lib") env.setvar('JASPERINC', os.path.join(jasper, "include")) env.setvar('JASPERLIB', jasperlibdir) else: if os.getenv('JASPERINC') or os.getenv('JASPERLIB'): raise EasyBuildError( "JasPer module not loaded, but JASPERINC and/or JASPERLIB still set?" ) else: self.log.info( "JasPer module not loaded, assuming that's OK...") # enable support for large file support in netCDF env.setvar('WRFIO_NCD_LARGE_FILE_SUPPORT', '1') # patch arch/Config_new.pl script, so that run_cmd_qa receives all output to answer questions if LooseVersion(self.version) < LooseVersion('4.0'): patch_perl_script_autoflush( os.path.join(wrfdir, "arch", "Config_new.pl")) # determine build type option to look for build_type_option = None self.comp_fam = self.toolchain.comp_family() if self.comp_fam == toolchain.INTELCOMP: # @UndefinedVariable if LooseVersion(self.version) >= LooseVersion('3.7'): build_type_option = "INTEL\ \(ifort\/icc\)" else: build_type_option = "Linux x86_64 i486 i586 i686, ifort compiler with icc" elif self.comp_fam == toolchain.GCC: # @UndefinedVariable if LooseVersion(self.version) >= LooseVersion('3.7'): build_type_option = "GNU\ \(gfortran\/gcc\)" else: build_type_option = "x86_64 Linux, gfortran compiler with gcc" else: raise EasyBuildError( "Don't know how to figure out build type to select.") # fetch selected build type (and make sure it makes sense) known_build_types = ['serial', 'smpar', 'dmpar', 'dm+sm'] self.parallel_build_types = ["dmpar", "dm+sm"] bt = self.cfg['buildtype'] if bt not in known_build_types: raise EasyBuildError( "Unknown build type: '%s'. Supported build types: %s", bt, known_build_types) # Escape the "+" in "dm+sm" since it's being used in a regexp below. bt = bt.replace('+', r'\+') # fetch option number based on build type option and selected build type if LooseVersion(self.version) >= LooseVersion('3.7'): # the two relevant lines in the configure output for WRF 3.8 are: # 13. (serial) 14. (smpar) 15. (dmpar) 16. (dm+sm) INTEL (ifort/icc) # 32. (serial) 33. (smpar) 34. (dmpar) 35. (dm+sm) GNU (gfortran/gcc) build_type_question = "\s*(?P<nr>[0-9]+)\.\ \(%s\).*%s" % ( bt, build_type_option) else: # the relevant lines in the configure output for WRF 3.6 are: # 13. Linux x86_64 i486 i586 i686, ifort compiler with icc (serial) # 14. Linux x86_64 i486 i586 i686, ifort compiler with icc (smpar) # 15. Linux x86_64 i486 i586 i686, ifort compiler with icc (dmpar) # 16. Linux x86_64 i486 i586 i686, ifort compiler with icc (dm+sm) # 32. x86_64 Linux, gfortran compiler with gcc (serial) # 33. x86_64 Linux, gfortran compiler with gcc (smpar) # 34. x86_64 Linux, gfortran compiler with gcc (dmpar) # 35. x86_64 Linux, gfortran compiler with gcc (dm+sm) build_type_question = "\s*(?P<nr>[0-9]+).\s*%s\s*\(%s\)" % ( build_type_option, bt) # run configure script cmd = "./configure" qa = { # named group in match will be used to construct answer "Compile for nesting? (1=basic, 2=preset moves, 3=vortex following) [default 1]:": "1", "Compile for nesting? (0=no nesting, 1=basic, 2=preset moves, 3=vortex following) [default 0]:": "0" } no_qa = [ "testing for fseeko and fseeko64", r"If you wish to change the default options, edit the file:[\s\n]*arch/configure_new.defaults" ] std_qa = { # named group in match will be used to construct answer r"%s.*\n(.*\n)*Enter selection\s*\[[0-9]+-[0-9]+\]\s*:" % build_type_question: "%(nr)s", } run_cmd_qa(cmd, qa, no_qa=no_qa, std_qa=std_qa, log_all=True, simple=True) cfgfile = 'configure.wrf' # make sure correct compilers are being used comps = { 'SCC': os.getenv('CC'), 'SFC': os.getenv('F90'), 'CCOMP': os.getenv('CC'), 'DM_FC': os.getenv('MPIF90'), 'DM_CC': "%s -DMPI2_SUPPORT" % os.getenv('MPICC'), } regex_subs = [(r"^(%s\s*=\s*).*$" % k, r"\1 %s" % v) for (k, v) in comps.items()] apply_regex_substitutions(cfgfile, regex_subs) # rewrite optimization options if desired if self.cfg['rewriteopts']: # replace default -O3 option in configure.wrf with CFLAGS/FFLAGS from environment self.log.info("Rewriting optimization options in %s" % cfgfile) # set extra flags for Intel compilers # see http://software.intel.com/en-us/forums/showthread.php?t=72109&p=1#146748 if self.comp_fam == toolchain.INTELCOMP: # @UndefinedVariable # -O3 -heap-arrays is required to resolve compilation error for envvar in ['CFLAGS', 'FFLAGS']: val = os.getenv(envvar) if '-O3' in val: env.setvar(envvar, '%s -heap-arrays' % val) self.log.info("Updated %s to '%s'" % (envvar, os.getenv(envvar))) # replace -O3 with desired optimization options regex_subs = [ (r"^(FCOPTIM.*)(\s-O3)(\s.*)$", r"\1 %s \3" % os.getenv('FFLAGS')), (r"^(CFLAGS_LOCAL.*)(\s-O3)(\s.*)$", r"\1 %s \3" % os.getenv('CFLAGS')), ] apply_regex_substitutions(cfgfile, regex_subs)
(r'.*fortran 90 compiler interfaced with .*\s*:\n\(suggestions\s*: .*\)', f90_seq), (r'Please type the ABSOLUTE name of .*library.*, or ignore\s*[:]*\s*[\n]*.*', ''), (r'Please .* to save this draft configuration file :\n.*', '%s.x' % self.conf_file), ]) no_qa = [ ".*ignored.", ] env.setvar('GMKTMP', self.builddir) env.setvar('GMKFILE', self.conf_file) run_cmd_qa("gmkfilemaker", qa, std_qa=stdqa, no_qa=no_qa) # set environment variables for installation dirs env.setvar('ROOTPACK', os.path.join(self.installdir, 'rootpack')) env.setvar('ROOTBIN', os.path.join(self.installdir, 'rootpack')) env.setvar('HOMEPACK', os.path.join(self.installdir, 'pack')) env.setvar('HOMEBIN', os.path.join(self.installdir, 'pack')) # patch config file to include right Fortran compiler flags regex_subs = [(r"^(FRTFLAGS\s*=.*)$", r"\1 %s" % os.getenv('FFLAGS'))] apply_regex_substitutions(self.conf_filepath, regex_subs) def build_step(self): """No separate build procedure for ALADIN (see install_step).""" pass
def install_step(self): """Interactive install of Maple.""" installers = glob.glob(os.path.join(self.builddir, 'Maple*Installer*')) if installers: if len(installers) == 1: cmd = installers[0] else: raise EasyBuildError("Found multiple installers: %s", ', '.join(installers)) else: raise EasyBuildError("Could not locate installer in %s", self.builddir) qa = { 'PRESS <ENTER> TO CONTINUE:': '', "Press [Enter] to continue:": '', 'DO YOU ACCEPT THE TERMS OF THIS LICENSE AGREEMENT? (Y/N):': 'Y', "Do you accept this license? [y/n]:": 'y', 'ENTER AN ABSOLUTE PATH, OR PRESS <ENTER> TO ACCEPT THE DEFAULT :': self.installdir, 'IS THIS CORRECT? (Y/N):': 'Y', 'Do you wish to have a shortcut installed on your desktop? ->1- Yes 2- No ENTER THE NUMBER ' + 'FOR YOUR CHOICE, OR PRESS <ENTER> TO ACCEPT THE DEFAULT::': '2', "Do you wish to have a shortcut installed on your desktop? [Y/n]:": 'n', '->1- Single User License 2- Network License ENTER THE NUMBER FOR YOUR CHOICE, ' + 'OR PRESS <ENTER> TO ACCEPT THE DEFAULT::': '2', 'PRESS <ENTER> TO EXIT THE INSTALLER:': '', 'License server (DEFAULT: ):': self.cfg['license_server'], "License server []:": self.cfg['license_server'], 'Port number (optional) (DEFAULT: ):': '', '->1- Configure toolbox for Matlab 2- Do not configure at this time ENTER THE NUMBER FOR YOUR CHOICE, ' + 'OR PRESS <ENTER> TO ACCEPT THE DEFAULT::': '2', "MATLAB Configuration [y/N]:": 'n', "Check for updates now [Y/n]:": 'n', "Use proxy server when checking for updates [y/N]:": 'n', "Downloads & Service Packs. [Y/n]:": 'n', } std_qa = { "Choose Install Folder \[.*\]:": self.installdir, "\[2\] Network License.*\nPlease choose an option \[.\] :": '2', "\[1\] Single Server.*\n.*\nPlease choose an option \[.\] :": '1', "Port number \[[0-9]+\]:": '', "Enable periodic checking for Maple .* updates after installation \[Y/n\]:": 'n', } no_qa = [ 'Graphical installers are not supported by the VM. The console mode will be used instead...', 'Extracting the JRE from the installer archive...', 'Launching installer...', "Configuring the installer for this system's environment...", 'Unpacking the JRE...', '\[[-|]*', ] run_cmd_qa(cmd, qa, std_qa=std_qa, no_qa=no_qa, log_all=True, simple=True) upgrade_installers = glob.glob( os.path.join(self.builddir, 'Maple*Upgrade*')) if upgrade_installers: if len(upgrade_installers) == 1: cmd = upgrade_installers[0] qa = { "Press [Enter] to continue:": '', "Do you accept this license? [y/n]:": 'y', } std_qa = { "Please specify the path to your existing Maple .* Installation.\s*\n\s*\[.*\]:": self.installdir, } run_cmd_qa(cmd, qa, std_qa=std_qa, log_all=True, simple=True) else: raise EasyBuildError("Found multiple upgrade installers: %s", ', '.join(upgrade_installers)) else: self.log.info("No upgrade installers found in %s", self.builddir)
def configure_step(self): """ Configure Geant4 build, either via CMake for versions more recent than 9.4, or using an interactive configuration procedure otherwise. """ # Geant4 switched to a CMake build system in version 9.4 if LooseVersion(self.version) >= LooseVersion("9.4"): mkdir('configdir') os.chdir('configdir') super(EB_Geant4, self).configure_step(srcdir="..") else: pwd = self.cfg['start_dir'] dst = self.installdir clhepdir = get_software_root('CLHEP') cmd = "%s/Configure -E -build" % pwd self.qanda = { # questions and answers for version 9.1.p03 "There exists a config.sh file. Shall I use it to set the defaults? [y]": "n", "Would you like to see the instructions? [n]": "", "[Type carriage return to continue]": "", "Definition of G4SYSTEM variable is Linux-g++. That stands for: 1) OS : Linux" \ "2) Compiler : g++ To modify default settings, select number above (e.g. 2) " \ "[Press [Enter] for default settings]": "2", "Which C++ compiler? [g++]": "$(GPP)", "Confirm your selection or set recommended 'g++'! [*]": "", "Definition of G4SYSTEM variable is Linux-icc. That stands for: 1) OS : Linux 2)" \ "Compiler : icc To modify default settings, select number above (e.g. 2) " \ "[Press [Enter] for default settings]": "", "Do you expect to run these scripts and binaries on multiple machines? [n]": "y", "Where is Geant4 source installed? [%s]" % pwd: "", "Specify the path where Geant4 libraries and source files should be installed." \ " [%s]" % pwd: dst, "Do you want to copy all Geant4 headers in one directory? [n]": "y", "Please, specify default directory where ALL the Geant4 data is installed:" \ "G4LEVELGAMMADATA: %(pwd)s/data/PhotonEvaporation2.0 G4RADIOACTIVEDATA: " \ "%(pwd)s/data/RadioactiveDecay3.2 G4LEDATA: %(pwd)s/data/G4EMLOW5.1 G4NEUTRONHPDATA: " \ "%(pwd)s/data/G4NDL3.12 G4ABLADATA: %(pwd)s/data/G4ABLA3.0 You will be asked about " \ "customizing these next. [%(pwd)s/data]" % {'pwd': pwd}: "%s/data" % dst, "Directory %s/data doesn't exist. Use that name anyway? [n]" % dst: "y", "Please, specify default directory where the Geant4 data is installed: " \ "1) G4LEVELGAMMADATA: %(dst)s/data/PhotonEvaporation2.0 2) G4RADIOACTIVEDATA: " \ "%(dst)s/data/RadioactiveDecay3.2 3) G4LEDATA: %(dst)s/data/G4EMLOW5.1 4) G4NEUTRONHPDATA: " \ "%(dst)s/data/G4NDL3.12 5) G4ABLADATA: %(dst)s/data/G4ABLA3.0 To modify default settings, " \ "select number above (e.g. 2) [Press [Enter] for default settings]" % {'dst': dst}: "", "Please, specify where CLHEP is installed: CLHEP_BASE_DIR: ": clhepdir, "Please, specify where CLHEP is installed: CLHEP_BASE_DIR: [%s]" % clhepdir: "", "You can customize paths and library name of you CLHEP installation: 1) CLHEP_INCLUDE_DIR: " \ "%(clhepdir)s/include 2) CLHEP_LIB_DIR: %(clhepdir)s/lib 3) CLHEP_LIB: CLHEP To modify " \ "default settings, select number above (e.g. 2) [Press [Enter] for default settings]" % {'clhepdir': clhepdir}: "", "By default 'static' (.a) libraries are built. Do you want to build 'shared' (.so) " \ "libraries? [n]": "y", "You selected to build 'shared' (.so) libraries. Do you want to build 'static' (.a) " \ "libraries too? [n]": "y", "Do you want to build 'global' compound libraries? [n]": "", "Do you want to compile libraries in DEBUG mode (-g)? [n]": "", "G4UI_NONE If this variable is set, no UI sessions nor any UI libraries are built. " \ "This can be useful when running a pure batch job or in a user framework having its own " \ "UI system. Do you want to set this variable ? [n]": "", "G4UI_BUILD_XAW_SESSION G4UI_USE_XAW Specifies to include and use the XAW interfaces in " \ "the application to be built. The XAW (X11 Athena Widget set) extensions are required to " \ "activate and build this driver. [n]": "", "G4UI_BUILD_XM_SESSION G4UI_USE_XM Specifies to include and use the XM Motif based user " \ "interfaces. The XM Motif extensions are required to activate and build this driver. [n]": "", "G4VIS_NONE If this variable is set, no visualization drivers will be built or used. Do " \ "you want to set this variable ? [n]": "n", "G4VIS_BUILD_OPENGLX_DRIVER G4VIS_USE_OPENGLX It is an interface to the de facto standard " \ "3D graphics library, OpenGL. It is well suited for real-time fast visualization and " \ "prototyping. The X11 version of the OpenGL libraries is required. [n]": "", "G4VIS_BUILD_OPENGLXM_DRIVER G4VIS_USE_OPENGLXM It is an interface to the de facto " \ "standard 3D graphics library, OpenGL. It is well suited for real-time fast visualization " \ "and prototyping. The X11 version of the OpenGL libraries and the Motif Xm extension is " \ "required. [n]": "", "G4VIS_BUILD_DAWN_DRIVER G4VIS_USE_DAWN DAWN drivers are interfaces to the Fukui Renderer " \ "DAWN. DAWN is a vectorized 3D PostScript processor suited to prepare technical high " \ "quality outputs for presentation and/or documentation. [n]": "", "G4VIS_BUILD_OIX_DRIVER G4VIS_USE_OIX The OpenInventor driver is based on OpenInventor tech" \ "nology for scientific visualization. The X11 version of OpenInventor is required. [n]": "", "G4VIS_BUILD_RAYTRACERX_DRIVER G4VIS_USE_RAYTRACERX Allows for interactive ray-tracing " \ "graphics through X11. The X11 package is required. [n]": "", "G4VIS_BUILD_VRML_DRIVER G4VIS_USE_VRML These driver generate VRML files, which describe " \ "3D scenes to be visualized with a proper VRML viewer. [n]": "", "G4LIB_BUILD_GDML Setting this variable will enable building of the GDML plugin module " \ "embedded in Geant4 for detector description persistency. It requires your system to have " \ "the XercesC library and headers installed. Do you want to set this variable? [n]": "", "G4LIB_BUILD_G3TOG4 The utility module 'g3tog4' will be built by setting this variable. " \ "NOTE: it requires a valid FORTRAN compiler to be installed on your system and the " \ "'cernlib' command in the path, in order to build the ancillary tools! Do you want to " \ "build 'g3tog4' ? [n]": "", "G4LIB_BUILD_ZLIB Do you want to activate compression for output files generated by the " \ "HepRep visualization driver? [n]": "y", "G4ANALYSIS_USE Activates the configuration setup for allowing plugins to analysis tools " \ "based on AIDA (Astract Interfaces for Data Analysis). In order to use AIDA features and " \ "compliant analysis tools, the proper environment for these tools will have to be set " \ "(see documentation for the specific analysis tools). [n]": "", "Press [Enter] to start installation or use a shell escape to edit config.sh: ": "", # extra questions and answers for version 9.2.p03 "Directory %s doesn't exist. Use that name anyway? [n]" % dst: "y", "Specify the path where the Geant4 data libraries PhotonEvaporation%s " \ "RadioactiveDecay%s G4EMLOW%s G4NDL%s G4ABLA%s are " \ "installed. For now, a flat directory structure is assumed, and this can be customized " \ "at the next step if needed. [%s/data]" % (self.cfg['PhotonEvaporationVersion'], self.cfg['G4RadioactiveDecayVersion'], self.cfg['G4EMLOWVersion'], self.cfg['G4NDLVersion'], self.cfg['G4ABLAVersion'], pwd ): "%s/data" % dst, "Please enter 1) Another path to search in 2) 'f' to force the use of the path " \ "you entered previously (the data libraries are not needed to build Geant4, but " \ "are needed to run applications later). 3) 'c' to customize the data paths, e.g. " \ "if you have the data libraries installed in different locations. [f]": "", "G4UI_BUILD_QT_SESSION G4UI_USE_QT Setting these variables will enable the building " \ "of the G4 Qt based user interface module and the use of this module in your " \ "applications respectively. The Qt3 or Qt4 headers, libraries and moc application are " \ "required to enable the building of this module. Do you want to enable build and use of " \ "this module? [n]": "", # extra questions and answers for version 9.4.po1 "What is the path to the Geant4 source tree? [%s]" % pwd: "", "Where should Geant4 be installed? [%s]" % pwd: dst, "Do you want to install all Geant4 headers in one directory? [n]": "y", "Do you want to build shared libraries? [y]": "", "Do you want to build static libraries too? [n]": "", "Do you want to build global libraries? [y]": "", "Do you want to build granular libraries as well? [n]": "", "Do you want to build libraries with debugging information? [n]": "", "Specify the path where the Geant4 data libraries are installed: [%s/data]" % pwd: "%s/data" % dst, "How many parallel jobs should make launch? [1]": "%s" % self.cfg['parallel'], "Please enter 1) Another path to search in 2) 'f' to force the use of the path you entered " \ "previously (the data libraries are NOT needed to build Geant4, but are needed to run " \ "applications later). 3) 'c' to customize the data paths, e.g. if you have the data " \ "libraries installed in different locations. [f]": "", "Enable building of User Interface (UI) modules? [y]": "", "Enable building of the XAW (X11 Athena Widget set) UI module? [n]": "", "Enable building of the X11-Motif (Xm) UI module? [n]": "", "Enable building of the Qt UI module? [n]": "", "Enable building of visualization drivers? [y]": "n", "Enable the Geometry Description Markup Language (GDML) module? [n]": "", "Enable build of the g3tog4 utility module? [n]": "", "Enable internal zlib compression for HepRep visualization? [n] ": "", } self.noqanda = [ r"Compiling\s+.*?\s+\.\.\.", r"Making\s+dependency\s+for\s+file\s+.*?\s+\.\.\.", r"Making\s+libname\.map\s+starter\s+file\s+\.\.\.", r"Making\s+libname\.map\s+\.\.\.", r"Reading\s+library\s+get_name\s+map\s+file\s*\.\.\.", r"Reading\s+dependency\s+files\s*\.\.\.", r"Creating\s+shared\s+library\s+.*?\s+\.\.\.", ] run_cmd_qa(cmd, self.qanda, self.noqanda, log_all=True, simple=True) # determining self.g4system try: scriptdirbase = os.path.join(pwd, '.config', 'bin') filelist = os.listdir(scriptdirbase) except OSError, err: raise EasyBuildError("Failed to determine self.g4system: %s", err) if len(filelist) != 1: raise EasyBuildError( "Exactly one directory is expected in %s; found back: %s", scriptdirbase, filelist) else: self.g4system = filelist[0] self.scriptdir = os.path.join(scriptdirbase, self.g4system) if not os.path.isdir(self.scriptdir): raise EasyBuildError( "Something went wrong. Dir: %s doesn't exist.", self.scriptdir) self.log.info( "The directory containing several important scripts to be copied was found: %s" % self.scriptdir) # copying config.sh to pwd try: self.log.info("copying config.sh to %s" % pwd) shutil.copy2(os.path.join(self.scriptdir, 'config.sh'), pwd) except IOError, err: raise EasyBuildError("Failed to copy config.sh to %s", pwd)
def install_step(self): """Custom install procedure for RepeatMasker.""" super(EB_RepeatMasker, self).install_step() # check for required dependencies perl_root = get_software_root('Perl') if perl_root: perl = os.path.join(perl_root, 'bin', 'perl') else: raise EasyBuildError("Missing required dependency: Perl") trf_root = get_software_root('TRF') if trf_root: trf = os.path.join(trf_root, 'trf') else: raise EasyBuildError("Missing required dependency: TRF") # determine which search engine to use # see also http://www.repeatmasker.org/RMDownload.html cand_search_engines = ['CrossMatch', 'RMBlast', 'WUBlast', 'HMMER'] search_engine = None for dep in cand_search_engines: if get_software_root(dep): if search_engine is None: search_engine = dep else: raise EasyBuildError( "Found multiple candidate search engines: %s and %s", search_engine, dep) if search_engine is None: raise EasyBuildError( "No search engine found, one of these must be included as dependency: %s", ' '.join(cand_search_engines)) change_dir(self.installdir) patch_perl_script_autoflush('configure') search_engine_map = { 'CrossMatch': '1', 'RMBlast': '2', 'WUBlast': '3', 'HMMER': '4', } search_engine_bindir = os.path.join(get_software_root(search_engine), 'bin') cmd = "perl ./configure" qa = { '<PRESS ENTER TO CONTINUE>': '', # select search engine 'Enter Selection:': search_engine_map[search_engine], } std_qa = { r'\*\*PERL PROGRAM\*\*\n([^*]*\n)+Enter path.*': perl, r'\*\*REPEATMASKER INSTALLATION DIRECTORY\*\*\n([^*]*\n)+Enter path.*': self.installdir, r'\*\*TRF PROGRAM\*\*\n([^*]*\n)+Enter path.*': trf, # search engine installation path (location of /bin subdirectory) # also enter 'Y' to confirm + '5' ("Done") to complete selection process for search engine r'\*\*.* INSTALLATION PATH\*\*\n([^*]*\n)+Enter path.*': search_engine_bindir + '\nY\n5', } run_cmd_qa(cmd, qa, std_qa=std_qa, log_all=True, simple=True, log_ok=True)
# fetch option number based on build type option and selected build type build_type_question = "\s*(?P<nr>[0-9]+).\s*%s\s*\(?%s\)?\s*\n" % ( build_type_option, knownbuildtypes[bt]) cmd = "./configure" qa = {} no_qa = [".*compiler is.*"] std_qa = { # named group in match will be used to construct answer r"%s(.*\n)*Enter selection\s*\[[0-9]+-[0-9]+\]\s*:" % build_type_question: "%(nr)s", } run_cmd_qa(cmd, qa, no_qa=no_qa, std_qa=std_qa, log_all=True, simple=True) # make sure correct compilers and compiler flags are being used comps = { 'SCC': "%s -I$(JASPERINC) %s" % (os.getenv('CC'), libpnginc), 'SFC': os.getenv('F90'), 'DM_FC': os.getenv('MPIF90'), 'DM_CC': os.getenv('MPICC'), 'FC': os.getenv('MPIF90'), 'CC': os.getenv('MPICC'), } fn = 'configure.wps' for line in fileinput.input(fn, inplace=1, backup='.orig.comps'): for (k, v) in comps.items():
def configure_step(self): """Configure WIEN2k build by patching siteconfig_lapw script and running it.""" self.cfgscript = "siteconfig_lapw" # patch config file first # toolchain-dependent values comp_answer = None if self.toolchain.comp_family( ) == toolchain.INTELCOMP: # @UndefinedVariable if LooseVersion( get_software_version("icc")) >= LooseVersion("2011"): if LooseVersion(self.version) < LooseVersion("17"): comp_answer = 'I' # Linux (Intel ifort 12.0 compiler + mkl ) else: comp_answer = 'LI' # Linux (Intel ifort compiler (12.0 or later)+mkl+intelmpi)) else: comp_answer = "K1" # Linux (Intel ifort 11.1 compiler + mkl ) elif self.toolchain.comp_family( ) == toolchain.GCC: # @UndefinedVariable if LooseVersion(self.version) < LooseVersion("17"): comp_answer = 'V' # Linux (gfortran compiler + gotolib) else: comp_answer = 'LG' # Linux (gfortran compiler + OpenBlas) else: raise EasyBuildError( "Failed to determine toolchain-dependent answers.") # libraries liblapack = os.getenv('LIBLAPACK_MT').replace('static', 'dynamic') libscalapack = os.getenv('LIBSCALAPACK_MT').replace( 'static', 'dynamic') rlibs = "%s %s" % (liblapack, self.toolchain.get_flag('openmp')) rplibs = [libscalapack, liblapack] fftwver = get_software_version('FFTW') if fftwver: suff = '' if LooseVersion(fftwver) >= LooseVersion("3"): suff = '3' rplibs.insert(0, "-lfftw%(suff)s_mpi -lfftw%(suff)s" % {'suff': suff}) else: rplibs.append(os.getenv('LIBFFT')) rplibs = ' '.join(rplibs) vars = { 'FC': '%s' % os.getenv('F90'), 'FOPT': '%s' % os.getenv('FFLAGS'), 'MPF': '%s' % os.getenv('MPIF90'), 'FPOPT': '%s' % os.getenv('FFLAGS'), 'CC': os.getenv('CC'), 'LDFLAGS': '$(FOPT) %s ' % os.getenv('LDFLAGS'), 'R_LIBS': rlibs, # libraries for 'real' (not 'complex') binary 'RP_LIBS': rplibs, # libraries for 'real' parallel binary 'MPIRUN': '', } for line in fileinput.input(self.cfgscript, inplace=1, backup='.orig'): # set config parameters for (key, val) in vars.items(): regexp = re.compile('^([a-z0-9]+):%s:(.*)' % key) res = regexp.search(line) if res: # we need to exclude the lines with 'current', otherwise we break the script if not res.group(1) == "current": if 'OPT' in key: # append instead of replace line = regexp.sub( '\\1:%s:%s %s' % (key, res.group(2), val), line) else: line = regexp.sub('\\1:%s:%s' % (key, val), line) # avoid exit code > 0 at end of configuration line = re.sub('(\s+)exit 1', '\\1exit 0', line) sys.stdout.write(line) # set correct compilers env.setvar('bin', os.getcwd()) dc = { 'COMPILERC': os.getenv('CC'), 'COMPILER': os.getenv('F90'), 'COMPILERP': os.getenv('MPIF90'), } if LooseVersion(self.version) < LooseVersion("17"): for (key, val) in dc.items(): write_file(key, val) else: dc['cc'] = dc.pop('COMPILERC') dc['fortran'] = dc.pop('COMPILER') dc['parallel'] = dc.pop('COMPILERP') write_file('WIEN2k_COMPILER', '\n'.join(['%s:%s' % (k, v) for k, v in dc.items()])) # configure with patched configure script self.log.debug('%s part I (configure)' % self.cfgscript) cmd = "./%s" % self.cfgscript qanda = { 'Press RETURN to continue': '', 'Your compiler:': '', 'Hit Enter to continue': '', 'Remote shell (default is ssh) =': '', 'Remote copy (default is scp) =': '', 'and you need to know details about your installed mpi ..) (y/n)': 'y', 'Q to quit Selection:': 'Q', 'A Compile all programs (suggested) Q Quit Selection:': 'Q', ' Please enter the full path of the perl program: ': '', 'continue or stop (c/s)': 'c', '(like taskset -c). Enter N / your_specific_command:': 'N', } if LooseVersion(self.version) >= LooseVersion("13"): fftw_root = get_software_root('FFTW') if fftw_root: fftw_maj = get_software_version('FFTW').split('.')[0] fftw_spec = 'FFTW%s' % fftw_maj else: raise EasyBuildError("Required FFTW dependency is missing") qanda.update({ ') Selection:': comp_answer, 'Shared Memory Architecture? (y/N):': 'N', 'Set MPI_REMOTE to 0 / 1:': '0', 'You need to KNOW details about your installed MPI and FFTW ) (y/n)': 'y', 'Do you want to use FFTW (recommended, but for sequential code not required)? (Y,n):': 'y', 'Please specify whether you want to use FFTW3 (default) or FFTW2 (FFTW3 / FFTW2):': fftw_spec, 'Please specify the ROOT-path of your FFTW installation (like /opt/fftw3):': fftw_root, 'is this correct? enter Y (default) or n:': 'Y', }) libxcroot = get_software_root('libxc') if LooseVersion(self.version) < LooseVersion("17"): libxcstr1 = ' before' libxcstr3 = '' elif LooseVersion(self.version) > LooseVersion("19"): libxcstr1 = ' - usually not needed' libxcstr3 = 'root-' else: libxcstr1 = '' libxcstr3 = '' libxcquestion1 = 'LIBXC (that you have installed%s)? (y,N):' % libxcstr1 libxcquestion2 = 'Do you want to automatically search for LIBXC installations? (Y,n):' libxcquestion3 = 'Please enter the %sdirectory of your LIBXC-installation!:' % libxcstr3 libxcquestion4 = 'Please enter the lib-directory of your LIBXC-installation (usually lib or lib64)!:' if libxcroot: qanda.update({ libxcquestion1: 'y', libxcquestion2: 'n', libxcquestion3: libxcroot, libxcquestion4: 'lib' }) else: qanda.update({libxcquestion: ''}) if LooseVersion(self.version) >= LooseVersion("17"): scalapack_libs = os.getenv('LIBSCALAPACK').split() scalapack = next( (lib[2:] for lib in scalapack_libs if 'scalapack' in lib), 'scalapack') blacs = next( (lib[2:] for lib in scalapack_libs if 'blacs' in lib), 'openblas') qanda.update({ 'You need to KNOW details about your installed MPI, ELPA, and FFTW ) (y/N)': 'y', 'Do you want to use a present ScaLAPACK installation? (Y,n):': 'y', 'Do you want to use the MKL version of ScaLAPACK? (Y,n):': 'n', # we set it ourselves below 'Do you use Intel MPI? (Y,n):': 'y', 'Is this correct? (Y,n):': 'y', 'Please specify the target architecture of your ScaLAPACK libraries (e.g. intel64)!:': '', 'ScaLAPACK root:': os.getenv('MKLROOT') or os.getenv('EBROOTSCALAPACK'), 'ScaLAPACK library:': scalapack, 'BLACS root:': os.getenv('MKLROOT') or os.getenv('EBROOTOPENBLAS'), 'BLACS library:': blacs, 'Please enter your choice of additional libraries!:': '', 'Do you want to use a present FFTW installation? (Y,n):': 'y', 'Please specify the path of your FFTW installation (like /opt/fftw3/) ' 'or accept present choice (enter):': fftw_root, 'Please specify the target achitecture of your FFTW library (e.g. lib64) ' 'or accept present choice (enter):': '', 'Do you want to automatically search for FFTW installations? (Y,n):': 'n', 'Please specify the ROOT-path of your FFTW installation (like /opt/fftw3/) ' 'or accept present choice (enter):': fftw_root, 'Is this correct? enter Y (default) or n:': 'Y', 'Please specify the name of your FFTW library or accept present choice (enter):': '', 'Please specify your parallel compiler options or accept the recommendations ' '(Enter - default)!:': '', 'Please specify your MPIRUN command or accept the recommendations (Enter - default)!:': '', # the temporary directory is hardcoded into execution scripts and must exist at runtime 'Please enter the full path to your temporary directory:': '/tmp', }) std_qa = {} elparoot = get_software_root('ELPA') if elparoot: apply_regex_substitutions( self.cfgscript, [(r'cat elpahelp2$', 'cat -n elpahelp2')]) elpa_dict = { 'root': elparoot, 'version': get_software_version('ELPA'), 'variant': 'elpa_openmp' if self.toolchain.get_flag('openmp') else 'elpa' } elpa_dir = "%(root)s/include/%(variant)s-%(version)s" % elpa_dict std_qa.update({ r".*(?P<number>[0-9]+)\t%s\n(.*\n)*" % elpa_dir: "%(number)s", }) qanda.update({ 'Do you want to use ELPA? (y,N):': 'y', 'Do you want to automatically search for ELPA installations? (Y,n):': 'n', 'Please specify the ROOT-path of your ELPA installation (like /usr/local/elpa/) ' 'or accept present path (Enter):': elparoot, 'Please specify the lib-directory of your ELPA installation (e.g. lib or lib64)!:': 'lib', 'Please specify the name of your installed ELPA library (e.g. elpa or elpa_openmp)!:': elpa_dict['variant'], }) else: qanda.update({'Do you want to use ELPA? (y,N):': 'n'}) else: qanda.update({ 'compiler) Selection:': comp_answer, 'Shared Memory Architecture? (y/n):': 'n', 'If you are using mpi2 set MPI_REMOTE to 0 Set MPI_REMOTE to 0 / 1:': '0', 'Do you have MPI and Scalapack installed and intend to run ' 'finegrained parallel? (This is usefull only for BIG cases ' '(50 atoms and more / unit cell) and you need to know details ' 'about your installed mpi and fftw ) (y/n)': 'y', }) no_qa = [ 'You have the following mkl libraries in %s :' % os.getenv('MKLROOT'), "%s[ \t]*.*" % os.getenv('MPIF90'), "%s[ \t]*.*" % os.getenv('F90'), "%s[ \t]*.*" % os.getenv('CC'), ".*SRC_.*", "Please enter the full path of the perl program:", ] std_qa.update({ r'S\s+Save and Quit[\s\n]+To change an item select option.[\s\n]+Selection:': 'S', 'Recommended setting for parallel f90 compiler: .* Current selection: Your compiler:': os.getenv('MPIF90'), r'process or you can change single items in "Compiling Options".[\s\n]+Selection:': 'S', r'A\s+Compile all programs (suggested)[\s\n]+Q\s*Quit[\s\n]+Selection:': 'Q', }) run_cmd_qa(cmd, qanda, no_qa=no_qa, std_qa=std_qa, log_all=True, simple=True) # post-configure patches parallel_options = {} parallel_options_fp = os.path.join(self.cfg['start_dir'], 'parallel_options') if self.cfg['wien_mpirun']: parallel_options.update({'WIEN_MPIRUN': self.cfg['wien_mpirun']}) if self.cfg['taskset'] is None: self.cfg['taskset'] = 'no' parallel_options.update({'TASKSET': self.cfg['taskset']}) for opt in ['use_remote', 'mpi_remote', 'wien_granularity']: parallel_options.update({opt.upper(): int(self.cfg[opt])}) write_file( parallel_options_fp, '\n'.join( ['setenv %s "%s"' % tup for tup in parallel_options.items()])) if self.cfg['remote']: if self.cfg['remote'] == 'pbsssh': extratxt = '\n'.join([ '', "set remote = pbsssh", "setenv PBSSSHENV 'LD_LIBRARY_PATH PATH'", '', ]) write_file(parallel_options_fp, extratxt, append=True) else: raise EasyBuildError("Don't know how to handle remote %s", self.cfg['remote']) self.log.debug("Patched file %s: %s", parallel_options_fp, read_file(parallel_options_fp))
def configure_step(self): """Configure build: - set required environment variables (for netCDF, JasPer) - patch compile script and ungrib Makefile for non-default install paths of WRF and JasPer - run configure script and figure how to select desired build option - patch configure.wps file afterwards to fix 'serial compiler' setting """ # netCDF dependency check + setting env vars (NETCDF, NETCDFF) set_netcdf_env_vars(self.log) # WRF dependency check wrf = get_software_root('WRF') if wrf: wrfdir = os.path.join(wrf, det_wrf_subdir(get_software_version('WRF'))) else: raise EasyBuildError("WRF module not loaded?") self.compile_script = 'compile' if LooseVersion(self.version) >= LooseVersion('4.0.3'): # specify install location of WRF via $WRF_DIR (supported since WPS 4.0.3) # see https://github.com/wrf-model/WPS/pull/102 env.setvar('WRF_DIR', wrfdir) else: # patch compile script so that WRF is found regex_subs = [(r"^(\s*set\s*WRF_DIR_PRE\s*=\s*)\${DEV_TOP}(.*)$", r"\1%s\2" % wrfdir)] apply_regex_substitutions(self.compile_script, regex_subs) # libpng dependency check libpng = get_software_root('libpng') zlib = get_software_root('zlib') if libpng: paths = [libpng] if zlib: paths.insert(0, zlib) libpnginc = ' '.join( ['-I%s' % os.path.join(path, 'include') for path in paths]) libpnglib = ' '.join( ['-L%s' % os.path.join(path, 'lib') for path in paths]) else: # define these as empty, assume that libpng will be available via OS (e.g. due to --filter-deps=libpng) libpnglib = "" libpnginc = "" # JasPer dependency check + setting env vars jasper = get_software_root('JasPer') if jasper: env.setvar('JASPERINC', os.path.join(jasper, "include")) jasperlibdir = os.path.join(jasper, "lib") env.setvar('JASPERLIB', jasperlibdir) jasperlib = "-L%s" % jasperlibdir else: raise EasyBuildError("JasPer module not loaded?") # patch ungrib Makefile so that JasPer is found jasperlibs = "%s -ljasper %s -lpng" % (jasperlib, libpnglib) regex_subs = [ (r"^(\s*-L\.\s*-l\$\(LIBTARGET\))(\s*;.*)$", r"\1 %s\2" % jasperlibs), (r"^(\s*\$\(COMPRESSION_LIBS\))(\s*;.*)$", r"\1 %s\2" % jasperlibs), ] apply_regex_substitutions(os.path.join('ungrib', 'src', 'Makefile'), regex_subs) # patch arch/Config.pl script, so that run_cmd_qa receives all output to answer questions patch_perl_script_autoflush(os.path.join("arch", "Config.pl")) # configure # determine build type option to look for self.comp_fam = self.toolchain.comp_family() build_type_option = None if LooseVersion(self.version) >= LooseVersion("3.4"): knownbuildtypes = {'smpar': 'serial', 'dmpar': 'dmpar'} if self.comp_fam == toolchain.INTELCOMP: # @UndefinedVariable build_type_option = " Linux x86_64, Intel compiler" elif self.comp_fam == toolchain.GCC: # @UndefinedVariable if LooseVersion(self.version) >= LooseVersion("3.6"): build_type_option = "Linux x86_64, gfortran" else: build_type_option = "Linux x86_64 g95" else: raise EasyBuildError( "Don't know how to figure out build type to select.") else: knownbuildtypes = {'smpar': 'serial', 'dmpar': 'DM parallel'} if self.comp_fam == toolchain.INTELCOMP: # @UndefinedVariable build_type_option = "PC Linux x86_64, Intel compiler" elif self.comp_fam == toolchain.GCC: # @UndefinedVariable build_type_option = "PC Linux x86_64, gfortran compiler," knownbuildtypes['dmpar'] = knownbuildtypes['dmpar'].upper() else: raise EasyBuildError( "Don't know how to figure out build type to select.") # check and fetch selected build type bt = self.cfg['buildtype'] if bt not in knownbuildtypes.keys(): raise EasyBuildError( "Unknown build type: '%s'. Supported build types: %s", bt, knownbuildtypes.keys()) # fetch option number based on build type option and selected build type build_type_question = r"\s*(?P<nr>[0-9]+).\s*%s\s*\(?%s\)?\s*\n" % ( build_type_option, knownbuildtypes[bt]) cmd = ' '.join( [self.cfg['preconfigopts'], './configure', self.cfg['configopts']]) qa = {} no_qa = [".*compiler is.*"] std_qa = { # named group in match will be used to construct answer r"%s(.*\n)*Enter selection\s*\[[0-9]+-[0-9]+\]\s*:" % build_type_question: "%(nr)s", } run_cmd_qa(cmd, qa, no_qa=no_qa, std_qa=std_qa, log_all=True, simple=True) # make sure correct compilers and compiler flags are being used comps = { 'SCC': "%s -I$(JASPERINC) %s" % (os.getenv('CC'), libpnginc), 'SFC': os.getenv('F90'), 'DM_FC': os.getenv('MPIF90'), 'DM_CC': os.getenv('MPICC'), 'FC': os.getenv('MPIF90'), 'CC': os.getenv('MPICC'), } if self.toolchain.options.get('openmp', None): comps.update({ 'LDFLAGS': '%s %s' % (self.toolchain.get_flag('openmp'), os.environ['LDFLAGS']) }) regex_subs = [(r"^(%s\s*=\s*).*$" % key, r"\1 %s" % val) for (key, val) in comps.items()] apply_regex_substitutions('configure.wps', regex_subs)
def configure_step(self): """Configure GAMESS-US build via provided interactive 'config' script.""" # machine type platform_name = get_platform_name() x86_64_linux_re = re.compile('^x86_64-.*$') if x86_64_linux_re.match(platform_name): machinetype = "linux64" else: raise EasyBuildError("Build target %s currently unsupported", platform_name) # compiler config comp_fam = self.toolchain.comp_family() fortran_comp, fortran_ver = None, None if comp_fam == toolchain.INTELCOMP: fortran_comp = 'ifort' (out, _) = run_cmd("ifort -v", simple=False) res = re.search(r"^ifort version ([0-9]+)\.[0-9.]+$", out) if res: fortran_ver = res.group(1) else: raise EasyBuildError( "Failed to determine ifort major version number") elif comp_fam == toolchain.GCC: fortran_comp = 'gfortran' fortran_ver = '.'.join(get_software_version('GCC').split('.')[:2]) else: raise EasyBuildError("Compiler family '%s' currently unsupported.", comp_fam) # math library config known_mathlibs = ['imkl', 'OpenBLAS', 'ATLAS', 'ACML'] mathlib, mathlib_root = None, None for mathlib in known_mathlibs: mathlib_root = get_software_root(mathlib) if mathlib_root is not None: break if mathlib_root is None: raise EasyBuildError( "None of the known math libraries (%s) available, giving up.", known_mathlibs) if mathlib == 'imkl': mathlib = 'mkl' mathlib_root = os.path.join(mathlib_root, 'mkl') else: mathlib = mathlib.lower() # verify selected DDI communication layer known_ddi_comms = ['mpi', 'mixed', 'shmem', 'sockets'] if not self.cfg['ddi_comm'] in known_ddi_comms: raise EasyBuildError( "Unsupported DDI communication layer specified (known: %s): %s", known_ddi_comms, self.cfg['ddi_comm']) # MPI library config mpilib, mpilib_root, mpilib_path = None, None, None if self.cfg['ddi_comm'] == 'mpi': known_mpilibs = ['impi', 'OpenMPI', 'MVAPICH2', 'MPICH2'] for mpilib in known_mpilibs: mpilib_root = get_software_root(mpilib) if mpilib_root is not None: break if mpilib_root is None: raise EasyBuildError( "None of the known MPI libraries (%s) available, giving up.", known_mpilibs) mpilib_path = mpilib_root if mpilib == 'impi': mpilib_path = os.path.join(mpilib_root, 'intel64') else: mpilib = mpilib.lower() else: mpilib, mpilib_root = '', '' # run interactive 'config' script to generate install.info file cmd = "%(preconfigopts)s ./config %(configopts)s" % { 'preconfigopts': self.cfg['preconfigopts'], 'configopts': self.cfg['configopts'], } qa = { "After the new window is open, please hit <return> to go on.": '', "please enter your target machine name: ": machinetype, "Version? [00] ": self.version, "Please enter your choice of FORTRAN: ": fortran_comp, "hit <return> to continue to the math library setup.": '', "MKL pathname? ": mathlib_root, "MKL version (or 'skip')? ": 'skip', "MKL version (or 'proceed')? ": 'proceed', # changed in gamess-20170420R1 "please hit <return> to compile the GAMESS source code activator": '', "please hit <return> to set up your network for Linux clusters.": '', "communication library ('sockets' or 'mpi')? ": self.cfg['ddi_comm'], "Enter MPI library (impi, mvapich2, mpt, sockets):": mpilib, "Enter MPI library (impi, mpich, mpich2, mvapich2, mpt, sockets):": mpilib, # changed in gamess-20170420R1 "Please enter your %s's location: " % mpilib: mpilib_root, "Do you want to try LIBCCHEM? (yes/no): ": 'no', "Enter full path to OpenBLAS libraries (without 'lib' subdirectory):": mathlib_root, "Optional: Build Michigan State University CCT3 & CCSD3A methods? (yes/no): ": 'no', } stdqa = { r"GAMESS directory\? \[.*\] ": self.builddir, r"GAMESS build directory\? \[.*\] ": self.installdir, # building in install directory r"Enter only the main version number, such as .*\nVersion\? ": fortran_ver, r".+gfortran version.\n( \n)?Please enter only the first decimal place, such as .*:": fortran_ver, "Enter your choice of 'mkl' or .* 'none': ": mathlib, } run_cmd_qa(cmd, qa=qa, std_qa=stdqa, log_all=True, simple=True) self.log.debug("Contents of install.info:\n%s" % read_file(os.path.join(self.builddir, 'install.info'))) # patch hardcoded settings in rungms to use values specified in easyconfig file rungms = os.path.join(self.builddir, 'rungms') extra_gmspath_lines = "set ERICFMT=$GMSPATH/auxdata/ericfmt.dat\nset MCPPATH=$GMSPATH/auxdata/MCP\n" try: for line in fileinput.input(rungms, inplace=1, backup='.orig'): line = re.sub(r"^(\s*set\s*TARGET)=.*", r"\1=%s" % self.cfg['ddi_comm'], line) line = re.sub( r"^(\s*set\s*GMSPATH)=.*", r"\1=%s\n%s" % (self.installdir, extra_gmspath_lines), line) line = re.sub(r"(null\) set VERNO)=.*", r"\1=%s" % self.version, line) line = re.sub(r"^(\s*set DDI_MPI_CHOICE)=.*", r"\1=%s" % mpilib, line) line = re.sub( r"^(\s*set DDI_MPI_ROOT)=.*%s.*" % mpilib.lower(), r"\1=%s" % mpilib_path, line) line = re.sub(r"^(\s*set GA_MPI_ROOT)=.*%s.*" % mpilib.lower(), r"\1=%s" % mpilib_path, line) # comment out all adjustments to $LD_LIBRARY_PATH that involves hardcoded paths line = re.sub(r"^(\s*)(setenv\s*LD_LIBRARY_PATH\s*/.*)", r"\1#\2", line) if self.cfg['scratch_dir']: line = re.sub(r"^(\s*set\s*SCR)=.*", r"\1=%s" % self.cfg['scratch_dir'], line) line = re.sub(r"^(\s*set\s*USERSCR)=.*", r"\1=%s" % self.cfg['scratch_dir'], line) sys.stdout.write(line) except IOError as err: raise EasyBuildError("Failed to patch %s: %s", rungms, err)
def install_step(self): """Install ABAQUS using 'setup'.""" if LooseVersion(self.version) >= LooseVersion('2016'): change_dir(os.path.join(self.cfg['start_dir'], '1')) qa = { "Enter selection (default: Install):": '', } no_qa = [ '___', r'\(\d+ MB\)', ] std_qa = { # disable installation of Tosca (6) and Isight (7) r"Isight\nEnter selection \(default: Next\):": '6\n7\n\n', r"(?<!Isight)\nEnter selection \(default: Next\):": '', r"SIMULIA[0-9]*doc.*:": os.path.join(self.installdir, 'doc'), r"SimulationServices.*:": os.path.join(self.installdir, 'sim'), r"Choose the CODE installation directory.*:\n.*\n\n.*:": os.path.join(self.installdir, 'sim'), r"SIMULIA/CAE.*:": os.path.join(self.installdir, 'cae'), r"location of your Abaqus services \(solvers\).*(\n.*){8}:\s*": os.path.join(self.installdir, 'sim'), r"Default.*SIMULIA/Commands\]:\s*": os.path.join(self.installdir, 'Commands'), r"Default.*SIMULIA/CAE/plugins.*:\s*": os.path.join(self.installdir, 'plugins'), r"Default.*SIMULIA/Isight.*:\s*": os.path.join(self.installdir, 'Isight'), r"License Server [0-9]+\s*(\n.*){3}:": 'abaqusfea', # bypass value for license server r"License Server . \(redundant\)\s*(\n.*){3}:": '', r"Please choose an action:": '1', r"SIMULIA/Tosca.*:": os.path.join(self.installdir, 'tosca'), r"location of your existing ANSA installation.*(\n.*){8}:": '', r"FLUENT Path.*(\n.*){7}:": '', } run_cmd_qa('./StartTUI.sh', qa, no_qa=no_qa, std_qa=std_qa, log_all=True, simple=True, maxhits=100) else: change_dir(self.builddir) if self.cfg['install_cmd'] is None: self.cfg['install_cmd'] = "%s/%s-%s/setup" % ( self.builddir, self.name, self.version.split('-')[0]) self.cfg['install_cmd'] += " -replay %s" % self.replayfile if LooseVersion(self.version) < LooseVersion("6.13"): self.cfg['install_cmd'] += " -nosystemcheck" super(EB_ABAQUS, self).install_step() if LooseVersion(self.version) >= LooseVersion('2016'): # also install hot fixes (if any) hotfixes = [src for src in self.src if 'CFA' in src['name']] if hotfixes: # first install Part_3DEXP_SimulationServices hotfix(es), if any hotfixes_3dexp = [ src for src in self.src if 'CFA' in src['name'] and '3DEXP' in src['name'] ] if hotfixes_3dexp: hotfix_dir = os.path.join( self.builddir, 'Part_3DEXP_SimulationServices.Linux64', '1', 'Software') change_dir(hotfix_dir) # SIMULIA_ComputeServices part subdirs = glob.glob( 'HF_SIMULIA_ComputeServices.HF*.Linux64') if len(subdirs) == 1: subdir = subdirs[0] else: raise EasyBuildError( "Failed to find expected subdir for hotfix: %s", subdirs) cwd = change_dir(os.path.join(subdir, '1')) std_qa = { r"Enter selection \(default: Next\):": '', "Choose the .*installation directory.*\n.*\n\n.*:": os.path.join(self.installdir, 'sim'), r"Enter selection \(default: Install\):": '', } run_cmd_qa('./StartTUI.sh', {}, std_qa=std_qa, log_all=True, simple=True, maxhits=100) # F_CAASIMULIAComputeServicesBuildTime part change_dir(cwd) subdirs = glob.glob( 'HF_CAASIMULIAComputeServicesBuildTime.HF*.Linux64') if len(subdirs) == 1: subdir = subdirs[0] else: raise EasyBuildError( "Failed to find expected subdir for hotfix: %s", subdirs) change_dir(os.path.join(cwd, subdir, '1')) run_cmd_qa('./StartTUI.sh', {}, std_qa=std_qa, log_all=True, simple=True, maxhits=100) # next install Part_SIMULIA_Abaqus_CAE hotfix hotfix_dir = os.path.join(self.builddir, 'Part_SIMULIA_Abaqus_CAE.Linux64', '1', 'Software') change_dir(hotfix_dir) subdirs = glob.glob('SIMULIA_Abaqus_CAE.HF*.Linux64') if len(subdirs) == 1: subdir = subdirs[0] else: raise EasyBuildError( "Failed to find expected subdir for hotfix: %s", subdirs) cwd = change_dir(os.path.join(subdir, '1')) std_qa = { r"Enter selection \(default: Next\):": '', "Choose the .*installation directory.*\n.*\n\n.*:": os.path.join(self.installdir, 'cae'), r"Enter selection \(default: Install\):": '', r"\[1\] Continue\n(?:.|\n)*Please choose an action:": '1', r"\[2\] Continue\n(?:.|\n)*Please choose an action:": '2', } no_qa = [ r"Please be patient; it will take a few minutes to complete\.\n(\.)*" ] run_cmd_qa('./StartTUI.sh', {}, no_qa=no_qa, std_qa=std_qa, log_all=True, simple=True, maxhits=100)