Пример #1
0
def submit_job(job, script=None):
    """Submit the specified job to queue for calculation"""

    logging.debug("Submitting job to queue")

    if not script:
        try:
            script = turbogo_helpers.read_clean_file("submitscript.sge")
        except turbogo_helpers.FileAccessError:
            raise turbogo_helpers.FileAccessError
    # submit job in Popen pipe and get job number back.
    p = Popen("qsub", stdin=PIPE, stdout=PIPE)
    poutput, perr = p.communicate(input=script)
    if "has been submitted" in poutput:
        jobid = poutput.split("\n")[0].split(" ")[2]
        if turbogo_helpers.is_int(jobid):
            job.jobid = jobid
            logging.info("Job {} with job id {} submitted".format(job.name, jobid))
            turbogo_helpers.write_file("jobid", ["{}: {}".format(job.jobtype, jobid)])
        else:
            job.jobid = None
            logging.warning("Job id unknown.")
    else:
        job.jobid = None
        logging.warning("Error starting job. qsub output: \n{}".format(poutput))
    return job.jobid
Пример #2
0
def ensure_ts(job):
    """
    This runs to read out the vibrational modes. If there are more than one negative,
    run screwer to adjust the geometry along the imaginary coordinate, and
    resubmits job.
    """
    if job.freqopt == 'numforce':
        newdir = os.path.join(job.indir, 'numforce')
    else:
        newdir = job.indir
    filetoread = os.path.join(newdir, 'control')

    controlfile = turbogo_helpers.read_clean_file(filetoread)

    vib1= False
    vib2 = False

    for i in range(len(controlfile)):
        if '$vibrational spectrum' in controlfile[i]:
            for j in range (i+3, len(controlfile)):
                col = controlfile[j][15:34].strip()
                if col != '0.00':
                    try:
                        if not vib1:
                            vib1 = float(col)
                        elif not vib2:
                            vib2 = float(col)
                    except ValueError:
                        pass
                    else:
                        mode = controlfile[j][:6].strip()
        if vib2:
            break

    if vib1 and vib2:
        if vib1 < 0 and vib2 > 0:
            return 'ts'
        elif vib1 > 0:
            return 'opt'
        elif vib2 < 0:
            return 'imaginary'  # itvc = 1 SHOULD only ever return 1 img. freq
    else:
        logging.warning(
            'Error getting vibrational frequencies from job {}.'.format(
            job.name
        ))
        return 'error'
Пример #3
0
def ensure_not_ts(job):
    """
    This runs to read out the vibrational modes. If there are negatives, runs
    screwer to adjust the geometry along the imaginary coordinate, and
    resubmits job.
    """
    if job.freqopt == 'numforce':
        newdir = os.path.join(job.indir, 'numforce')
    else:
        newdir = job.indir
    filetoread = os.path.join(newdir, 'control')

    controlfile = turbogo_helpers.read_clean_file(filetoread)

    vib1 = False

    for i in range(len(controlfile)):
        if '$vibrational spectrum' in controlfile[i]:
            for j in range (i+3, len(controlfile)):
                col = controlfile[j][15:34].strip()
                if not (col == '0.00' or col == '-0.00'):
                    try:
                        vib1 = float(col)
                    except ValueError:
                        pass
                    else:
                        mode = controlfile[j][:6].strip()
                        break
        if vib1:
            break

    if vib1:
        if job.firstfreq == vib1:
            #Found the same TS as before. End job.
            return 'same'
        job.firstfreq = vib1
        if vib1 < 0:
            os.chdir(newdir)
            screwer = Screwer(mode)
            try:
                screwer.run_screwer()
            except Exception as e:
                logging.warning("Error '{}' running screwer on job {}.".format(
                    e, job.name))
                os.chdir(TOPDIR)
                return "error"
            control = turbogo_helpers.read_clean_file('control')
            newcoord = list()
            readin = False
            for line in control:
                if '$newcoord' in line:
                    readin = -1
                elif '$end' in line:
                    readin = False
                if readin:
                    newcoord.append(line)
                elif readin == -1:
                    readin = True
            if job.freqopt == 'numforce':
                os.chdir(os.pardir)
                turbogo_helpers.write_file('coord', newcoord)
                try:  # Better to remove numforce, if not no biggie
                    os.remove(os.path.join(os.curdir, 'control'))
                    shutil.rmtree(os.path.join(os.curdir, 'numforce'))
                except OSError:
                    pass
            try:
                job.jobid, job.freqopt, job.name, job.jobtype = jobrunner(job=self.job)
                job.curstart = time()
            except Exception as e:
                logging.warning("Error {} resubmitting job {}.".format(
                    e, job.name))
                os.chdir(TOPDIR)
                return 'error'
            os.chdir(TOPDIR)
            return 'opt'
        else:
            return 'completed'
    else:
        logging.warning(
            'Error getting vibrational frequencies from job {}.'.format(
            job.name
        ))
        return 'error'
Пример #4
0
def jobsetup(infile):
    """
    Read the input file, get the keyword flags & geometry. Utilizes a gaussian
    type input file.
    """

    lines = turbogo_helpers.read_clean_file(infile)

    iargs = list()
    igeom = list()
    control_add = list()
    control_remove = list()

    # first parse %args from top of file
    lines.reverse()
    moreargs = True
    while moreargs:
        if lines[-1][0] == "%":
            iargs.append(lines.pop())
        else:
            moreargs = False

    args = turbogo_helpers.check_args(iargs)
    logging.debug("{} args processed".format(len(args)))

    # immediately following %args is the #route card
    if not lines[-1][0] == "#":
        logging.error(
            """Syntax error at route. Must immediately follow
                      arguements ('%') and start with #"""
        )
        raise InputSyntaxError(
            str(lines[0]),
            """Syntax error at route.
                               Must immediately follow arguements ('%') and
                               start with #""",
        )
    else:
        iroute = lines.pop()

    logging.debug("Parsing input route card.")
    route = turbogo_helpers.check_route(iroute)
    logging.debug("{} Route parameters processed".format(len(route)))

    # specs from gaussian: blank line required
    if not lines[-1] == "":
        logging.error(
            """Syntax error after route. Blank line required before
                      title"""
        )
        raise InputSyntaxError(
            str(lines[0]),
            """Syntax error after route.
                               Blank line required before title""",
        )
    else:
        del lines[-1]

    # Now is the job title.
    title = str(lines[-1])
    logging.debug("Title: {}".format(title))
    del lines[-1]

    # Gaussian spec another blank line
    if not lines[-1] == "":
        logging.error(
            """Syntax error after title. Blank line required before
                      charge & spin"""
        )
        raise InputSyntaxError(
            str(lines[0]),
            """Syntax error after title.
                               Blank line required before charge & spin""",
        )
    else:
        del lines[-1]

    # Charge and spin (0 1)
    ichspin = lines[-1]
    ch_spin = turbogo_helpers.check_chspin(ichspin)
    logging.debug("Charge of {} and spin of {}.".format(ch_spin["ch"], ch_spin["spin"]))
    del lines[-1]

    # Input Geometry in xyz cartesian format
    moregeom = True
    while moregeom:
        if not lines[-1][:1] == "":
            igeom.append(lines.pop())
        else:
            moregeom = False

    geom = turbogo_helpers.check_geom(igeom)
    logging.debug("{} lines of geometry processed".format(len(geom)))

    # gaussian spec blankline
    if not lines[-1] == "":
        logging.error("Syntax error after geometry. Blank line required.")
        raise InputSyntaxError(
            str(lines[0]),
            """Syntax error after geometry.
                               Blank line required.""",
        )
    else:
        del lines[-1]

    # new spec: manual add or subtract from control file with:
    # $opt to add, or:
    # -$opt to remove
    if len(lines) > 0:
        logging.debug("Parsing additional control arguements")
        morelines = True
        while morelines:
            try:
                if lines[-1][0] == "$" or lines[-1][0] == "-" and lines[-1][1] == "$":
                    if lines[-1][0] == "$":
                        control_add.append(lines.pop())
                    else:
                        control_remove.append(lines.pop())
                else:
                    morelines = False
            except IndexError:
                morelines = False
        logging.debug("{} additional lines processed".format(len(control_add)))

    # Set up job.class
    logging.debug("Setting up Job with collected information.")
    job = Job()
    job.name = title
    job.charge = ch_spin["ch"]
    job.spin = ch_spin["spin"]
    if "basis" in route:
        job.basis = route["basis"]
    if "functional" in route:
        job.functional = route["functional"]
    if "jobtype" in route:
        job.jobtype = route["jobtype"]
    else:
        job.jobtype = "sp"
    if job.jobtype == "opt" or job.jobtype == "optfreq":
        # one atom checking - can't opt one atom, so single point it.
        if len(geom) == 1:
            logging.debug("One atom job changed to SP")
            job.jobtype = "sp"
    if "freqopts" in route and job.jobtype != "sp":
        job.freqopts = route["freqopts"]
    elif job.jobtype == "freq" and not "freqopts" in route:
        job.freqopts = DEFAULT_FREQ
    elif job.jobtype == "ts" and not "freqopts" in route:
        job.freqopts = DEFAULT_FREQ
    if "ri" in route:
        job.ri = True
    else:
        job.ri = False
    if "marij" in route and "ri" in route:
        job.marij = True
    else:
        job.ri = False
    if "disp" in route or job.functional == "b97-d":
        job.disp = True
    if "freeh" in route:
        job.freeh = True
    if job.freeh:
        job.freqopts += "+freeh"
    if "iterations" in args:
        job.iterations = int(args["iterations"])
    elif "maxcycles" in args:
        job.iterations = int(args["maxcycles"])
    if "nproc" in args:
        job.nproc = int(args["nproc"])
    if "cosmo" in args:
        job.cosmo = args["cosmo"]
    if "rt" in args:
        job.rt = "{}:00:00".format(args["rt"])
    if job.jobtype != "freq":
        if "arch" in args:
            job.para_arch = args["arch"]
    else:
        job.para_arch = "SMP"
    if "mod" in args and not args["mod"]:
        logging.debug("No mod of control requested")
    else:
        control_add = turbogo_helpers.auto_control_mod(control_add, job)
    job.control_add = control_add
    job.control_remove = control_remove
    job.geometry = geom
    return job