113540Sandrea.mondelli@ucf.edu#!/usr/bin/env python2.7 22357Sktlim@umich.edu# Copyright (c) 2006 The Regents of The University of Michigan 32357Sktlim@umich.edu# All rights reserved. 42357Sktlim@umich.edu# 52357Sktlim@umich.edu# Redistribution and use in source and binary forms, with or without 62357Sktlim@umich.edu# modification, are permitted provided that the following conditions are 72357Sktlim@umich.edu# met: redistributions of source code must retain the above copyright 82357Sktlim@umich.edu# notice, this list of conditions and the following disclaimer; 92357Sktlim@umich.edu# redistributions in binary form must reproduce the above copyright 102357Sktlim@umich.edu# notice, this list of conditions and the following disclaimer in the 112357Sktlim@umich.edu# documentation and/or other materials provided with the distribution; 122357Sktlim@umich.edu# neither the name of the copyright holders nor the names of its 132357Sktlim@umich.edu# contributors may be used to endorse or promote products derived from 142357Sktlim@umich.edu# this software without specific prior written permission. 152357Sktlim@umich.edu# 162357Sktlim@umich.edu# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 172357Sktlim@umich.edu# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 182357Sktlim@umich.edu# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 192357Sktlim@umich.edu# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 202357Sktlim@umich.edu# OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 212357Sktlim@umich.edu# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 222357Sktlim@umich.edu# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 232357Sktlim@umich.edu# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 242357Sktlim@umich.edu# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 252357Sktlim@umich.edu# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 262357Sktlim@umich.edu# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 272357Sktlim@umich.edu# 282357Sktlim@umich.edu# Authors: Kevin Lim 292357Sktlim@umich.edu 302357Sktlim@umich.eduimport os, os.path, shutil, signal, socket, sys 312357Sktlim@umich.edufrom os import environ as env 322357Sktlim@umich.edufrom os.path import join as joinpath, expanduser 332357Sktlim@umich.edu 342357Sktlim@umich.edudef date(): 352357Sktlim@umich.edu import time 362357Sktlim@umich.edu return time.strftime('%a %b %e %H:%M:%S %Z %Y', time.localtime()) 372357Sktlim@umich.edu 382357Sktlim@umich.edudef cleandir(dir): 392357Sktlim@umich.edu for root, dirs, files in os.walk(dir, False): 402357Sktlim@umich.edu for name in files: 412357Sktlim@umich.edu os.remove(joinpath(root, name)) 422357Sktlim@umich.edu for name in dirs: 432357Sktlim@umich.edu os.rmdir(joinpath(root, name)) 442357Sktlim@umich.edu 452357Sktlim@umich.educlass rsync: 462357Sktlim@umich.edu def __init__(self): 472357Sktlim@umich.edu self.sudo = False 482357Sktlim@umich.edu self.rsync = 'rsync' 492357Sktlim@umich.edu self.compress = False 502357Sktlim@umich.edu self.archive = True 512357Sktlim@umich.edu self.delete = False 522357Sktlim@umich.edu self.options = '' 532357Sktlim@umich.edu 542357Sktlim@umich.edu def do(self, src, dst): 552357Sktlim@umich.edu args = [] 562357Sktlim@umich.edu if self.sudo: 572357Sktlim@umich.edu args.append('sudo') 582357Sktlim@umich.edu 592357Sktlim@umich.edu args.append(self.rsync) 602357Sktlim@umich.edu if (self.archive): 612357Sktlim@umich.edu args.append('-a') 622357Sktlim@umich.edu if (self.compress): 632357Sktlim@umich.edu args.append('-z') 642357Sktlim@umich.edu if (self.delete): 652357Sktlim@umich.edu args.append('--delete') 662357Sktlim@umich.edu if len(self.options): 672357Sktlim@umich.edu args.append(self.options) 682357Sktlim@umich.edu args.append(src) 692357Sktlim@umich.edu args.append(dst) 702357Sktlim@umich.edu 712357Sktlim@umich.edu return os.spawnvp(os.P_WAIT, args[0], args) 722357Sktlim@umich.edu 732357Sktlim@umich.educlass JobDir(object): 742357Sktlim@umich.edu def __init__(self, dir): 752357Sktlim@umich.edu self.dir = dir 762357Sktlim@umich.edu 772357Sktlim@umich.edu def file(self, filename): 782357Sktlim@umich.edu return joinpath(self.dir, filename) 792357Sktlim@umich.edu 802357Sktlim@umich.edu def create(self): 812357Sktlim@umich.edu if os.path.exists(self.dir): 822357Sktlim@umich.edu if not os.path.isdir(self.dir): 832357Sktlim@umich.edu sys.exit('%s is not a directory. Cannot build job' % self.dir) 842357Sktlim@umich.edu else: 852357Sktlim@umich.edu os.mkdir(self.dir) 862357Sktlim@umich.edu 872357Sktlim@umich.edu def exists(self): 882357Sktlim@umich.edu return os.path.isdir(self.dir) 892357Sktlim@umich.edu 902357Sktlim@umich.edu def clean(self): 912357Sktlim@umich.edu cleandir(self.dir) 922357Sktlim@umich.edu 932357Sktlim@umich.edu def hasfile(self, filename): 942357Sktlim@umich.edu return os.path.isfile(self.file(filename)) 952357Sktlim@umich.edu 962357Sktlim@umich.edu def echofile(self, filename, string): 972357Sktlim@umich.edu filename = self.file(filename) 982357Sktlim@umich.edu try: 992357Sktlim@umich.edu f = file(filename, 'w') 1002357Sktlim@umich.edu print >>f, string 1012357Sktlim@umich.edu f.flush() 1022357Sktlim@umich.edu f.close() 1032357Sktlim@umich.edu except IOError,e: 1042357Sktlim@umich.edu sys.exit(e) 1052357Sktlim@umich.edu 1062357Sktlim@umich.edu def rmfile(self, filename): 1072357Sktlim@umich.edu filename = self.file(filename) 1082357Sktlim@umich.edu if os.path.isfile(filename): 1092357Sktlim@umich.edu os.unlink(filename) 1102357Sktlim@umich.edu 1112357Sktlim@umich.edu def readval(self, filename): 1122357Sktlim@umich.edu filename = self.file(filename) 1132357Sktlim@umich.edu f = file(filename, 'r') 1142357Sktlim@umich.edu value = f.readline().strip() 1152357Sktlim@umich.edu f.close() 1162357Sktlim@umich.edu return value 1172357Sktlim@umich.edu 1182357Sktlim@umich.edu def setstatus(self, string): 1192357Sktlim@umich.edu filename = self.file('.status') 1202357Sktlim@umich.edu try: 1212357Sktlim@umich.edu f = file(filename, 'a') 1222357Sktlim@umich.edu print >>f, string 1232357Sktlim@umich.edu f.flush() 1242357Sktlim@umich.edu f.close() 1252357Sktlim@umich.edu except IOError,e: 1262357Sktlim@umich.edu sys.exit(e) 1272357Sktlim@umich.edu 1282357Sktlim@umich.edu def getstatus(self): 1292357Sktlim@umich.edu filename = self.file('.status') 1302357Sktlim@umich.edu try: 1312357Sktlim@umich.edu f = file(filename, 'r') 1322357Sktlim@umich.edu except IOError, e: 1332357Sktlim@umich.edu return 'none' 1342357Sktlim@umich.edu 1352357Sktlim@umich.edu # fast forward to the end 1362357Sktlim@umich.edu for line in f: pass 1372357Sktlim@umich.edu 1382357Sktlim@umich.edu # the first word on the last line is the status 1392357Sktlim@umich.edu return line.split(' ')[0] 1402357Sktlim@umich.edu 1412357Sktlim@umich.edu def __str__(self): 1422357Sktlim@umich.edu return self.dir 1432357Sktlim@umich.edu 1442357Sktlim@umich.eduif __name__ == '__main__': 1452357Sktlim@umich.edu import platform 1462357Sktlim@umich.edu binaries = { 'i686' : 'm5.i386', 1472357Sktlim@umich.edu 'x86_64' : 'm5.amd64' } 1482357Sktlim@umich.edu binary = binaries[platform.machine()] 1492357Sktlim@umich.edu 1502357Sktlim@umich.edu cwd = os.getcwd() 1512357Sktlim@umich.edu rootdir = env.setdefault('ROOTDIR', os.path.dirname(cwd)) 1522357Sktlim@umich.edu oar_jobid = int(env['OAR_JOBID']) 1532357Sktlim@umich.edu oar_jobname = os.path.basename(cwd) 1542357Sktlim@umich.edu #pbs_jobname = env['PBS_JOBNAME'] 1552357Sktlim@umich.edu basedir = joinpath(rootdir, 'Base') 1562357Sktlim@umich.edu jobname = env.setdefault('JOBNAME', oar_jobname) 1572357Sktlim@umich.edu jobfile = env.setdefault('JOBFILE', joinpath(rootdir, 'Test.py')) 1582357Sktlim@umich.edu outdir = env.setdefault('OUTPUT_DIR', cwd) 1592357Sktlim@umich.edu env['POOLJOB'] = 'True' 1602357Sktlim@umich.edu 1612357Sktlim@umich.edu if os.path.isdir("/work"): 1622357Sktlim@umich.edu workbase = "/work" 1632357Sktlim@umich.edu else: 1642357Sktlim@umich.edu workbase = "/tmp/" 1652357Sktlim@umich.edu 1662357Sktlim@umich.edu workdir = joinpath(workbase, '%s.%s' % (env['USER'], oar_jobid)) 1672357Sktlim@umich.edu host = socket.gethostname() 1682357Sktlim@umich.edu 1692357Sktlim@umich.edu os.umask(0022) 1702357Sktlim@umich.edu 1712357Sktlim@umich.edu jobdir = JobDir(outdir) 1722357Sktlim@umich.edu 1732357Sktlim@umich.edu started = date() 1742357Sktlim@umich.edu jobdir.echofile('.running', started) 1752357Sktlim@umich.edu jobdir.rmfile('.queued') 1762357Sktlim@umich.edu jobdir.echofile('.host', host) 1772357Sktlim@umich.edu 1782357Sktlim@umich.edu jobdir.setstatus('running on %s on %s' % (host, started)) 1792357Sktlim@umich.edu 1802357Sktlim@umich.edu if os.path.isdir(workdir): 1812357Sktlim@umich.edu cleandir(workdir) 1822357Sktlim@umich.edu else: 1832357Sktlim@umich.edu os.mkdir(workdir) 1842357Sktlim@umich.edu 1852357Sktlim@umich.edu if False and os.path.isdir('/z/dist'): 1862357Sktlim@umich.edu sync = rsync() 1872357Sktlim@umich.edu sync.delete = True 1882357Sktlim@umich.edu sync.sudo = True 1892357Sktlim@umich.edu sync.do('poolfs::dist/m5/', '/z/dist/m5/') 1902357Sktlim@umich.edu 1912357Sktlim@umich.edu try: 1922357Sktlim@umich.edu os.chdir(workdir) 1932357Sktlim@umich.edu except OSError,e: 1942357Sktlim@umich.edu sys.exit(e) 1952357Sktlim@umich.edu 1962357Sktlim@umich.edu os.symlink(jobdir.file('output'), 'status.out') 1972357Sktlim@umich.edu 1982357Sktlim@umich.edu args = [ joinpath(basedir, binary), joinpath(basedir, 'run.py') ] 1992357Sktlim@umich.edu if not len(args): 2002357Sktlim@umich.edu sys.exit("no arguments") 2012357Sktlim@umich.edu 2022357Sktlim@umich.edu print 'starting job... %s' % started 2032357Sktlim@umich.edu print ' '.join(args) 2042357Sktlim@umich.edu print 2052357Sktlim@umich.edu sys.stdout.flush() 2062357Sktlim@umich.edu 2072357Sktlim@umich.edu childpid = os.fork() 2082357Sktlim@umich.edu if not childpid: 2092357Sktlim@umich.edu # Execute command 2102357Sktlim@umich.edu sys.stdin.close() 2112357Sktlim@umich.edu fd = os.open(jobdir.file("output"), 2122357Sktlim@umich.edu os.O_WRONLY | os.O_CREAT | os.O_TRUNC) 2132357Sktlim@umich.edu os.dup2(fd, sys.stdout.fileno()) 2142357Sktlim@umich.edu os.dup2(fd, sys.stderr.fileno()) 2152357Sktlim@umich.edu os.execvp(args[0], args) 2162357Sktlim@umich.edu 2172357Sktlim@umich.edu def handler(signum, frame): 2182357Sktlim@umich.edu if childpid != 0: 2192357Sktlim@umich.edu os.kill(childpid, signum) 2202357Sktlim@umich.edu 2212357Sktlim@umich.edu signal.signal(signal.SIGHUP, handler) 2222357Sktlim@umich.edu signal.signal(signal.SIGINT, handler) 2232357Sktlim@umich.edu signal.signal(signal.SIGQUIT, handler) 2242357Sktlim@umich.edu signal.signal(signal.SIGTERM, handler) 2252357Sktlim@umich.edu signal.signal(signal.SIGCONT, handler) 2262357Sktlim@umich.edu signal.signal(signal.SIGUSR1, handler) 2272357Sktlim@umich.edu signal.signal(signal.SIGUSR2, handler) 2282357Sktlim@umich.edu 2292357Sktlim@umich.edu done = 0 2302357Sktlim@umich.edu while not done: 2312357Sktlim@umich.edu try: 2322357Sktlim@umich.edu thepid,ec = os.waitpid(childpid, 0) 2332357Sktlim@umich.edu if ec: 2342357Sktlim@umich.edu print 'Exit code ', ec 2352357Sktlim@umich.edu status = 'failure' 2362357Sktlim@umich.edu else: 2372357Sktlim@umich.edu status = 'success' 2382357Sktlim@umich.edu done = 1 2392357Sktlim@umich.edu except OSError: 2402357Sktlim@umich.edu pass 2412357Sktlim@umich.edu 2422357Sktlim@umich.edu complete = date() 2432357Sktlim@umich.edu print '\njob complete... %s' % complete 2442357Sktlim@umich.edu jobdir.echofile('.%s' % status, complete) 2452357Sktlim@umich.edu jobdir.rmfile('.running') 2462357Sktlim@umich.edu jobdir.setstatus('%s on %s' % (status, complete)) 247