1#!/usr/bin/python 2# -*- Mode: python -*- 3 4# Copyright (C) 2001-2006 Artifex Software Inc. 5# All Rights Reserved. 6# 7# This software is provided AS-IS with no warranty, either express or 8# implied. 9# 10# This software is distributed under license and may not be copied, modified 11# or distributed except as expressly authorized under the terms of that 12# license. Refer to licensing information at http://www.artifex.com/ 13# or contact Artifex Software, Inc., 7 Mt. Lassen Drive - Suite A-134, 14# San Rafael, CA 94903, U.S.A., +1(415)492-9861, for further information. 15 16# $Id$ 17 18# This script builds a revision of gs, including svn update, configure, make, install 19# 20# If the revision is HEAD, make install is done; and the svn tree is put (HEAD) and installed 21# into gsconf.gsroot (usually /home/regression/gshead) 22# 23# If the revision is not HEAD, no install is done; and the tree is put into gs.<revision> 24# 25# If release is not None, then a release is built - in progress 26# 27 28 29import os, sys, shutil 30import time 31import optparse, myoptparse 32import string, re 33import gsconf 34 35myself="build_revision.py" 36myversion="1.00" 37 38def logMessage(message,file,revision,printMessage=True): 39 message_time=time.strftime("%Y-%m-%d-%H:%M:%S", time.localtime()) 40 message=myself+" "+revision+" "+message_time+" "+message 41 if printMessage: 42 print message 43 if file: 44 message+="\n" 45 file.write(message) 46 file.flush() 47 48def read_all_lines(f): 49 file = open(f, 'r') 50 lines = file.readlines() 51 file.close() 52 return string.join(lines, '') 53 54def get_revision(dir=None): 55 if dir: 56 cwd=os.getcwd() 57 os.chdir(dir) 58 p = os.popen("svn info") 59 for line in p: 60 if "Revision:" in line: 61 revision=line.strip('Revision: ') 62 revision=revision.strip('\n') 63 break 64 else: 65 revision = None 66 if dir: 67 os.chdir(cwd) 68 return revision 69 70def change_gsproduct(file): 71 tmpfile = "%s.tmp" % (file,) 72 73 startre = re.compile("^#ifndef\ GS_PRODUCT$") 74 changere = re.compile("^.*?\"[A-Za-z -]+\".*?$") 75 endre = re.compile("^$") 76 77 old = open(file, "r") 78 new = open(tmpfile, "w") 79 80 state = 0 81 for line in old.readlines(): 82 if state == 0: 83 m = startre.search(line) 84 if m: 85 state = 1 86 87 new.write(line) 88 elif state == 1: 89 m = changere.search(line) 90 if m: 91 state = 2 92 new.write("\t\"GPL Ghostscript\"\n") 93 else: 94 new.write(line) 95 elif state == 2: 96 m = endre.search(line) 97 if m: 98 state = 0 99 100 new.write(line) 101 102 old.close() 103 new.close() 104 105 os.unlink(file) 106 os.rename(tmpfile, file) 107 108def update_ghostscript(revision,release, 109 gsroot, 110 options, 111 update_stdout,update_stderr, 112 config_stdout,config_stderr, 113 make_stdout,make_stderr, 114 install_stdout,install_stderr, 115 cumulative_file 116 ): 117 118 myself=options.myself+" update_ghostscript" 119 120 if options and options.__dict__.has_key("verbose") and options.verbose: 121 print myself,gsroot 122 123 if release: 124 print myself,"release not yet supported" 125 126 if options and options.__dict__.has_key("capture") and options.capture: 127 captureOutput = True 128 else: 129 captureOutput = False 130 131 update_stdout_file = open(update_stdout, "w") 132 message="update_stdout" 133 logMessage(message,update_stdout_file,revision,printMessage=False) 134 update_stdout_file.close() 135 136 update_stderr_file = open(update_stderr, "w") 137 message="update_stderr" 138 logMessage(message,update_stderr_file,revision,printMessage=False) 139 update_stderr_file.close() 140 141 cwd=os.getcwd() 142 143 revision_file = gsroot+"revision" # remove history until we have successfully completed the update" 144 if os.path.exists(revision_file): 145 os.unlink(revision_file) 146 147 # to prevent errors from left-over installations, remove the install tree 148 if revision == "HEAD": 149 installtree=gsconf.installtree 150 if os.path.exists(installtree): 151 message="remove old installation directory tree "+installtree 152 logMessage(message,cumulative_file,revision) 153 # do a check for sanity of the path 154 if os.path.exists(installtree+"/bin") and os.path.exists(installtree+"/bin/gs"): 155 shutil.rmtree(installtree+"/bin",ignore_errors=True) 156 shutil.rmtree(installtree+"/man",ignore_errors=True) 157 shutil.rmtree(installtree+"/share",ignore_errors=True) 158 159 update_stdout_file = open(update_stdout, "w") 160 161 if options and options.__dict__.has_key("svn") and options.svn: 162 163 product_file = "%sbase/gscdef.c" % (gsroot) 164 if os.path.exists(product_file): 165 os.unlink(product_file) 166 167 # make the source tree corrrect from svn repository 168 169 message="svn checkout "+gsroot 170 logMessage(message,update_stdout_file,revision,printMessage=False) 171 logMessage(message,cumulative_file,revision) 172 173 host="http://svn.ghostscript.com/ghostscript/trunk/gs " 174 175 if os.path.exists(gsroot): 176 revisionarg="-r"+revision+" " 177 command="svn update "+revisionarg+gsroot 178 else: 179 revisionarg="-r"+revision+" " 180 command="svn co "+revisionarg+host+gsroot 181 182 logMessage(message,update_stdout_file,revision,printMessage=False) 183 logMessage(command,cumulative_file,revision) 184 185 if captureOutput: 186 capture=" >> "+update_stdout 187 command+=capture 188 if os.system(command) != 0: 189 msg = "Ghostscript update failed during svn update\n\n" 190 msg = msg + "stdout log:\n\n" 191 msg = msg + read_all_lines(update_stdout) 192 msg = msg + "\nstderr log:\n\n" 193 msg = msg + read_all_lines(update_stderr) 194 logMessage(message,cumulative_file,revision) 195 return (1,msg) 196 197 if revision == "HEAD": 198 revision_value=get_revision(gsroot) 199 else: 200 revision_value = revision 201 202 sys.modules["gsconf"].__dict__["revision"] = revision_value 203 204 205 os.chdir(gsroot) 206 207 message="revision is " + str(revision) 208 logMessage(message,update_stdout_file,revision,printMessage=False) 209 logMessage(message,cumulative_file,revision) 210 211 if options and options.__dict__.has_key("configure") and options.configure: 212 change_gsproduct(product_file) 213 214 message="product change complete:"+product_file 215 logMessage(message,update_stdout_file,revision,printMessage=False) 216 logMessage(message,cumulative_file,revision,) 217 218 if revision == "HEAD": 219 installpath=gsconf.installtree 220 command="./autogen.sh --prefix=" + installpath 221 # HACK: configuring with cups support makes the build script 222 # try to install outside of prefix. Disable for now. 223 command+=" --disable-cups" 224 else: 225 command="./autogen.sh" 226 227 logMessage(command,update_stdout_file,revision,printMessage=False) 228 logMessage(command,cumulative_file,revision) 229 if captureOutput: 230 capture=" > " + config_stdout + " 2> " + config_stderr 231 command+=capture 232 if os.system(command) != 0: 233 msg = "Ghostscript update failed during configuration.\n\n" 234 msg = msg + "stdout log:\n\n" 235 msg = msg + read_all_lines(make_stdout) 236 msg = msg + "\nstderr log:\n\n" 237 msg = msg + read_all_lines(make_stderr) 238 logMessage(message,cumulative_file,revision) 239 return (1,msg) 240 241 message="configuration complete" 242 logMessage(message,update_stdout_file,revision,printMessage=False) 243 logMessage(message,cumulative_file,revision) 244 245 246 if options and options.__dict__.has_key("makeclean") and options.makeclean: 247 command ="make clean " 248 logMessage(command,update_stdout_file,revision,printMessage=False) 249 logMessage(command,cumulative_file,revision) 250 if captureOutput: 251 capture=" > /dev/null 2> /dev/null" 252 command+=capture 253 if os.system(command) != 0: 254 msg = "Ghostscript update failed during make clean\n\n" 255 logMessage(message,cumulative_file,revision) 256 return (1,msg) 257 258 message="make clean complete" 259 logMessage(message,update_stdout_file,revision,printMessage=False) 260 logMessage(message,cumulative_file,revision) 261 262 if options and options.__dict__.has_key("make") and options.make: 263 command="make " 264 logMessage(command,update_stdout_file,revision,printMessage=False) 265 logMessage(command,cumulative_file,revision) 266 if captureOutput: 267 capture="> " + make_stdout + " 2> " + make_stderr 268 command+=capture 269 if os.system(command) != 0: 270 msg = "Ghostscript update failed during make\n\n" 271 msg = msg + "stdout log:\n\n" 272 msg = msg + read_all_lines(make_stdout) 273 msg = msg + "\nstderr log:\n\n" 274 msg = msg + read_all_lines(make_stderr) 275 logMessage(message,cumulative_file,revision) 276 return (1,msg) 277 278 message="make complete" 279 logMessage(message,update_stdout_file,revision,printMessage=False) 280 logMessage(message,cumulative_file,revision) 281 282 if revision == "HEAD": 283 command="make install " 284 logMessage(command,update_stdout_file,revision,printMessage=False) 285 logMessage(command,cumulative_file,revision) 286 if captureOutput: 287 capture="> " + install_stdout + " 2> " + install_stderr 288 command+=capture 289 if os.system(command) != 0: 290 msg = "Ghostscript update failed during install\n\n" 291 msg = msg + "stdout log:\n\n" 292 msg = msg + read_all_lines(install_stdout) 293 msg = msg + "\nstderr log:\n\n" 294 msg = msg + read_all_lines(install_stderr) 295 logMessage(message,cumulative_file,revision) 296 return (1,msg) 297 298 message="make install complete" 299 logMessage(message,update_stdout_file,revision,printMessage=False) 300 logMessage(message,cumulative_file,revision) 301 302 message="installation directory tree is "+gsroot 303 logMessage(message,cumulative_file,revision) 304 305 revision_file_name="revision" 306 revision_file = open(revision_file_name, "w") 307 message=revision_value+"\n" 308 revision_file.write(message) 309 revision_file.close() 310 311 os.chdir(cwd) # return to directory 312 313 update_stdout_file.close() 314 315 return (0,"success") 316 317######################################################### 318 319if __name__ == "__main__": 320 321 os.umask(0002) 322 323 optionsParser=optparse.OptionParser() 324 325 optionsParser.add_option('--version',action='store_true',help="get my version") 326 327 optionsParser.add_option('--revision',action='store',help="under contruction",default="HEAD") 328 optionsParser.add_option('--release',action='store',help="under contruction",default=None) 329 330 optionsParser.add_option('--time','-m',action='store',help="provide start time",default=None) 331 332 optionsParser.add_option('--nosvn',action='store_true',help="do not update the revision source from the svn repository") 333 optionsParser.add_option('--noconfigure',action='store_true',help="do not run auto configure") 334 optionsParser.add_option('--nomakeclean',action='store_true',help="do not make clean before make") 335 optionsParser.add_option('--nomake',action='store_true',help="do not make") 336 337 optionsParser.add_option('--nocapture',action='store_true',help="do not capture stdout and stderr from commands") 338 339 optionsParser.add_option('--remove',action='store_true',help="remove the built directories") 340 341 (options,arguments)=myoptparse.parseCommandLineBasic(optionsParser) 342 343 myself=options.myself 344 345 if options.version: 346 print options.myself,"version",myversion 347 sys.exit(1) 348 349 options.svn = not options.nosvn 350 options.configure = not options.noconfigure 351 options.make = not options.nomake 352 options.makeclean = not options.nomakeclean 353 354 options.capture = not options.nocapture 355 356 revision = options.revision 357 release = options.release 358 359 now=options.time 360 361 logdir=gsconf.logdir 362 if not os.path.exists(logdir): 363 os.mkdir(logdir) 364 365 if now: 366 pass # use command line value of time 367 else: 368 now=time.strftime("%Y-%m-%d-%H:%M:%S", time.localtime()) 369 370 print myself,revision 371 if revision == "HEAD": 372 prefix=logdir+now+"." 373 gsroot=gsconf.gsroot 374 gspath=gsconf.installtree+"bin/gs" 375 gsinstall=gsconf.installtree 376 else: 377 prefix=logdir+revision+"."+now+"." 378 gsroot=gsconf.root+"gs."+revision+"/" 379 gspath=gsroot+"bin/gs" 380 gsinstall=None 381 382 update_stdout=prefix+gsconf.update_stdout 383 update_stderr=prefix+gsconf.update_stderr 384 config_stdout=prefix+gsconf.config_stdout 385 config_stderr=prefix+gsconf.config_stderr 386 make_stdout=prefix+gsconf.make_stdout 387 make_stderr=prefix+gsconf.make_stderr 388 install_stdout=prefix+gsconf.install_stdout 389 install_stderr=prefix+gsconf.install_stderr 390 391 cumulative_file=None 392 393 (err,message) = update_ghostscript(revision,release, 394 gsroot, 395 options, 396 update_stdout,update_stderr, 397 config_stdout,config_stderr, 398 make_stdout,make_stderr, 399 install_stdout,install_stderr, 400 cumulative_file=None 401 ) 402 if err != 0: 403 print message 404 sys.exit(1) 405 406 revision=get_revision(gsroot) 407 408 if not os.path.exists(gspath): 409 message=myself+" FATAL "+"the gs executable does not exist "+gspath 410 logMessage(message,None,revision) 411 sys.exit(1) 412 413 if options.remove: 414 if os.path.exists(gsroot): 415 print "shutil.rmtree(gsroot)",gsroot 416 shutil.rmtree(gsroot) 417 if gsinstall: 418 print "shutil.rmtree(gsinstall)",gsinstall 419 shutil.rmtree(gsinstall) 420 421 print myself,revision,"done" 422 423 sys.exit(0) 424