[cig-commits] [commit] baagaard/binary-packaging: Created make_package for creating binary package. (d5dd0dc)
cig_noreply at geodynamics.org
cig_noreply at geodynamics.org
Mon Oct 21 13:38:11 PDT 2013
Repository : ssh://geoshell/pylith
On branch : baagaard/binary-packaging
Link : https://github.com/geodynamics/pylith/compare/0000000000000000000000000000000000000000...d5dd0dcd3e7f9adf371e85dfbcd7f46d00005760
>---------------------------------------------------------------
commit d5dd0dcd3e7f9adf371e85dfbcd7f46d00005760
Author: Brad Aagaard <baagaard at usgs.gov>
Date: Mon Oct 21 13:39:55 2013 -0700
Created make_package for creating binary package.
Refactor creating binary package from buildbot. Appears to work for
linux. Not tested for cygwin.
>---------------------------------------------------------------
d5dd0dcd3e7f9adf371e85dfbcd7f46d00005760
packager/cig.ico | Bin 0 -> 1078 bytes
packager/cygwin.py | 343 +++++++++++++++++++++++++++++++++
packager/make_package.py | 482 +++++++++++++++++++++++++++++++++++++++++++++++
packager/packinglist.cfg | 91 +++++++++
4 files changed, 916 insertions(+)
diff --git a/packager/cig.ico b/packager/cig.ico
new file mode 100644
index 0000000..34896de
Binary files /dev/null and b/packager/cig.ico differ
diff --git a/packager/cygwin.py b/packager/cygwin.py
new file mode 100644
index 0000000..618a8a3
--- /dev/null
+++ b/packager/cygwin.py
@@ -0,0 +1,343 @@
+#!/usr/bin/env python
+#
+# ----------------------------------------------------------------------
+#
+# Brad T. Aagaard, U.S. Geological Survey
+# Charles A. Williams, GNS Science
+# Matthew G. Knepley, University of Chicago
+#
+# This code was developed as part of the Computational Infrastructure
+# for Geodynamics (http://geodynamics.org).
+#
+# Copyright (c) 2010-2013 University of California, Davis
+#
+# See COPYING for license information.
+#
+# ----------------------------------------------------------------------
+#
+# Functions used in creating PyLith binary with cygwin for windows.
+#
+# Usage: make_package.py
+
+import os, sys
+from os.path import basename, dirname, isabs, isdir, isfile, join
+import shutil
+
+def installCigIcon(prefix):
+ cigIco = "cig.ico"
+ os.system("cp %s %s" % (cigIco, prefix))
+ return
+
+
+def minCygwin(python):
+ # Minimal set of Cygwin binaries, as determined while preparing for CFEM 2006.
+ l = [
+ "[.exe",
+ "bash.exe",
+ "cat.exe",
+ "cp.exe",
+ "env.exe",
+ "cygattr-1.dll",
+ "cygiconv-2.dll",
+ "cygintl-8.dll",
+ "cygncurses-9.dll",
+ "cygpath.exe",
+ "cygcheck.exe",
+ "cygreadline7.dll",
+ "cyggfortran-3.dll",
+ "cyggcc_s-1.dll",
+ "cygstdc++-6.dll",
+ "cygncursesw-10.dll",
+ # This is given special treatment.
+ "cygwin1.dll",
+ "cygz.dll", # for HDF5 (used by Cigma)
+ "echo.exe",
+ "gunzip",
+ "gzip.exe",
+ "lib" + python + ".dll",
+ "ln.exe",
+ "ls.exe",
+ "ldd.exe",
+ "pwd.exe",
+ "python",
+ python + ".exe",
+ "rm.exe",
+ "sed.exe",
+ "sh.exe",
+ "tar.exe",
+ "vim-nox.exe",
+ "which.exe",
+ ]
+ l = ["/bin/" + b for b in l]
+
+ # Additional Python stuff.
+ l.extend([
+ "/lib/" + python,
+ "/usr/include/" + python,
+ ])
+
+ # Lapack libraries (used by numpy) now placed in own location.
+ l.extend([
+ "/lib/lapack",
+ ])
+
+ return l
+
+def installMungedCygwinDLL(munged):
+ # We don't require that the user has Cygwin installed. At the
+ # same time, we need to avoid conflicts if they *do* have it
+ # installed.
+
+ # Therefore, we install a munged copy of "cygwin1.dll", performing
+ # the following transformations:
+ # Cygnus Solutions -> Cigwin Solutions
+ # cygwin1S4 -> cigwin1S4
+ # These are the registry key name and the shared memory object
+ # name, respectively.
+
+ # N.B.: It is significant that the replacement string is the same
+ # length as the original string. Otherwise, the DLL would become
+ # corrupted.
+
+ # This gives us the freedom to create our own chrooted environment
+ # using Cygwin's mounts, without messing-up the Cygwin registry on
+ # systems that do have Cygwin installed. Registry clean-up at
+ # uninstall is also made easy.
+
+ # Ugly, yes; but so much easier than building a custom Cygwin from
+ # source...
+ status = os.system("""sed -b """
+ """-e "s/Cygnus Solutions/Cigwin Solutions/g" """
+ """-e s/cygwin1S4/cigwin1S4/g """
+ """/bin/cygwin1.dll > %s""" % munged)
+ if status != 0:
+ sys.exit("sed: exit %d" % status)
+ return
+
+
+def installMinimalCygwin(python, prefix):
+ cygwin = minCygwin(python)
+ copyAll(cygwin, prefix)
+ installMungedCygwinDLL("bin/cygwin1.dll")
+ return
+
+
+def rebaseDLLs(stage):
+ # Work-around "unable to remap xyz.dll to same address as parent".
+ # The base and offset were determined through trial-and-error.
+
+ print "Rebasing DLLs."
+
+ dlls = []
+
+ for dirpath, dirnames, filenames in os.walk(stage):
+ for filename in filenames:
+ if filename.endswith(".dll"):
+ dll = join(dirpath, filename)
+ print dll
+ dlls.append(dll)
+
+ if not dlls:
+ sys.exit("no DLLs found!")
+ dlls = ' '.join(dlls)
+
+ status = os.system("""rebase -v -d -b 0x70000000 -o 0x100000 %s""" % dlls)
+ if status != 0:
+ sys.exit("rebase: exit %d" % status)
+ return
+
+
+def stageInstallation(prefix, workdir, python, pl):
+
+ stage = join(workdir, "buildbot-win-stage")
+ shutil.rmtree(stage, ignore_errors=True)
+ os.mkdir(stage)
+ os.chdir(stage)
+
+ print "Copying packing list to %s." % stage
+ copyAll(pl.files(), prefix)
+
+ print "Installing minimal cygwin."
+ installMinimalCygwin(python, prefix)
+
+ rebaseDLLs(stage)
+
+ return stage
+
+
+def generateISS(workdir, sourceDir, info, pl, bashrc, python, stage=None):
+ s = open(workdir + "/buildbot.iss", "w")
+
+
+ # [Setup]
+ s.write(
+"""; Inno Setup Script generated by BuildBot
+
+[Setup]
+AppName=%(AppName)s
+AppVerName=%(AppVerName)s
+AppPublisher=Computational Infrastructure for Geodynamics
+AppPublisherURL=http://www.geodynamics.org/
+AppSupportURL=http://www.geodynamics.org/
+AppUpdatesURL=http://www.geodynamics.org/
+DefaultDirName={pf}\\%(AppName)s
+DefaultGroupName=%(AppName)s
+SourceDir=%(SourceDir)s
+
+""" % info
+ )
+
+
+ # [Tasks]
+ s.write(
+"""
+[Tasks]
+Name: "desktopicon"; Description: "Create a &desktop icon"; GroupDescription: "Additional icons:"
+
+""")
+
+
+ # [Files]
+ # NOTE: Don't use "Flags: ignoreversion" on any shared system files
+ s.write(
+"""
+[Files]
+"""
+ )
+ if stage:
+ for pathname in os.listdir(stage):
+ if isfile(pathname):
+ s.write("""Source: "%s"; DestDir: "{app}"; Flags: ignoreversion\n""" % pathname)
+ else:
+ s.write("""Source: "%s\\*"; DestDir: "{app}\\%s"; Flags: ignoreversion recursesubdirs\n""" % (pathname, pathname))
+ else:
+ for src, dest in itwindirs(pl.directories, sourceDir):
+ s.write("""Source: "%s\\*"; DestDir: "%s"; Flags: ignoreversion recursesubdirs\n""" % (src, dest))
+ for src, dest in itwinfiles(pl.files(), sourceDir):
+ s.write("""Source: "%s"; DestDir: "%s"; Flags: ignoreversion\n""" % (src, dest))
+ for f in [bashrc, "cig.ico"]:
+ s.write("""Source: "%s"; DestDir: "{app}"; Flags: ignoreversion\n""" % f)
+
+
+ # [Dirs]
+ s.write(
+"""
+[Dirs]
+; Cygwin demands a /tmp directory
+Name: "{app}\\tmp"
+; for our /usr mounts
+Name: "{app}\\usr"
+Name: "{app}\\usr\\bin"
+Name: "{app}\\usr\\lib"
+
+"""
+ )
+
+
+ # [Registry]
+ s.write(
+"""
+[Registry]
+Root: HKLM; Subkey: "Software\\Cigwin Solutions"; Flags: uninsdeletekey noerror
+Root: HKLM; Subkey: "Software\\Cigwin Solutions\\Cygwin"; Flags: uninsdeletekey noerror
+Root: HKLM; Subkey: "Software\\Cigwin Solutions\\Cygwin\\mounts v2"; Flags: uninsdeletekey noerror
+Root: HKLM; Subkey: "Software\\Cigwin Solutions\\Cygwin\\mounts v2\\/"; Flags: uninsdeletekey noerror
+Root: HKLM; Subkey: "Software\\Cigwin Solutions\\Cygwin\\mounts v2\\/"; Flags: noerror; ValueType: string; ValueName: "native"; ValueData: "{app}"
+Root: HKLM; Subkey: "Software\\Cigwin Solutions\\Cygwin\\mounts v2\\/"; Flags: noerror; ValueType: dword; ValueName: "flags"; ValueData: "00000002"
+Root: HKLM; Subkey: "Software\\Cigwin Solutions\\Cygwin\\mounts v2\\/usr/bin"; Flags: uninsdeletekey noerror
+Root: HKLM; Subkey: "Software\\Cigwin Solutions\\Cygwin\\mounts v2\\/usr/bin"; Flags: noerror; ValueType: string; ValueName: "native"; ValueData: "{app}\\bin"
+Root: HKLM; Subkey: "Software\\Cigwin Solutions\\Cygwin\\mounts v2\\/usr/bin"; Flags: noerror; ValueType: dword; ValueName: "flags"; ValueData: "00000002"
+Root: HKLM; Subkey: "Software\\Cigwin Solutions\\Cygwin\\mounts v2\\/usr/lib"; Flags: uninsdeletekey noerror
+Root: HKLM; Subkey: "Software\\Cigwin Solutions\\Cygwin\\mounts v2\\/usr/lib"; Flags: noerror; ValueType: string; ValueName: "native"; ValueData: "{app}\\lib"
+Root: HKLM; Subkey: "Software\\Cigwin Solutions\\Cygwin\\mounts v2\\/usr/lib"; Flags: noerror; ValueType: dword; ValueName: "flags"; ValueData: "00000002"
+; for non-admin install
+Root: HKCU; Subkey: "Software\\Cigwin Solutions"; Flags: uninsdeletekey
+Root: HKCU; Subkey: "Software\\Cigwin Solutions\\Cygwin"; Flags: uninsdeletekey
+Root: HKCU; Subkey: "Software\\Cigwin Solutions\\Cygwin\\mounts v2"; Flags: uninsdeletekey
+Root: HKCU; Subkey: "Software\\Cigwin Solutions\\Cygwin\\mounts v2\\/"; Flags: uninsdeletekey
+Root: HKCU; Subkey: "Software\\Cigwin Solutions\\Cygwin\\mounts v2\\/"; ValueType: string; ValueName: "native"; ValueData: "{app}"
+Root: HKCU; Subkey: "Software\\Cigwin Solutions\\Cygwin\\mounts v2\\/"; ValueType: dword; ValueName: "flags"; ValueData: "00000002"
+Root: HKCU; Subkey: "Software\\Cigwin Solutions\\Cygwin\\mounts v2\\/usr/bin"; Flags: uninsdeletekey
+Root: HKCU; Subkey: "Software\\Cigwin Solutions\\Cygwin\\mounts v2\\/usr/bin"; ValueType: string; ValueName: "native"; ValueData: "{app}\\bin"
+Root: HKCU; Subkey: "Software\\Cigwin Solutions\\Cygwin\\mounts v2\\/usr/bin"; ValueType: dword; ValueName: "flags"; ValueData: "00000002"
+Root: HKCU; Subkey: "Software\\Cigwin Solutions\\Cygwin\\mounts v2\\/usr/lib"; Flags: uninsdeletekey
+Root: HKCU; Subkey: "Software\\Cigwin Solutions\\Cygwin\\mounts v2\\/usr/lib"; ValueType: string; ValueName: "native"; ValueData: "{app}\\lib"
+Root: HKCU; Subkey: "Software\\Cigwin Solutions\\Cygwin\\mounts v2\\/usr/lib"; ValueType: dword; ValueName: "flags"; ValueData: "00000002"
+
+"""
+ )
+
+
+ # [INI]
+ s.write("""[INI]\n""")
+ for name, filename, url in pl.urls:
+ s.write("""Filename: "{app}\\%(filename)s.url"; Section: "InternetShortcut"; Key: "URL"; String: "%(url)s"\n""" %
+ {'filename': filename, 'url': url})
+
+
+ # [Icons]
+ s.write(
+"""
+[Icons]
+Name: "{group}\\%(AppName)s"; Filename: "{app}\\bin\\bash.exe"; Parameters: "--init-file %(bashrc)s -i"; WorkingDir: "{app}"; IconFilename: "{app}\\cig.ico"
+Name: "{userdesktop}\\%(AppName)s"; Filename: "{app}\\bin\\bash.exe"; Tasks: desktopicon; Parameters: "--init-file %(bashrc)s -i"; WorkingDir: "{app}"; IconFilename: "{app}\\cig.ico"
+""" % {'AppName': info['AppName'], 'bashrc': bashrc}
+ )
+ for name, filename, url in pl.urls:
+ s.write("""Name: "{group}\\%s"; Filename: "{app}\\%s.url"\n""" % (name, filename))
+ s.write("""Name: "{group}\Uninstall %(AppName)s"; Filename: "{uninstallexe}"\n""" % info)
+
+
+ # [Run]
+ s.write(
+"""
+[Run]
+Filename: "{app}\\bin\\bash.exe"; Description: "Launch %(AppName)s"; Parameters: "--init-file %(bashrc)s -i"; WorkingDir: "{app}"; Flags: nowait postinstall skipifsilent
+
+""" % {'AppName': info['AppName'], 'bashrc': bashrc}
+ )
+
+
+ # [UninstallDelete]
+ s.write("""[UninstallDelete]\n""")
+ for name, filename, url in pl.urls:
+ s.write("""Type: files; Name: "{app}\%s.url"\n""" % filename)
+ for filename in [".bash_history"]:
+ s.write("""Type: files; Name: "{app}\%s"\n""" % filename)
+
+ s.write("\n; end of file\n")
+
+ return
+
+
+def createInstaller(python, stage, workdir, name, package, version, pl,
+ installer):
+
+ sourceDir = cygpath("-w", stage)
+
+ info = {
+ "AppName": name,
+ "AppVerName": name + " v" + version,
+ "SourceDir": sourceDir,
+ }
+
+ installCigIcon(stage)
+ bashrc = generateBashrc(stage, package, info)
+
+ generateISS(workdir, sourceDir, info, pl, bashrc, python, stage)
+
+ os.chdir(workdir)
+
+ os.system("unix2dos buildbot.iss")
+
+ status = os.system("iscc buildbot.iss")
+ if status != 0:
+ sys.exit("iscc: exit %d" % status)
+
+ status = os.system("mv %s/Output/setup.exe %s.exe" % (stage, installer))
+ if status != 0:
+ sys.exit("mv: exit %d" % status)
+
+ return
+
+
diff --git a/packager/make_package.py b/packager/make_package.py
new file mode 100755
index 0000000..a1be441
--- /dev/null
+++ b/packager/make_package.py
@@ -0,0 +1,482 @@
+#!/usr/bin/env python
+#
+# ----------------------------------------------------------------------
+#
+# Brad T. Aagaard, U.S. Geological Survey
+# Charles A. Williams, GNS Science
+# Matthew G. Knepley, University of Chicago
+#
+# This code was developed as part of the Computational Infrastructure
+# for Geodynamics (http://geodynamics.org).
+#
+# Copyright (c) 2010-2013 University of California, Davis
+#
+# See COPYING for license information.
+#
+# ----------------------------------------------------------------------
+#
+# Create PyLith binary package.
+#
+# Usage: make_package.py
+
+import os, sys, platform
+from popen2 import Popen4
+from glob import glob
+from os.path import basename, dirname, isabs, isdir, isfile, join
+import shutil
+from distutils.sysconfig import parse_makefile
+from ConfigParser import ConfigParser
+import cygwin
+
+
+class Packaging(object):
+ _name = 'packaging'
+ _attrs = ['bin_dirs',
+ 'lib_dirs',
+ 'misc_dirs',
+ 'files',
+ 'strip_list',
+ 'exclude',
+ 'scripts',
+ 'urls',
+ ]
+
+
+class Config(object):
+
+ sections = [Packaging]
+
+ #@classmethod
+ def readPackingList(cls):
+
+ parser = ConfigParser()
+ curdir = dirname(__file__)
+ parser.read(join(curdir, "packinglist.cfg"))
+
+ config = Config()
+
+ for sectionCls in cls.sections:
+ sectionDct = parser._sections.get(sectionCls._name, None)
+ section = None
+ if sectionDct is not None:
+ section = sectionCls()
+ for attr in section._attrs:
+ value = sectionDct.get(attr, "")
+ value = value.split()
+ setattr(section, attr, value)
+ setattr(config, sectionCls._name, section)
+
+ return config
+ readPackingList = classmethod(readPackingList)
+
+
+def getMakeInfo():
+ # NYI: This is Autotools-specific.
+ makefile = parse_makefile("Makefile")
+ info = {'package_name': makefile['PACKAGE_NAME'],
+ 'package': makefile['PACKAGE'],
+ 'version': makefile['VERSION'],
+ 'srcdir': makefile['abs_top_srcdir'],
+ 'prefix': makefile['prefix'],
+ 'python_version': makefile['PYTHON_VERSION'],
+ }
+ return info
+
+
+
+def walkDirTree(dirname):
+ """
+ Get list of files in tree under dirname.
+ """
+ fullNames = []
+ for dirpath, dirs, files in os.walk(dirname):
+ for f in files:
+ fullNames.append(os.path.join(dirpath, f))
+ return fullNames
+
+
+def filterList(l, excludes):
+ try:
+ import re, functools, operator
+
+ pats = [re.compile(ex) for ex in excludes]
+ return [i for i in l if not functools.reduce(operator.or_, [bool(pat.match(i)) for pat in pats])]
+ except (ImportError, AttributeError):
+ import re, operator
+
+ pats = [re.compile(ex) for ex in excludes]
+ return [i for i in l if not reduce(operator.or_, [bool(pat.match(i)) for pat in pats])]
+
+
+class PackingList(object):
+ def __init__(self, config, opSys, python):
+
+ binDirs = config.packaging.bin_dirs
+ libDirs = config.packaging.lib_dirs
+ miscDirs = config.packaging.misc_dirs
+ if platform.machine() == "x86_64":
+ libDirs.append("lib64")
+ self.directories = binDirs + libDirs + miscDirs
+
+ self.extraFiles = config.packaging.files
+ self.exclude = config.packaging.exclude
+
+ self.programs = []
+ for d in binDirs:
+ self.programs.extend(walkDirTree(d))
+ self.programs = filterList(self.programs, self.exclude)
+
+ self.libraries = []
+ for d in libDirs:
+ self.libraries.extend(walkDirTree(d))
+ self.libraries = filterList(self.libraries, self.exclude)
+
+ self.misc = []
+ for d in miscDirs:
+ self.misc.extend(walkDirTree(d))
+ self.misc = filterList(self.misc, self.exclude)
+
+ # KLUDGE Explicitly add include/pythonX.X/pyconfig.h if it exists.
+ pythonConfigFile = "include/" + python + "/pyconfig.h"
+ if isfile(pythonConfigFile):
+ self.misc.append(pythonConfigFile)
+
+ # Scripts are application specific.
+ self.scripts = []
+ for s in config.packaging.scripts:
+ s = "bin/" + s
+ self.scripts.append(s)
+
+ # Suffix for libraries that will be stripped of symbols.
+ if opSys == "linux":
+ libSuffix = ".so"
+ elif opSys == "darwin":
+ libSuffix = ".dylib"
+ elif opSys == "win":
+ libSuffix = ".dll"
+ else:
+ sys.exit("Unknown OS: " + opSys)
+
+ self.stripList = []
+ if opSys == "win":
+ for f in config.packaging.strip_list:
+ fdll = f.replace("lib/lib", "bin/cyg")+"-0"+libSuffix
+ if fdll in self.libraries:
+ self.stripList.append(fdll)
+ else:
+ for f in config.packaging.strip_list:
+ flib = f+libSuffix
+ if flib in self.libraries:
+ self.stripList.append(flib)
+
+ cig = [("CIG", "cig", "http://www.geodynamics.org/")]
+ self.urls = cig + tupleUp(config.packaging.urls, 3)
+
+ return
+
+
+ def addFile(self, f):
+ self.misc.append(f)
+
+ def addDirectory(self, d):
+ self.directories.append(d)
+ newFiles = walkDirTree(d)
+ newFiles = filterList(newFiles, self.exclude)
+ self.misc.extend(newFiles)
+
+
+ def files(self):
+ for f in self.programs:
+ yield f
+ for f in self.libraries:
+ yield f
+ for f in self.misc:
+ yield f
+ for f in self.extraFiles:
+ yield f
+ return
+
+
+ def all(self):
+ for d in self.directories:
+ yield d
+ for f in self.files():
+ yield f
+ return
+
+
+def tupleUp(l, n):
+ tuples = []
+ i = iter(l)
+ try:
+ while True:
+ t = []
+ for count in xrange(n):
+ t.append(i.next())
+ tuples.append(tuple(t))
+ except StopIteration:
+ pass
+ return tuples
+
+
+def spawn(*argv):
+ print ' '.join(argv)
+ status = os.spawnvp(os.P_WAIT, argv[0], argv)
+ if status != 0:
+ statusMsg = "%s: %s: exit %d" % (sys.argv[0], argv[0], status)
+ sys.exit(statusMsg)
+ return
+
+
+def ospawn(*argv):
+ print ' '.join(argv)
+ child = Popen4(argv)
+
+ child.tochild.close()
+
+ output = child.fromchild.readlines()
+ status = child.wait()
+
+ exitStatus = None
+ if (os.WIFSIGNALED(status)):
+ statusStr = "signal %d" % os.WTERMSIG(status)
+ elif (os.WIFEXITED(status)):
+ exitStatus = os.WEXITSTATUS(status)
+ statusStr = "exit %d" % exitStatus
+ else:
+ statusStr = "status %d" % status
+ if exitStatus != 0:
+ sys.exit("%s: %s: %s" % (sys.argv[0], argv[0], statusStr))
+
+ return output
+
+
+def cygpath(*args):
+ output = ospawn("cygpath", *args)
+ return output[0].rstrip()
+
+
+def getGitInfo(srcdir):
+ workdir = os.getcwd()
+ os.chdir(srcdir)
+ output = ospawn("git", "branch", "-v")
+ os.chdir(workdir)
+ revision = "unknown"
+ for line in output:
+ if line[0] == "*":
+ values = line.split()
+ revision = values[2]
+ return revision
+
+
+def itwindirs(l, sourceDir):
+ for src in l:
+ if isinstance(src, tuple):
+ src, dest = src
+ elif isabs(src):
+ dest = src[1:]
+ else:
+ dest = src
+ src = cygpath("-w", src)
+ if src.startswith(sourceDir):
+ src = src[len(sourceDir)+1:]
+ dest = "{app}\\" + dest.replace("/", "\\")
+ yield src, dest
+ return
+
+
+def itwinfiles(l, sourceDir):
+ for src in l:
+ if isinstance(src, tuple):
+ src, dest = src
+ elif isabs(src):
+ dest = dirname(src)[1:]
+ else:
+ dest = dirname(src)
+ src = cygpath("-w", src)
+ if src.startswith(sourceDir):
+ src = src[len(sourceDir)+1:]
+ dest = "{app}\\" + dest.replace("/", "\\")
+ yield src, dest
+ return
+
+
+def copyAll(srcList, prefix):
+ for src in srcList:
+ if isinstance(src, tuple):
+ src, dest = src
+ elif isabs(src):
+ dest = dirname(src)[1:]
+ else:
+ dest = dirname(src)
+ if not isabs(src):
+ src = join(prefix, src)
+ if not isdir(dest):
+ os.makedirs(dest)
+
+ if not isdir(src):
+ shutil.copy(src, dest) # faster than os.system() for small files
+ else:
+ os.system("cp -r %s %s" % (src, dest))
+ return
+
+
+def generateBashrc(prefix, package, info):
+ bashrc = "." + package.lower() + "rc"
+ s = open(prefix + "/" + bashrc, "w")
+
+ stuff = {
+ "line": "-" * len(info["AppVerName"]),
+ }
+ stuff.update(info)
+
+ s.write(
+r"""
+
+export PATH=/usr/bin:/bin:/lib:/lib/lapack:$PATH
+
+echo %(line)s
+echo %(AppVerName)s
+echo %(line)s
+
+PS1='\[\e]0;\w\a\]\n\[\e[32m\]\u@\h \[\e[33m\]\w\[\e[0m\]\n\$ '
+""" % stuff
+ )
+
+ return bashrc
+
+
+def stripBinaries(pl, opSys):
+ strip = "strip"
+ if opSys == "darwin":
+ # Just plain "strip" renders our Python interpreter unusable
+ # by extension modules.
+ strip = "strip -S"
+ if len(pl.stripList) > 0:
+ status = os.system(strip + " " + " ".join(pl.stripList))
+ if status != 0:
+ sys.exit("strip: exit %d" % status)
+ return
+
+
+def rewriteScripts(pl, prefix, opSys):
+ # Tweak the shebang line of scripts so they are relative instead
+ # of absolute.
+
+ if opSys == "win":
+ # chrooted environment
+ relative = "#!/bin/%s"
+ else:
+ relative = "#!/usr/bin/env %s"
+ absolute = "#!" + prefix + "/bin/"
+
+ for script in pl.scripts:
+ s = open(script, "r")
+ lines = s.readlines()
+ s.close()
+ shebang = lines[0]
+ if shebang.startswith(absolute):
+ interpreter = shebang[len(absolute):]
+ shebang = relative % interpreter
+ s = open(script, "w")
+ s.write(shebang)
+ for line in lines[1:]:
+ s.write(line)
+ s.close()
+
+ return
+
+
+def installSource(pl, taggedArchive):
+ src = "src"
+ shutil.rmtree(src, ignore_errors=True)
+ if not isdir(src):
+ os.makedirs(src)
+ spawn("tar", "-C", src, "-xf", taggedArchive)
+ pl.addDirectory(src)
+ return
+
+
+def mkpkg():
+ # WithProperties simply doesn't work in this case.
+ if False:
+ revision = sys.argv[2]
+ if revision:
+ revision = "r" + revision
+ else:
+ revision = "forced"
+
+ makeinfo = getMakeInfo()
+ python = "python"+makeinfo['python_version']
+ distdir = makeinfo['package'] + "-" + makeinfo['version']
+ prefix = makeinfo['prefix']
+ package = makeinfo['package']
+ print "version:", makeinfo['version']
+ print "python:", python
+ print "prefix:", prefix
+ print "distdir:", distdir
+
+ revision = getGitInfo(makeinfo['srcdir'])
+ opSys = platform.system().lower()
+ if opSys.startswith("cygwin"):
+ opSys = "win"
+ if opSys=="darwin":
+ arch = opSys + "-" + platform.mac_ver()[0]
+ else:
+ arch = opSys + "-" + (platform.processor() or platform.machine()) # Why does every last detail have to be painful?
+
+ config = Config.readPackingList()
+ if config.packaging is None:
+ sys.exit("ERROR: No packaging configuation.")
+
+ # Make source distribution (also extracted into binary package)
+ archive = distdir + ".tar.gz"
+ taggedArchive = revision + "-" + archive
+ status = os.system("make dist")
+ if status != 0:
+ sys.exit("make: exit %d" % status)
+ os.system("mv " + archive + " " + taggedArchive)
+
+ workdir = os.getcwd()
+ os.chdir(prefix)
+
+ pl = PackingList(config, opSys, python)
+
+ stripBinaries(pl, opSys)
+ rewriteScripts(pl, prefix, opSys)
+ installSource(pl, join(workdir, taggedArchive))
+
+ distdir_arch = distdir + "-" + arch
+ if opSys == "darwin" or opSys == "linux":
+ # No .dmg on Mac for now.
+ os.chdir(workdir)
+ os.system("rm " + distdir_arch)
+ os.system("ln -s " + prefix + " " + distdir_arch)
+
+ # Write packing list to file
+ plfile = open("tar_list", "w")
+ plfile.write('\n'.join([os.path.join(distdir_arch, m) for m in pl.files()]))
+ plfile.close()
+
+ archive = distdir_arch + ".tar.gz"
+ taggedArchive = revision + "-" + archive
+ status = os.system("tar cvzf " + archive + " -T tar_list")
+ if status != 0:
+ sys.exit("tar: exit %d" % status)
+
+ os.system("mv " + archive + " " + taggedArchive)
+ os.system("rm tar_list " + distdir_arch)
+ shutil.rmtree("src", ignore_errors=True)
+
+ elif opSys == "win":
+ stage = cygwin.stageInstallation(prefix, workdir, python, pl)
+ cygwin.createInstaller(python, stage, workdir, name, package, version, pl,
+ revision + "-" + distdir_arch)
+ else:
+ sys.exit("unknown OS: " + opSys)
+
+ return
+
+
+if __name__ == "__main__":
+ mkpkg()
diff --git a/packager/packinglist.cfg b/packager/packinglist.cfg
new file mode 100644
index 0000000..2d84ab8
--- /dev/null
+++ b/packager/packinglist.cfg
@@ -0,0 +1,91 @@
+# -*- cfg -*-
+[packaging]
+
+bin_dirs =
+ bin
+
+lib_dirs =
+ lib
+
+misc_dirs =
+ etc
+ share
+
+files =
+ ./setup.sh
+
+
+strip_list =
+ lib/libpylith
+ lib/libspatialdata
+
+exclude =
+ bin/cpp$
+ bin/c\+\+$
+ bin/gcc$
+ bin/gccbug
+ bin/g\+\+$
+ bin/gcov
+ bin/gfortran$
+ bin/.*-.*-c\+\+.*
+ bin/.*-.*-g\+\+.*
+ bin/.*-.*-gcc.*
+ bin/.*-.*-gfortran.*
+ bin/mpicc
+ bin/mpicxx
+ bin/mpic\+\+
+ bin/mpif77
+ bin/mpif90
+ bin/TOPSGenerator\.py
+ bin/TOPSInstaller\.py
+ bin/adiforfix\.py
+ bin/adprocess\.py
+ bin/2to3
+ bin/bfort
+ bin/bib2html
+ bin/bsp_virtual
+ bin/configVars\.py
+ bin/doc2lt
+ bin/doctext
+ bin/f2py
+ bin/maint/.*
+ bin/matio\.py
+ bin/matlab/.*
+ bin/parseargs\.py
+ bin/petsc_libtool
+ bin/petscmpiexec
+ bin/petscrun
+ bin/popup
+ bin/portabilitycheck\.py
+ bin/processSummary\.py
+ bin/pstogif
+ bin/pstoxbm
+ bin/task_manager
+ bin/taucc\.py
+ bin/tohtml
+ bin/update\.py
+ bin/urlget
+ bin/urlget\.py
+ bin/win32fe/.*
+ share/man/man1/cpp\.1
+ share/man/man1/g\+\+\.1
+ share/man/man1/gcc\.1
+ share/man/man1/gfortran\.1
+ share/man/man3/.*
+ share/info/.*
+ share/doc/.*
+ lib/.*\.a
+ lib/gcc/.*-.*/.*
+
+scripts =
+ pylith
+ pylithinfo
+ pylith_genxdmf
+
+# pyconvert.py
+# gensimpledb.py
+# powerlaw_gendb.py
+
+
+
+
More information about the CIG-COMMITS
mailing list