def build_binaries(TARGETS, COMPILER, V_MAJOR, FILES, DEST): from functools import partial as func_partial CmdClass = COMPILER.CmdClass def fix_dirsep(path, target): if not is_win32 and target.iswin: # Wine needs Windows-style paths. path = path.replace(Path.sep, r"\\") return path if not is_win32 and any(t.iswin for t in TARGETS) and \ not locate_command("wine"): print("Warning: cannot build Windows binaries: 'wine' is not in PATH.") TARGETS = [t for t in TARGETS if not t.iswin] # Create a curried build function with common parameters. build_binary = func_partial(build_dil, CmdClass, FILES, exe=COMPILER, versions=["D" + V_MAJOR]) BINS = [] # Successfully compiled binaries. for target in TARGETS: print("== Building {name} {bits}bit binary ==".format(**target)) dbgargs = rlsargs = {"m%d" % target.bits: True} if target.iswin: dbgargs = rlsargs = dict(rlsargs, wine=not is_win32) if target.islin: dbgargs = dict(rlsargs, lnk_args=["-ltango-dmd", "-lphobos2", "-ldl"]) # Destination dir for the binary. B = (DEST / target.dir / "bin%d" % target.bits).mkdir() SFX = "" # An optional suffix. Empty for now. DBGEXE, RLSEXE = (B / target[exe] % SFX for exe in ("dbgexe", "rlsexe")) dbgargs.update(debug_info=True) build_binary(fix_dirsep(DBGEXE, target), **dbgargs) # NB: the -inline switch makes the binaries significantly larger on Linux. # Enable inlining when DMDBUG #7967 is fixed. rlsargs.update(release=True, optimize=True, inline=False) build_binary(fix_dirsep(RLSEXE, target), **rlsargs) DBGEXE.target = RLSEXE.target = target BINS += [exe for exe in (DBGEXE, RLSEXE) if exe.exists] return BINS
def build_binaries(TARGETS, COMPILER, V_MAJOR, FILES, DEST): from functools import partial as func_partial CmdClass = COMPILER.CmdClass def fix_dirsep(path, target): if not is_win32 and target.iswin: # Wine needs Windows-style paths. path = path.replace(Path.sep, r"\\") return path if not is_win32 and any(t.iswin for t in TARGETS) and \ not locate_command("wine"): print("Warning: cannot build Windows binaries: 'wine' is not in PATH.") TARGETS = [t for t in TARGETS if not t.iswin] # Create a curried build function with common parameters. build_binary = func_partial(build_dil, CmdClass, FILES, exe=COMPILER, versions=["D"+V_MAJOR]) BINS = [] # Successfully compiled binaries. for target in TARGETS: print("== Building {name} {bits}bit binary ==".format(**target)) dbgargs = rlsargs = {"m%d" % target.bits : True} if target.iswin: dbgargs = rlsargs = dict(rlsargs, wine=not is_win32) if target.islin: dbgargs = dict(rlsargs, lnk_args=["-ltango-dmd", "-lphobos2", "-ldl"]) # Destination dir for the binary. B = (DEST/target.dir/"bin%d"%target.bits).mkdir() SFX = "" # An optional suffix. Empty for now. DBGEXE, RLSEXE = (B/target[exe] % SFX for exe in ("dbgexe", "rlsexe")) dbgargs.update(debug_info=True) build_binary(fix_dirsep(DBGEXE, target), **dbgargs) # NB: the -inline switch makes the binaries significantly larger on Linux. # Enable inlining when DMDBUG #7967 is fixed. rlsargs.update(release=True, optimize=True, inline=False) build_binary(fix_dirsep(RLSEXE, target), **rlsargs) DBGEXE.target = RLSEXE.target = target BINS += [exe for exe in (DBGEXE, RLSEXE) if exe.exists] return BINS
def init(cback): global callback, labels, win, is_open callback = cback is_open = False win = Toplevel(TK_ROOT) win.title("BEE2") win.resizable(False, False) tk_tools.set_window_icon(win) win.protocol("WM_DELETE_WINDOW", exit_win) win.transient(TK_ROOT) win.withdraw() if utils.MAC: # Switch to use the 'modal' window style on Mac. TK_ROOT.call('::tk::unsupported::MacWindowStyle', 'style', win, 'moveableModal', '') # Stop our init from triggering UI sounds. sound.block_fx() frame = ttk.Frame(win, padding=10) frame.grid(row=0, column=0, sticky='NSEW') frame.rowconfigure(0, weight=1) frame.columnconfigure(0, weight=1) labels['noOptions'] = ttk.Label(frame, text=_('No Properties available!')) widgets['saveButton'] = ttk.Button(frame, text=_('Close'), command=exit_win) widgets['titleLabel'] = ttk.Label(frame, text='') widgets['titleLabel'].grid(columnspan=9) widgets['div_1'] = ttk.Separator(frame, orient="vertical") widgets['div_2'] = ttk.Separator(frame, orient="vertical") widgets['div_h'] = ttk.Separator(frame, orient="horizontal") for key, (prop_type, prop_name) in PROP_TYPES.items(): # Translate property names from Valve's files. if prop_name.startswith('PORTAL2_'): prop_name = gameMan.translate(prop_name) + ':' labels[key] = ttk.Label(frame, text=prop_name) if prop_type is PropTypes.CHECKBOX: values[key] = IntVar(value=DEFAULTS[key]) out_values[key] = srctools.bool_as_int(DEFAULTS[key]) widgets[key] = ttk.Checkbutton( frame, variable=values[key], command=func_partial(set_check, key), ) widgets[key].bind('<Return>', func_partial( toggleCheck, key, values[key], )) elif prop_type is PropTypes.OSCILLATE: values[key] = IntVar(value=DEFAULTS[key]) out_values[key] = srctools.bool_as_int(DEFAULTS[key]) widgets[key] = ttk.Checkbutton( frame, variable=values[key], command=func_partial(save_rail, key), ) elif prop_type is PropTypes.PANEL: frm = ttk.Frame(frame) widgets[key] = frm values[key] = StringVar(value=DEFAULTS[key]) for pos, (angle, disp_angle) in enumerate(PANEL_ANGLES): ttk.Radiobutton( frm, variable=values[key], value=angle, text=gameMan.translate(disp_angle), command=func_partial(save_angle, key, angle), ).grid(row=0, column=pos) frm.columnconfigure(pos, weight=1) elif prop_type is PropTypes.GELS: frm = ttk.Frame(frame) widgets[key] = frm values[key] = IntVar(value=DEFAULTS[key]) for pos, text in enumerate(PAINT_OPTS): ttk.Radiobutton( frm, variable=values[key], value=pos, text=gameMan.translate(text), command=func_partial(save_paint, key, pos), ).grid(row=0, column=pos) frm.columnconfigure(pos, weight=1) out_values[key] = str(DEFAULTS[key]) elif prop_type is PropTypes.PISTON: widgets[key] = pist_scale = ttk.Scale( frame, from_=0, to=4, orient="horizontal", command=func_partial(save_pist, key), ) values[key] = DEFAULTS[key] out_values[key] = str(DEFAULTS[key]) if ((key == 'toplevel' and DEFAULTS['startup']) or (key == 'bottomlevel' and not DEFAULTS['startup'])): pist_scale.set( max(DEFAULTS['toplevel'], DEFAULTS['bottomlevel'])) if ((key == 'toplevel' and not DEFAULTS['startup']) or (key == 'bottomlevel' and DEFAULTS['startup'])): pist_scale.set( min(DEFAULTS['toplevel'], DEFAULTS['bottomlevel'])) elif prop_type is PropTypes.TIMER: widgets[key] = ttk.Scale( frame, from_=0, to=30, orient="horizontal", command=func_partial(save_tim, key), ) values[key] = DEFAULTS[key] values['startup'] = DEFAULTS['startup']
def init(cback): global callback, labels, win, is_open callback = cback is_open = False win = Toplevel(TK_ROOT) win.title("BEE2") win.resizable(False, False) win.iconbitmap('../BEE2.ico') win.protocol("WM_DELETE_WINDOW", exit_win) win.withdraw() labels['noOptions'] = ttk.Label(win, text='No Properties avalible!') widgets['saveButton'] = ttk.Button(win, text='Close', command=exit_win) widgets['titleLabel'] = ttk.Label(win, text='') widgets['titleLabel'].grid(columnspan=9) widgets['div_1'] = ttk.Separator(win, orient="vertical") widgets['div_2'] = ttk.Separator(win, orient="vertical") widgets['div_h'] = ttk.Separator(win, orient="horizontal") for key, (prop_type, prop_name) in PROP_TYPES.items(): labels[key] = ttk.Label(win, text=prop_name + ':') if prop_type == 'checkbox': values[key] = IntVar(value=DEFAULTS[key]) out_values[key] = utils.bool_as_int(DEFAULTS[key]) widgets[key] = ttk.Checkbutton( win, variable=values[key], command=func_partial(set_check, key), ) widgets[key].bind('<Return>', func_partial( toggleCheck, key, values[key], )) elif prop_type == 'railLift': values[key] = IntVar(value=DEFAULTS[key]) out_values[key] = utils.bool_as_int(DEFAULTS[key]) widgets[key] = ttk.Checkbutton( win, variable=values[key], command=func_partial(save_rail, key), ) elif prop_type == 'panAngle': frm = ttk.Frame(win) widgets[key] = frm values[key] = StringVar(value=DEFAULTS[key]) for pos, angle in enumerate(['30', '45', '60', '90']): ttk.Radiobutton( frm, variable=values[key], value=angle, text=angle, command=func_partial(save_angle, key, angle), ).grid(row=0, column=pos) frm.columnconfigure(pos, weight=1) elif prop_type == 'gelType': frm = ttk.Frame(win) widgets[key] = frm values[key] = IntVar(value=DEFAULTS[key]) for pos, text in enumerate(PAINT_OPTS): ttk.Radiobutton( frm, variable=values[key], value=pos, text=text, command=func_partial(save_paint, key, pos), ).grid(row=0, column=pos) frm.columnconfigure(pos, weight=1) out_values[key] = str(DEFAULTS[key]) elif prop_type == 'pistPlat': widgets[key] = Scale( win, from_=0, to=4, orient="horizontal", showvalue=False, command=func_partial(save_pist, key), ) values[key] = DEFAULTS[key] out_values[key] = str(DEFAULTS[key]) if ((key == 'toplevel' and DEFAULTS['startup']) or (key == 'bottomlevel' and not DEFAULTS['startup'])): widgets[key].set( max(DEFAULTS['toplevel'], DEFAULTS['bottomlevel'])) if ((key == 'toplevel' and not DEFAULTS['startup']) or (key == 'bottomlevel' and DEFAULTS['startup'])): widgets[key].set( min(DEFAULTS['toplevel'], DEFAULTS['bottomlevel'])) elif prop_type == 'timerDel': widgets[key] = ttk.Scale( win, from_=0, to=30, orient="horizontal", command=func_partial(save_tim, key), ) values[key] = DEFAULTS[key] elif prop_type == 'railPlat': widgets[key] = ttk.Checkbutton(win) values['startup'] = DEFAULTS['startup']
def main(): from functools import partial as func_partial from argparse import ArgumentParser, SUPPRESS parser = ArgumentParser() addarg = parser.add_argument addflag = func_partial(addarg, action="store_true") addarg("version", metavar="VERSION", nargs=1, help="the version to be released") addflag("-s", "--dsymbols", dest="debug_symbols", help="generate debug symbols for debug builds") addflag("-d", "--docs", dest="docs", help="generate documentation") addflag("-n", "--no-bin", dest="no_binaries", help="don't compile code") addflag("--7z", dest="_7z", help="create a 7z archive") addflag("--gz", dest="tar_gz", help="create a tar.gz archive") addflag("--bz2", dest="tar_bz2", help="create a tar.bz2 archive") addflag("--zip", dest="zip", help="create a zip archive") addflag("--deb", dest="deb", help="create deb files") addflag("--pdf", dest="pdf", help="create a PDF document") addflag("--chm", dest="chm", help=SUPPRESS) # "create a CHM file" addflag("-m", dest="copy_modified", help="copy modified files from the (git) working directory") addflag("--ldc", dest="ldc", help="use ldc instead of dmd") addarg("--src", dest="src", metavar="SRC", help="use SRC folder instead of checking out code with git") addarg("--cmp-exe", dest="cmp_exe", metavar="EXE_PATH", help="specify EXE_PATH if dmd/ldc is not in your PATH") addarg("--builddir", dest="builddir", metavar="DIR", help="where to build the release and archives (default is build/)") addarg( "--winpath", dest="winpath", metavar="P", help="permanently append P to PATH in the Windows (or wine's) registry. " "Exits the script.") addarg("--debm", dest="deb_mntnr", metavar="MTR", help=SUPPRESS) # Sets the maintainer info of the package. addarg("--debnum", dest="deb_num", metavar="NUM", default=1, help=SUPPRESS) # Sets the package number. options = args = parser.parse_args(sys.uargv[1:]) if options.winpath != None: from env_path import append2PATH append2PATH(options.winpath) return change_cwd(__file__) # Validate the version argument. m = re.match(r"^((\d)\.(\d{3})(?:-(\w+))?)(?:\+(\w+))?$", args.version) if not m: parser.error("invalid VERSION format: /\d.\d\d\d(-\w+)?/ E.g.: 1.123") # The version of DIL to be built. class Version(unicode): def __new__(cls, parts): v = unicode.__new__(cls, parts[0]) v.MAJ, v.MIN, SFX, BSFX = parts[1:] v.SFX = SFX or '' v.BINSFX = BSFX or '' return v VERSION = Version(m.groups()) # Pick a compiler for compiling DIL. CmdClass = (DMDCommand, LDCCommand)[options.ldc] COMPILER = Path(options.cmp_exe or CmdClass.exe) COMPILER.CmdClass = CmdClass if not COMPILER.exists and not locate_command(COMPILER): parser.error("The executable '%s' could not be located." % COMPILER) # Path to DIL's root folder. DIL = dil_path() # Build folder. BUILDROOT = Path(options.builddir or "build") / ("dil_" + VERSION) # Destination of distributable files. DEST = dil_path(BUILDROOT / "dil", dilconf=False) DEST.DOC = doc_path(DEST.DOC) # Temporary directory, deleted in the end. TMP = BUILDROOT / "tmp" # The list of module files (with info) that have been processed. MODLIST = TMP / "modules.txt" # The source files that need to be compiled and documentation generated for. FILES = [] # The folders and files which were produced by a build. PRODUCED = [] sw, sw_all = StopWatch(), StopWatch() # Check out a new working copy. BUILDROOT.rm().mkdir() # First remove the whole folder and recreate it. if options.src != None: # Use the source folder specified by the user. src = Path(options.src) if not src.exists: parser.error("the given SRC path (%s) doesn't exist" % src) #if src.ext in ('zip', 'gz', 'bz2'): # TODO: src.copy(DEST) else: if not locate_command('git'): parser.error("'git' is not in your PATH; specify --src instead") if not locate_command('tar'): parser.error("program 'tar' is not in your PATH") # Use git to checkout a clean copy. DEST.mkdir() TARFILE = DEST / "dil.tar" call_proc("git", "archive", "-o", TARFILE, "HEAD") call_proc("tar", "-xf", TARFILE.name, cwd=DEST) TARFILE.rm() if options.copy_modified: modified_files = call_read("git", "ls-files", "-m")[:-1] if modified_files != "": for f in modified_files.split("\n"): Path(f).copy(DEST / f) # Create other directories not available in a clean checkout. DOC = DEST.DOC Paths(DOC.HTMLSRC, DOC.CSS, DOC.IMG, DOC.JS, TMP).mkdirs() # Rebuild the path object for kandil. (Images are globbed.) DEST.KANDIL = kandil_path(DEST / "kandil") print("== Copying files ==") copy_files(DEST) # Find the source code files. FILES = find_dil_source_files(DEST.SRC) # Update the version info. update_VERSION(DEST.SRC / "dil" / "Version.d", VERSION) write_VERSION(VERSION, DEST) if options.docs: build_dil_if_inexistant(DIL.EXE) print("== Generating documentation ==") DOC_FILES = DEST.DATA / ("macros_dil.ddoc", "dilconf.d") + FILES versions = ["DDoc"] generate_docs(DIL.EXE, DEST.DOC, MODLIST, DOC_FILES, versions, options=['-v', '-i', '-hl', '--kandil']) if options.pdf: write_PDF(DEST, DEST.DOC, VERSION, TMP) #if options.chm: #write_CHM(DEST, DEST.DOC, VERSION, TMP) TARGETS = [Targets[n] for n in ("Lin32", "Lin64", "Win32")] if not options.no_binaries: BINS = build_binaries(TARGETS, COMPILER, VERSION.MAJ, FILES, DEST) for bin in BINS: (DIL.DATA / "dilconf.d").copy(bin.folder) PRODUCED += [(DEST.abspath, sw.stop())] # Remove unneeded directories. options.docs or DEST.DOC.rm() # Build archives. assert DEST[-1] != Path.sep create_archives(options, DEST.name, DEST.name, DEST.folder) if options.deb and not options.no_binaries: MTR = get_MAINTAINER(options.deb_mntnr) NUM = int(options.deb_num) # Make an archive for each architecture. SRC = Path(DEST) SRC.DATA = DEST.DATA SRC.DOC = DEST.DOC LINUX_BINS = [bin for bin in BINS if bin.target.islin] for arch in ("i386", "amd64"): # Gather the binaries that belong to arch. SRC.BINS = [bin for bin in LINUX_BINS if bin.target.arch == arch] sw.start() DEB = make_deb_package(SRC, DEST.folder, VERSION, arch, DEST, MTR, NUM) PRODUCED += [(DEB.abspath, sw.stop())] if not options.no_binaries: # Make an arch-independent folder. NOARCH = TMP / "dil_noarch" DEST.copy(NOARCH) (NOARCH / ("linux", "windows")).rm() # Linux: for bits in (32, 64): BIN = DEST / "linux" / "bin%d" % bits if not BIN.exists: continue SRC = (TMP / "dil_" + VERSION).rm() # Clear if necessary. NOARCH.copy(SRC) BIN.copy(SRC / "bin") write_modified_dilconf(SRC / "data" / "dilconf.d", SRC / "bin" / "dilconf.d", Path("${BINDIR}") / ".." / "data") NAME = BUILDROOT.abspath / "dil_%s_linux%s" % (VERSION, bits) for ext in (".7z", ".tar.xz"): sw.start() make_archive(SRC, NAME + ext) PRODUCED += [(NAME + ext, sw.stop())] SRC.rm() # Windows: for bits in (32, 64): if bits != 32: continue # Only 32bit supported atm. BIN = DEST / "windows" / "bin%d" % bits if not BIN.exists: continue SRC = (TMP / "dil_" + VERSION).rm() # Clear if necessary. NOARCH.copy(SRC) BIN.copy(SRC / "bin") write_modified_dilconf(SRC / "data" / "dilconf.d", SRC / "bin" / "dilconf.d", Path("${BINDIR}") / ".." / "data") NAME = BUILDROOT.abspath / "dil_%s_win%s" % (VERSION, bits) for ext in (".7z", ".zip"): sw.start() make_archive(SRC, NAME + ext) PRODUCED += [(NAME + ext, sw.stop())] SRC.rm() NOARCH.rm() # All platforms: NAME = BUILDROOT.abspath / "dil_%s_all" % VERSION for ext in (".7z", ".zip", ".tar.xz"): sw.start() make_archive(DEST, NAME + ext) PRODUCED += [(NAME + ext, sw.stop())] TMP.rm() if PRODUCED: print("\nProduced files/folders:") for x, sec in PRODUCED: if Path(x).exists: print(x + " (%.2fs)" % sec) print() print("Finished in %.2fs!" % sw_all.stop())
def init(cback): global callback, labels, win, is_open callback = cback is_open = False win = Toplevel(TK_ROOT) win.title("BEE2") win.resizable(False, False) win.iconbitmap('../BEE2.ico') win.protocol("WM_DELETE_WINDOW", exit_win) win.withdraw() labels['noOptions'] = ttk.Label(win, text='No Properties avalible!') widgets['saveButton'] = ttk.Button(win, text='Close', command=exit_win) widgets['titleLabel'] = ttk.Label(win, text='') widgets['titleLabel'].grid(columnspan=9) widgets['div_1'] = ttk.Separator(win, orient="vertical") widgets['div_2'] = ttk.Separator(win, orient="vertical") widgets['div_h'] = ttk.Separator(win, orient="horizontal") for key, (prop_type, prop_name) in PROP_TYPES.items(): labels[key] = ttk.Label(win, text=prop_name+':') if prop_type == 'checkbox': values[key] = IntVar(value=DEFAULTS[key]) out_values[key] = utils.bool_as_int(DEFAULTS[key]) widgets[key] = ttk.Checkbutton( win, variable=values[key], command=func_partial(set_check, key), ) widgets[key].bind( '<Return>', func_partial( toggleCheck, key, values[key], ) ) elif prop_type == 'railLift': values[key] = IntVar(value=DEFAULTS[key]) out_values[key] = utils.bool_as_int(DEFAULTS[key]) widgets[key] = ttk.Checkbutton( win, variable=values[key], command=func_partial(save_rail, key), ) elif prop_type == 'panAngle': frm = ttk.Frame(win) widgets[key] = frm values[key] = StringVar(value=DEFAULTS[key]) for pos, angle in enumerate(['30', '45', '60', '90']): ttk.Radiobutton( frm, variable=values[key], value=angle, text=angle, command=func_partial(save_angle, key, angle), ).grid(row=0, column=pos) frm.columnconfigure(pos, weight=1) elif prop_type == 'gelType': frm = ttk.Frame(win) widgets[key] = frm values[key] = IntVar(value=DEFAULTS[key]) for pos, text in enumerate(PAINT_OPTS): ttk.Radiobutton( frm, variable=values[key], value=pos, text=text, command=func_partial(save_paint, key, pos), ).grid(row=0, column=pos) frm.columnconfigure(pos, weight=1) out_values[key] = str(DEFAULTS[key]) elif prop_type == 'pistPlat': widgets[key] = Scale( win, from_=0, to=4, orient="horizontal", showvalue=False, command=func_partial(save_pist, key), ) values[key] = DEFAULTS[key] out_values[key] = str(DEFAULTS[key]) if ((key == 'toplevel' and DEFAULTS['startup']) or (key == 'bottomlevel' and not DEFAULTS['startup'])): widgets[key].set(max( DEFAULTS['toplevel'], DEFAULTS['bottomlevel'] )) if ((key == 'toplevel' and not DEFAULTS['startup']) or (key == 'bottomlevel' and DEFAULTS['startup'])): widgets[key].set(min( DEFAULTS['toplevel'], DEFAULTS['bottomlevel'])) elif prop_type == 'timerDel': widgets[key] = ttk.Scale( win, from_=0, to=30, orient="horizontal", command=func_partial(save_tim, key), ) values[key] = DEFAULTS[key] elif prop_type == 'railPlat': widgets[key] = ttk.Checkbutton(win) values['startup'] = DEFAULTS['startup']
def main(): from functools import partial as func_partial from argparse import ArgumentParser, SUPPRESS parser = ArgumentParser() addarg = parser.add_argument addflag = func_partial(addarg, action="store_true") addarg("version", metavar="VERSION", nargs=1, help="the version to be released") addflag("-s", "--dsymbols", dest="debug_symbols", help="generate debug symbols for debug builds") addflag("-d", "--docs", dest="docs", help="generate documentation") addflag("-n", "--no-bin", dest="no_binaries", help="don't compile code") addflag("--7z", dest="_7z", help="create a 7z archive") addflag("--gz", dest="tar_gz", help="create a tar.gz archive") addflag("--bz2", dest="tar_bz2", help="create a tar.bz2 archive") addflag("--zip", dest="zip", help="create a zip archive") addflag("--deb", dest="deb", help="create deb files") addflag("--pdf", dest="pdf", help="create a PDF document") addflag("--chm", dest="chm", help=SUPPRESS) # "create a CHM file" addflag("-m", dest="copy_modified", help="copy modified files from the (git) working directory") addflag("--ldc", dest="ldc", help="use ldc instead of dmd") addarg("--src", dest="src", metavar="SRC", help="use SRC folder instead of checking out code with git") addarg("--cmp-exe", dest="cmp_exe", metavar="EXE_PATH", help="specify EXE_PATH if dmd/ldc is not in your PATH") addarg("--builddir", dest="builddir", metavar="DIR", help="where to build the release and archives (default is build/)") addarg("--winpath", dest="winpath", metavar="P", help="permanently append P to PATH in the Windows (or wine's) registry. " "Exits the script.") addarg("--debm", dest="deb_mntnr", metavar="MTR", help=SUPPRESS) # Sets the maintainer info of the package. addarg("--debnum", dest="deb_num", metavar="NUM", default=1, help=SUPPRESS) # Sets the package number. options = args = parser.parse_args(sys.uargv[1:]) if options.winpath != None: from env_path import append2PATH append2PATH(options.winpath) return change_cwd(__file__) # Validate the version argument. m = re.match(r"^((\d)\.(\d{3})(?:-(\w+))?)(?:\+(\w+))?$", args.version) if not m: parser.error("invalid VERSION format: /\d.\d\d\d(-\w+)?/ E.g.: 1.123") # The version of DIL to be built. class Version(unicode): def __new__(cls, parts): v = unicode.__new__(cls, parts[0]) v.MAJ, v.MIN, SFX, BSFX = parts[1:] v.SFX = SFX or '' v.BINSFX = BSFX or '' return v VERSION = Version(m.groups()) # Pick a compiler for compiling DIL. CmdClass = (DMDCommand, LDCCommand)[options.ldc] COMPILER = Path(options.cmp_exe or CmdClass.exe) COMPILER.CmdClass = CmdClass if not COMPILER.exists and not locate_command(COMPILER): parser.error("The executable '%s' could not be located." % COMPILER) # Path to DIL's root folder. DIL = dil_path() # Build folder. BUILDROOT = Path(options.builddir or "build")/("dil_"+VERSION) # Destination of distributable files. DEST = dil_path(BUILDROOT/"dil", dilconf=False) DEST.DOC = doc_path(DEST.DOC) # Temporary directory, deleted in the end. TMP = BUILDROOT/"tmp" # The list of module files (with info) that have been processed. MODLIST = TMP/"modules.txt" # The source files that need to be compiled and documentation generated for. FILES = [] # The folders and files which were produced by a build. PRODUCED = [] sw, sw_all = StopWatch(), StopWatch() # Check out a new working copy. BUILDROOT.rm().mkdir() # First remove the whole folder and recreate it. if options.src != None: # Use the source folder specified by the user. src = Path(options.src) if not src.exists: parser.error("the given SRC path (%s) doesn't exist" % src) #if src.ext in ('zip', 'gz', 'bz2'): # TODO: src.copy(DEST) else: if not locate_command('git'): parser.error("'git' is not in your PATH; specify --src instead") if not locate_command('tar'): parser.error("program 'tar' is not in your PATH") # Use git to checkout a clean copy. DEST.mkdir() TARFILE = DEST/"dil.tar" call_proc("git", "archive", "-o", TARFILE, "HEAD") call_proc("tar", "-xf", TARFILE.name, cwd=DEST) TARFILE.rm() if options.copy_modified: modified_files = call_read("git", "ls-files", "-m")[:-1] if modified_files != "": for f in modified_files.split("\n"): Path(f).copy(DEST/f) # Create other directories not available in a clean checkout. DOC = DEST.DOC Paths(DOC.HTMLSRC, DOC.CSS, DOC.IMG, DOC.JS, TMP).mkdirs() # Rebuild the path object for kandil. (Images are globbed.) DEST.KANDIL = kandil_path(DEST/"kandil") print("== Copying files ==") copy_files(DEST) # Find the source code files. FILES = find_dil_source_files(DEST.SRC) # Update the version info. update_VERSION(DEST.SRC/"dil"/"Version.d", VERSION) write_VERSION(VERSION, DEST) if options.docs: build_dil_if_inexistant(DIL.EXE) print("== Generating documentation ==") DOC_FILES = DEST.DATA/("macros_dil.ddoc", "dilconf.d") + FILES versions = ["DDoc"] generate_docs(DIL.EXE, DEST.DOC, MODLIST, DOC_FILES, versions, options=['-v', '-i', '-hl', '--kandil']) if options.pdf: write_PDF(DEST, DEST.DOC, VERSION, TMP) #if options.chm: #write_CHM(DEST, DEST.DOC, VERSION, TMP) TARGETS = [Targets[n] for n in ("Lin32", "Lin64", "Win32")] if not options.no_binaries: BINS = build_binaries(TARGETS, COMPILER, VERSION.MAJ, FILES, DEST) for bin in BINS: (DIL.DATA/"dilconf.d").copy(bin.folder) PRODUCED += [(DEST.abspath, sw.stop())] # Remove unneeded directories. options.docs or DEST.DOC.rm() # Build archives. assert DEST[-1] != Path.sep create_archives(options, DEST.name, DEST.name, DEST.folder) if options.deb and not options.no_binaries: MTR = get_MAINTAINER(options.deb_mntnr) NUM = int(options.deb_num) # Make an archive for each architecture. SRC = Path(DEST) SRC.DATA = DEST.DATA SRC.DOC = DEST.DOC LINUX_BINS = [bin for bin in BINS if bin.target.islin] for arch in ("i386", "amd64"): # Gather the binaries that belong to arch. SRC.BINS = [bin for bin in LINUX_BINS if bin.target.arch == arch] sw.start() DEB = make_deb_package(SRC, DEST.folder, VERSION, arch, DEST, MTR, NUM) PRODUCED += [(DEB.abspath, sw.stop())] if not options.no_binaries: # Make an arch-independent folder. NOARCH = TMP/"dil_noarch" DEST.copy(NOARCH) (NOARCH/("linux", "windows")).rm() # Linux: for bits in (32, 64): BIN = DEST/"linux"/"bin%d"%bits if not BIN.exists: continue SRC = (TMP/"dil_"+VERSION).rm() # Clear if necessary. NOARCH.copy(SRC) BIN.copy(SRC/"bin") write_modified_dilconf(SRC/"data"/"dilconf.d", SRC/"bin"/"dilconf.d", Path("${BINDIR}")/".."/"data") NAME = BUILDROOT.abspath/"dil_%s_linux%s" % (VERSION, bits) for ext in (".7z", ".tar.xz"): sw.start() make_archive(SRC, NAME+ext) PRODUCED += [(NAME+ext, sw.stop())] SRC.rm() # Windows: for bits in (32, 64): if bits != 32: continue # Only 32bit supported atm. BIN = DEST/"windows"/"bin%d"%bits if not BIN.exists: continue SRC = (TMP/"dil_"+VERSION).rm() # Clear if necessary. NOARCH.copy(SRC) BIN.copy(SRC/"bin") write_modified_dilconf(SRC/"data"/"dilconf.d", SRC/"bin"/"dilconf.d", Path("${BINDIR}")/".."/"data") NAME = BUILDROOT.abspath/"dil_%s_win%s" % (VERSION, bits) for ext in (".7z", ".zip"): sw.start() make_archive(SRC, NAME+ext) PRODUCED += [(NAME+ext, sw.stop())] SRC.rm() NOARCH.rm() # All platforms: NAME = BUILDROOT.abspath/"dil_%s_all" % VERSION for ext in (".7z", ".zip", ".tar.xz"): sw.start() make_archive(DEST, NAME+ext) PRODUCED += [(NAME+ext, sw.stop())] TMP.rm() if PRODUCED: print("\nProduced files/folders:") for x, sec in PRODUCED: if Path(x).exists: print(x+" (%.2fs)"%sec) print() print("Finished in %.2fs!" % sw_all.stop())
def main(): from functools import partial as func_partial from optparse import OptionParser usage = "Usage: %s VERSION [Options]" % __file__ parser = OptionParser(usage=usage) add_option = func_partial(parser.add_option, action="store_true", default=False) add_option("-s", "--dsymbols", dest="debug_symbols", help="generate debug symbols for debug builds") add_option("-d", "--docs", dest="docs", help="generate documentation") add_option("-n", "--no-bin", dest="no_binaries", help="don't compile code") add_option("--7z", dest="_7z", help="create a 7z archive") add_option("--gz", dest="tar_gz", help="create a tar.gz archive") add_option("--bz2", dest="tar_bz2", help="create a tar.bz2 archive") add_option("--zip", dest="zip", help="create a zip archive") add_option("--pdf", dest="pdf", help="create a PDF document") #add_option("--chm", dest="chm", help="create a CHM file") add_option("-m", dest="copy_modified", help="copy modified files from the (git) working directory") parser.add_option("--src", dest="src", metavar="SRC", default=None, help="use SRC folder instead of checking out code with git") parser.add_option("--cmp-exe", dest="cmp_exe", metavar="EXE_PATH", help="specify EXE_PATH if dmd/ldc is not in your PATH") add_option("--ldc", dest="ldc", help="use ldc instead of dmd") parser.add_option("--builddir", dest="builddir", metavar="DIR", default=None, help="where to build the release and archives (default is build/)") parser.add_option("--winpath", dest="winpath", metavar="P", default=None, help="permanently append P to PATH in the Windows (or wine's) registry. " "Exits the script.") (options, args) = parser.parse_args(sys.uargv[1:]) if options.winpath != None: from env_path import append2PATH append2PATH(options.winpath, Path("")) return if len(args) < 1: return parser.print_help() if len(args) > 1: print("Warning! Arguments ignored: " + " ".join(args[1:])) change_cwd(__file__) # Validate the version argument. m = re.match(r"((\d)\.(\d\d\d)(-\w+)?)", args[0]) if not m: parser.error("invalid VERSION; format: /\d.\d\d\d(-\w+)?/ E.g.: 1.123") # The version of DIL to be built. VERSION, V_MAJOR, V_MINOR, V_SUFFIX = m.groups() V_SUFFIX = V_SUFFIX or '' # Pick a compiler for compiling DIL. CmdClass = (DMDCommand, LDCCommand)[options.ldc] COMPILER = Path(options.cmp_exe if options.cmp_exe else CmdClass.cmd) COMPILER.cmd = CmdClass if not COMPILER.exists and not locate_command(COMPILER): parser.error("The executable '%s' couldn't be located or does not exist." % COMPILER) # Path to DIL's root folder. DIL = dil_path() # Build folder. BUILD_DIR = Path(options.builddir or "build") # Destination of distributable files. DEST = dil_path(BUILD_DIR/("dil."+VERSION), dilconf=False) BIN = DEST.BIN # Shortcut to the bin/ folder. DEST.DOC = doc_path(DEST.DOC) # Temporary directory, deleted in the end. TMP = DEST/"tmp" # The list of module files (with info) that have been processed. MODLIST = TMP/"modules.txt" # The files to generate documentation for. FILES = [] # Create the build directory. BUILD_DIR.makedirs() # Check out a new working copy. DEST.rmtree() # First remove the tree. if options.src != None: # Use the source folder specified by the user. src = Path(options.src) if not src.exists: parser.error("the given SRC path (%s) doesn't exist" % src) #if src.ext in ('.zip', '.gz', 'bz2'): # TODO: src.copytree(DEST) elif locate_command('git'): # Use git to checkout a clean copy. DEST.mkdir() TARFILE = DEST/"dil.tar" subprocess.call(["git", "archive", "-o", TARFILE, "HEAD"]) subprocess.call(["tar", "-xf", TARFILE.name], cwd=DEST) TARFILE.rm() if options.copy_modified: modified_files = call_read(["git", "ls-files", "-m"])[:-1] if modified_files != "": for f in modified_files.split("\n"): Path(f).copy(DEST/f) else: parser.error("git is not in your PATH; specify --src instead") # Create other directories not available in a clean checkout. DOC = DEST.DOC map(Path.mkdir, (DEST.BIN, DOC, DOC.HTMLSRC, DOC.CSS, DOC.IMG, DOC.JS, TMP)) # Rebuild the path object for kandil. (Images are globbed.) DEST.KANDIL = kandil_path(DEST/"kandil") print("***** Copying files *****") copy_files(DEST) # Find the source code files. FILES = find_dil_source_files(DEST.SRC) # Update the version info. VERSION_FILE = DEST.SRC/"dil"/"Version.d" update_version(VERSION_FILE, V_MAJOR, V_MINOR, V_SUFFIX) if options.docs: build_dil_if_inexistant(DIL.EXE) print("***** Generating documentation *****") DOC_FILES = DEST.DATA//("macros_dil.ddoc", "dilconf.d") + FILES versions = ["DDoc"] generate_docs(DIL.EXE, DEST.DOC, MODLIST, DOC_FILES, versions, options=['-v', '-i', '-hl', '--kandil']) if options.pdf: write_PDF(DEST, DEST.DOC, VERSION, TMP) #if options.chm: #write_CHM(DEST, DEST.DOC, VERSION, TMP) COMPILER.use_wine = False use_wine = False if is_win32: build_linux_binaries = False build_windows_binaries = True else: build_linux_binaries = True build_windows_binaries = locate_command("wine") != None class BINPath(Path): def __div__(self, name): """ Converts a Unix path to a Windows path. """ name = Path.__div__(self, name) return name if name.ext != '.exe' else name.replace("/", r"\\") BIN = BINPath(BIN) use_wine = True # Use wine on Linux to build Windows binaries. if not build_windows_binaries: print("Error: can't build windows binaries: " "wine is not installed or not in PATH.") if options.no_binaries: build_linux_binaries = build_windows_binaries = False # Create partial functions with common parameters (aka. currying). # Note: the -inline switch makes the binaries significantly larger on Linux. linker_args = [None] build_dil_rls = func_partial(build_dil, COMPILER, FILES, release=True, optimize=True, inline=True, lnk_args=linker_args) build_dil_dbg = func_partial(build_dil, COMPILER, FILES, debug_info=options.debug_symbols, lnk_args=linker_args) if build_linux_binaries: print("\n***** Building Linux binaries *****\n") linker_args[0] = "-lmpfr" # Linux Debug Binaries build_dil_dbg(BIN/"dil_d") build_dil_dbg(BIN/"dil2_d", versions=["D2"]) # Linux Release Binaries build_dil_rls(BIN/"dil") build_dil_rls(BIN/"dil2", versions=["D2"]) if build_windows_binaries: print("\n***** Building Windows binaries *****\n") COMPILER.use_wine = use_wine linker_args[0] = "+mpfr.lib" # Windows Debug Binaries build_dil_dbg(BIN/"dil_d.exe") build_dil_dbg(BIN/"dil2_d.exe", versions=["D2"]) # Windows Release Binaries build_dil_rls(BIN/"dil.exe") build_dil_rls(BIN/"dil2.exe", versions=["D2"]) options.docs or DEST.DOC.rmtree() TMP.rmtree() # Build archives. assert DEST[-1] != Path.sep create_archives(options, DEST.name, DEST.name, DEST.folder)
def init(cback): global callback, labels, win, is_open callback = cback is_open = False win = Toplevel(TK_ROOT) win.title("BEE2") win.resizable(False, False) tk_tools.set_window_icon(win) win.protocol("WM_DELETE_WINDOW", exit_win) win.transient(TK_ROOT) win.withdraw() if utils.MAC: # Switch to use the 'modal' window style on Mac. TK_ROOT.call( '::tk::unsupported::MacWindowStyle', 'style', win, 'moveableModal', '' ) frame = ttk.Frame(win, padding=10) frame.grid(row=0, column=0, sticky='NSEW') frame.rowconfigure(0, weight=1) frame.columnconfigure(0, weight=1) labels['noOptions'] = ttk.Label(frame, text=_('No Properties available!')) widgets['saveButton'] = ttk.Button(frame, text=_('Close'), command=exit_win) widgets['titleLabel'] = ttk.Label(frame, text='') widgets['titleLabel'].grid(columnspan=9) widgets['div_1'] = ttk.Separator(frame, orient="vertical") widgets['div_2'] = ttk.Separator(frame, orient="vertical") widgets['div_h'] = ttk.Separator(frame, orient="horizontal") for key, (prop_type, prop_name) in PROP_TYPES.items(): # Translate property names from Valve's files. if prop_name.startswith('PORTAL2_'): prop_name = gameMan.translate(prop_name) + ':' labels[key] = ttk.Label(frame, text=prop_name) if prop_type is PropTypes.CHECKBOX: values[key] = IntVar(value=DEFAULTS[key]) out_values[key] = srctools.bool_as_int(DEFAULTS[key]) widgets[key] = ttk.Checkbutton( frame, variable=values[key], command=func_partial(set_check, key), ) widgets[key].bind( '<Return>', func_partial( toggleCheck, key, values[key], ) ) elif prop_type is PropTypes.OSCILLATE: values[key] = IntVar(value=DEFAULTS[key]) out_values[key] = srctools.bool_as_int(DEFAULTS[key]) widgets[key] = ttk.Checkbutton( frame, variable=values[key], command=func_partial(save_rail, key), ) elif prop_type is PropTypes.PANEL: frm = ttk.Frame(frame) widgets[key] = frm values[key] = StringVar(value=DEFAULTS[key]) for pos, (angle, disp_angle) in enumerate(PANEL_ANGLES): ttk.Radiobutton( frm, variable=values[key], value=angle, text=gameMan.translate(disp_angle), command=func_partial(save_angle, key, angle), ).grid(row=0, column=pos) frm.columnconfigure(pos, weight=1) elif prop_type is PropTypes.GELS: frm = ttk.Frame(frame) widgets[key] = frm values[key] = IntVar(value=DEFAULTS[key]) for pos, text in enumerate(PAINT_OPTS): ttk.Radiobutton( frm, variable=values[key], value=pos, text=gameMan.translate(text), command=func_partial(save_paint, key, pos), ).grid(row=0, column=pos) frm.columnconfigure(pos, weight=1) out_values[key] = str(DEFAULTS[key]) elif prop_type is PropTypes.PISTON: widgets[key] = Scale( frame, from_=0, to=4, orient="horizontal", showvalue=False, command=func_partial(save_pist, key), ) values[key] = DEFAULTS[key] out_values[key] = str(DEFAULTS[key]) if ((key == 'toplevel' and DEFAULTS['startup']) or (key == 'bottomlevel' and not DEFAULTS['startup'])): widgets[key].set(max( DEFAULTS['toplevel'], DEFAULTS['bottomlevel'] )) if ((key == 'toplevel' and not DEFAULTS['startup']) or (key == 'bottomlevel' and DEFAULTS['startup'])): widgets[key].set(min( DEFAULTS['toplevel'], DEFAULTS['bottomlevel'])) elif prop_type is PropTypes.TIMER: widgets[key] = ttk.Scale( frame, from_=0, to=30, orient="horizontal", command=func_partial(save_tim, key), ) values[key] = DEFAULTS[key] values['startup'] = DEFAULTS['startup']
def main(): from functools import partial as func_partial from optparse import OptionParser usage = "Usage: scripts/release.py VERSION [Options]" parser = OptionParser(usage=usage) add_option = func_partial(parser.add_option, action="store_true", default=False) add_option("-s", "--dsymbols", dest="debug_symbols", help="generate debug symbols for debug builds") add_option("-d", "--docs", dest="docs", help="generate documentation") add_option("-n", "--no-bin", dest="no_binaries", help="don't compile code") add_option("--7z", dest="_7z", help="create a 7z archive") add_option("--gz", dest="tar_gz", help="create a tar.gz archive") add_option("--bz2", dest="tar_bz2", help="create a tar.bz2 archive") add_option("--zip", dest="zip", help="create a zip archive") add_option("--pdf", dest="pdf", help="create a PDF document") add_option("-m", dest="copy_modified", help="copy modified files from the (git) working directory") parser.add_option("--src", dest="src", metavar="SRC", default=None, help="use SRC folder instead of checking out code with git") parser.add_option("--dmd-exe", dest="dmd_exe", metavar="EXE_PATH", default="dmd", help="specify EXE_PATH if dmd is not in your PATH") parser.add_option("--builddir", dest="builddir", metavar="DIR", default=None, help="where to build the release and archives (default is build/)") parser.add_option("--winpath", dest="winpath", metavar="P", default=None, help="permanently append P to PATH in the Windows (or wine's) registry. " "Exits the script.") (options, args) = parser.parse_args() if options.winpath != None: from env_path import append2PATH append2PATH(options.winpath, Path("")) return if len(args) < 1: return parser.print_help() if len(args) > 1: print "Warning! Arguments ignored: " + " ".join(args[1:]) change_cwd(__file__) # Validate the version argument. m = re.match(r"((\d)\.(\d\d\d)(-\w+)?)", args[0]) if not m: parser.error("invalid VERSION; format: /\d.\d\d\d(-\w+)?/ E.g.: 1.123") matched = m.groups() if not Path(options.dmd_exe).exists and not locate_command(options.dmd_exe): parser.error("The executable '%s' couldn't be located or does not exist." % options.dmd_exe) # Path to dil's root folder. DIL = dil_path() # Name or path to the executable of dmd. DMD_EXE = Path(options.dmd_exe) # The version of dil to be built. VERSION, V_MAJOR = matched[:2] V_MINOR, V_SUFFIX = (matched[2], firstof(str, matched[3], '')) # Build folder. BUILD_DIR = Path(firstof(str, options.builddir, "build")) # Destination of distributable files. DEST = dil_path(BUILD_DIR/("dil."+VERSION), dilconf=False) BIN = DEST.BIN # Shortcut to the bin/ folder. DEST.DOC = doc_path(DEST.DOC) # Temporary directory, deleted in the end. TMP = DEST/"tmp" # The list of module files (with info) that have been processed. MODLIST = TMP/"modules.txt" # The files to generate documentation for. FILES = [] # Create the build directory. BUILD_DIR.makedirs() # Check out a new working copy. DEST.rmtree() # First remove the tree. if options.src != None: # Use the source folder specified by the user. src = Path(options.src) if not src.exists: parser.error("the given SRC path (%s) doesn't exist" % src) #if src.ext in ('.zip', '.gz', 'bz2'): # TODO: src.copytree(DEST) elif locate_command('git'): # Use git to checkout a clean copy. os.system("git clone ./ '%s'" % DEST) (DEST/".git").rmtree() # Remove the .git folder. if options.copy_modified: modified_files = os.popen("git ls-files -m").read()[:-1] if modified_files != "": for f in modified_files.split("\n"): Path(f).copy(DEST/f) else: parser.error("git is not in your PATH; specify --src instead") # Create other directories not available in a clean checkout. DOC = DEST.DOC map(Path.mkdir, (DEST.BIN, DOC, DOC.HTMLSRC, DOC.CSS, DOC.IMG, DOC.JS, TMP)) # Rebuild the path object for kandil. (Images are globbed.) DEST.KANDIL = kandil_path(DEST/"kandil") # Find the source code files. FILES = find_dil_source_files(DEST.SRC) # Update the version info. VERSION_FILE = DEST.SRC/"dil"/"Version.d" update_version(VERSION_FILE, V_MAJOR, V_MINOR, V_SUFFIX) if options.docs: build_dil_if_inexistant(DIL.EXE) DOC_FILES = [DEST.KANDIL.ddoc] + \ DEST.DATA//("macros_dil.ddoc", "dilconf.d") + FILES print "***** Generating documentation *****" versions = ["DDoc"] generate_docs(DIL.EXE, DEST.DOC, MODLIST, DOC_FILES, versions, options=['-v', '-i', '-hl', '--kandil']) if options.pdf: write_PDF(DEST, DEST.DOC, VERSION, TMP) DMD_EXE.use_wine = False use_wine = False if platform is 'win32': build_linux_binaries = False build_windows_binaries = True else: build_linux_binaries = True build_windows_binaries = locate_command("wine") != None class BINPath(Path): def __div__(self, name): """ Converts a Unix path to a Windows path. """ name = Path.__div__(self, name) return name if name.ext != '.exe' else name.replace("/", r"\\") BIN = BINPath(BIN) use_wine = True # Use wine on Linux to build Windows binaries. if not build_windows_binaries: print "Error: can't build windows binaries: "\ "wine is not installed or not in PATH." if options.no_binaries: build_linux_binaries = build_windows_binaries = False # Create partial functions with common parameters. # Note: the -inline switch makes the binaries significantly larger on Linux. build_dil_rls = func_partial(build_dil, DMD_EXE, FILES, release=True, optimize=True, inline=True) build_dil_dbg = func_partial(build_dil, DMD_EXE, FILES, debug_info=options.debug_symbols) if build_linux_binaries: print "***** Building Linux binaries *****" # Linux Debug Binaries build_dil_dbg(BIN/"dil_d") build_dil_dbg(BIN/"dil2_d", versions=["D2"]) # Linux Release Binaries build_dil_rls(BIN/"dil") build_dil_rls(BIN/"dil2", versions=["D2"]) if build_windows_binaries: print "***** Building Windows binaries *****" DMD_EXE.use_wine = use_wine # Windows Debug Binaries build_dil_dbg(BIN/"dil_d.exe") build_dil_dbg(BIN/"dil2_d.exe", versions=["D2"]) # Windows Release Binaries build_dil_rls(BIN/"dil.exe") build_dil_rls(BIN/"dil2.exe", versions=["D2"]) print "***** Copying files *****" copy_files(DEST) options.docs or DEST.DOC.rmtree() TMP.rmtree() # Build archives. assert DEST[-1] != Path.sep opt = options for exec_cmd, cmd in zip((opt.tar_gz, opt.tar_bz2, opt.zip, opt._7z), ("tar --owner root --group root -czf %(name)s.tar.gz %(src)s", "tar --owner root --group root --bzip2 -cf %(name)s.tar.bz2 %(src)s", "zip -q -9 -r %(name)s.zip %(src)s", "7zr a %(name)s.7z %(src)s")): if not exec_cmd: continue if locate_command(cmd): print "Error: the utility '%s' is not in your PATH." % cmd continue cmd = cmd % dict(locals(), name=DEST, src=DEST) print cmd os.system(cmd)
def main(): from functools import partial as func_partial from optparse import OptionParser usage = "Usage: scripts/release.py VERSION [Options]" parser = OptionParser(usage=usage) add_option = func_partial(parser.add_option, action="store_true", default=False) add_option("-s", "--dsymbols", dest="debug_symbols", help="generate debug symbols for debug builds") add_option("-d", "--docs", dest="docs", help="generate documentation") add_option("--7z", dest="_7z", help="create a 7z archive") add_option("--gz", dest="tar_gz", help="create a tar.gz archive") add_option("--bz2", dest="tar_bz2", help="create a tar.bz2 archive") add_option("--zip", dest="zip", help="create a zip archive") add_option("--git", dest="git", help="use git to check out a clean copy (default is hg)") parser.add_option("--src", dest="src", metavar="SRC", default=None, help="use SRC folder instead of checking out code using hg or git") parser.add_option("--dmd-exe", dest="dmd_exe", metavar="EXE_PATH", default="dmd", help="specify EXE_PATH if dmd is not in your PATH") parser.add_option("--builddir", dest="builddir", metavar="DIR", default=None, help="where to build the release and archives (default is build/)") parser.add_option("--winpath", dest="winpath", metavar="P", default=None, help="permanently append P to PATH in the Windows (or wine's) registry. " "Exits the script.") (options, args) = parser.parse_args() if options.winpath != None: from env_path import append2PATH append2PATH(options.winpath, Path("")) return if len(args) < 1: return parser.print_help() if len(args) > 1: print "Warning! Arguments ignored: " + " ".join(args[1:]) # Validate the version argument. m = re.match(r"((\d)\.(\d\d\d)(-\w+)?)", args[0]) if not m: parser.error("invalid VERSION; format: /\d.\d\d\d(-\w+)?/ E.g.: 1.123") matched = m.groups() if not Path(options.dmd_exe).exists and not locate_command(options.dmd_exe): print "The executable '%s' couldn't be located or does not exist." % \ options.dmd_exe return notNone = max # Path of the executable of dil. DIL_EXE = Path("bin")/"dil" # Name or path to the executable of dmd. DMD_EXE = options.dmd_exe DMD_EXE_W = DMD_EXE # Executable to use for Windows builds. # The version of dil to be built. VERSION, V_MAJOR = matched[:2] V_MINOR, V_SUFFIX = (matched[2], notNone(matched[3], '')) # Build folder. BUILD_DIR = Path(notNone("build", options.builddir)) # Destination of distributable files. DEST = BUILD_DIR/("dil."+VERSION) # The destination of the binaries. DEST.BIN = DEST/"bin" BIN = DEST.BIN # Shortcut to the bin/ folder. # The source code folder of dil. DEST.SRC = DEST/"src" # Documentation folder of dil. DEST.DOC = DEST/"doc" # The JavaScript, CSS and image folders. DEST.JS, DEST.CSS, DEST.IMG = DEST.DOC//("js", "css", "img") # Destination of syntax highlighted source files. DEST.HTMLSRC = DEST.DOC/"htmlsrc" # Dil's data/ directory. DEST.DATA = DEST/'data' # Dil's fancy documentation format. DEST.KANDIL = DEST/"kandil" # Temporary directory, deleted in the end. TMP = DEST/"tmp" # The list of module files (with info) that have been processed. MODLIST = TMP/"modules.txt" # The files to generate documentation for. FILES = [] # Create the build directory. BUILD_DIR.makedirs() # Check out a new working copy. DEST.rmtree() # First remove the tree. if options.src != None: Path(options.src).copytree(DEST) elif options.git: if locate_command('git'): os.system("git clone ./ %(DEST)s && cd %(DEST)s && git checkout"%locals()) (DEST/".git").rmtree() # Remove the .git folder. else: raise Exception("git is not in your PATH") elif locate_command('hg'): os.system("hg archive -r tip -t files " + DEST) else: raise Exception("hg is not in your PATH; specify SRC or use git") # Create other directories not available in a clean checkout. map(Path.mkdir, (DEST.BIN, DEST.DOC, DEST.HTMLSRC, DEST.CSS, DEST.IMG, DEST.JS, TMP)) # Find the source code files. FILES = find_dil_source_files(DEST.SRC) # Make a backup of the original. VERSION_D = DEST.SRC/"dil"/"Version.d" VERSION_D.copy(TMP/"Version.d") # Update the version info. update_version(VERSION_D, V_MAJOR, V_MINOR) # Restore the original at the end of the build process. if options.docs: build_dil_if_inexistant(DIL_EXE) DOC_FILES = [DEST.KANDIL/"kandil.ddoc"] + \ DEST.DATA//("macros_dil.ddoc", "dilconf.d") + FILES versions = ["DDoc"] print "***** Generating documentation *****" generate_docs(DIL_EXE, DEST.DOC, MODLIST, DOC_FILES, versions, options='-v') modlist = read_modules_list(MODLIST) generate_modules_js(modlist, DEST.JS/"modules.js") print "***** Generating syntax highlighted HTML files *****" for args in generate_shl_files2(DIL_EXE, DEST.HTMLSRC, modlist): print "hl %s > %s" % args; download_jquery(DEST.JS/"jquery.js") if platform is 'win32': build_linux_binaries = False build_windows_binaries = True else: build_linux_binaries = True build_windows_binaries = locate_command("wine") != None class BINPath(Path): def __div__(self, name): """ Converts a Unix path to a Windows path. """ name = Path.__div__(self, name) return name if name.ext != '.exe' else name.replace("/", r"\\") BIN = BINPath(BIN) DMD_EXE_W = "wine dmd.exe" # Use wine on Linux to build Windows binaries. if not build_windows_binaries: print "Error: can't build windows binaries: "\ "wine is not installed or not in PATH." # Create partial functions with common parameters. # Note: the -inline switch makes the binaries significantly larger on Linux. build_dil_rls = func_partial(build_dil, FILES, dmd_exe=DMD_EXE, release=True, optimize=True, inline=True) build_dil_dbg = func_partial(build_dil, FILES, dmd_exe=DMD_EXE, debug_info=options.debug_symbols) if build_linux_binaries: print "***** Building Linux binaries *****" # Linux Debug Binaries build_dil_dbg(BIN/"dil_d") build_dil_dbg(BIN/"dil2_d", versions=["D2"]) # Linux Release Binaries build_dil_rls(BIN/"dil") build_dil_rls(BIN/"dil2", versions=["D2"]) if build_windows_binaries: print "***** Building Windows binaries *****" build_dil_dbg.keywords['dmd_exe'] = DMD_EXE_W build_dil_rls.keywords['dmd_exe'] = DMD_EXE_W # Windows Debug Binaries build_dil_dbg(BIN/"dil_d.exe") build_dil_dbg(BIN/"dil2_d.exe", versions=["D2"]) # Windows Release Binaries build_dil_rls(BIN/"dil.exe") build_dil_rls(BIN/"dil2.exe", versions=["D2"]) print "***** Copying files *****" copy_files(DEST) # Restore the original. NOTE: is this a good idea? (TMP/"Version.d").move(VERSION_D) if not options.docs: DEST.DOC.rmtree() TMP.rmtree() # Build archives. assert DEST[-1] != Path.sep opt = options for exec_cmd, cmd in zip((opt.tar_gz, opt.tar_bz2, opt.zip, opt._7z), ("tar --owner root --group root -czf %(name)s.tar.gz %(src)s", "tar --owner root --group root --bzip2 -cf %(name)s.tar.bz2 %(src)s", "zip -q -9 -r %(name)s.zip %(src)s", "7zr a %(name)s.7z %(src)s")): if not exec_cmd: continue if locate_command(cmd): print "Error: the utility '%s' is not in your PATH." % cmd continue cmd = cmd % dict(locals(), name=DEST, src=DEST) print cmd os.system(cmd)