From ac5f48478bee79b00e0895addc2704746385a2e6 Mon Sep 17 00:00:00 2001 From: Sebastian Kuhnert Date: Thu, 4 Sep 2008 22:16:23 +0000 Subject: texall script: performance improvements --- texall | 190 ++++++++++++++++++++++++++++++++++------------------------------- 1 file changed, 100 insertions(+), 90 deletions(-) (limited to 'texall') diff --git a/texall b/texall index 8169429..a6f98d4 100755 --- a/texall +++ b/texall @@ -131,6 +131,11 @@ class AnalyseTexDependencies(Analyser): stys = m.group(2) for sty in re_commawhitespace.split(stys): self.d.deps.append((sty, (".sty", ""))) + for m in re_usetheme.finditer(text): + themes = m.group(3) + ttype = m.group(1) + for theme in re_commawhitespace.split(themes): + self.d.deps.append(("beamer%stheme%s"%(ttype, theme), (".sty",))) for m in re_graphics.finditer(text): self.d.grfdeps.append(m.group(2)) def merge(self, d): @@ -145,8 +150,6 @@ class AnalyseTexDependencies(Analyser): for f in self.d.grfdeps: self.d.deps.append((f, (".pdf", ".jpg", ".png", ""))) -# TODO: Analyser for \usebeamerXXXtheme - class AnalyseTexBibfiles(Analyser): def __init__(self, d): d.bibfiles = [] @@ -199,8 +202,8 @@ class AnalyseLogErrors(Analyser): def __init__(self, d): d.errors = False Analyser.__init__(self, d) - def parse(self, line): - if re_error.match(line): + def parse(self, text): + if re_error.match(text): self.d.errors = True class AnalyseLogRequests(Analyser): @@ -213,57 +216,47 @@ class AnalyseLogRequests(Analyser): self.d.requests[name] = max(self.d.requests[name], priority) else: self.d.requests[name] = priority - def parse(self, line): - # line by line - if self.inrequest: - # strip newline character - while line[-1] in ("\n", "\r"): - line = line[:-1] - if line[:7] == "binary=": - self.reqbinary = line[7:] - elif line[:7] == "option=": - self.reqoptions.extend(line[7:].split(" ")) - elif line[:7] == "infile=": - self.reqinfile = line[7:] - elif line == ":REQ": - if self.reqbinary == None: - self.reqbinary = self.reqname - if self.reqbinary not in ("bibtex", "bibtex8"): - error(self.d.name, "ignoring request to run %s for security reasons"%self.reqbinary, warning=True) - self.inrequest = False - return - self.reqoptions[:0] = [self.reqbinary] - if self.reqbinary == "bibtex8": - self.reqoptions[1:1] = [ "--wolfgang" ] - if self.reqinfile != None: - self.reqoptions.append(self.reqinfile) - self.addrequest(tuple(self.reqoptions), self.reqpri) - self.inrequest=False - else: - error(self.d.name, "malformatted request ignored", warning=True) - self.inrequest=False - else: - m = re_logmatcher.match(line) - if m: - if m.group() == 'LaTeX Warning: There were undefined references.': - self.addrequest("latex",0) - elif m.group() == 'LaTeX Warning: Label(s) may have changed. Rerun to get cross-references right.': - self.addrequest("latex",0) - elif m.group(1)!=None: - self.addrequest(m.group(2), int(m.group(1))) - elif m.group(3)!=None: - self.inrequest = True - self.reqpri = int(m.group(3)) - self.reqname = m.group(4) - self.reqbinary = None - self.reqoptions = [] - self.reqinfile = None + def parse(self, text): + for m in re_logmatcher.finditer(text): + if m.group() == 'LaTeX Warning: There were undefined references.': + self.addrequest("latex",0) + elif m.group() == 'LaTeX Warning: Label(s) may have changed. Rerun to get cross-references right.': + self.addrequest("latex",0) + elif m.group(1)!=None: + self.addrequest(m.group(2), int(m.group(1))) + elif m.group(3)!=None: + pri = int(m.group(3)) + binary = m.group(4) + binary = None + options = [] + infile = None + for l in re_longreq.finditer(m.group(5)): + if l.group(1) == "infile": + infile = l.group(2) + elif l.group(1) == "option": + options.extend(l.group(2).split(" ")) + elif l.group(1) == "binary": + binary = l.group(2) + if binary not in ("bibtex", "bibtex8"): + error(self.d.name, "ignoring request to run %s for security reasons"%binary, warning=True) + continue + options[:0] = [binary] + if binary == "bibtex8": + options[1:1] = [ "--wolfgang" ] + if infile != None: + options.append(infile) + self.addrequest(tuple(options), pri) loganalysers = (AnalyseLogErrors, AnalyseLogRequests) +analysecachedir = None analysecache = {} def analyseFile(dirname, filename, analyserclasses, parsetype, fulltext=False, cache=False, recurse=None, recursesystemfiles=False): + global analysecachedir, analysecache + if dirname != analysecachedir: + analysecachedir = dirname + analysecache = {} pathname = os.path.join(dirname, filename) if cache and (parsetype, pathname) in analysecache: return analysecache[(parsetype, pathname)] @@ -272,9 +265,11 @@ def analyseFile(dirname, filename, analyserclasses, parsetype, fulltext=False, c for analyser in analyserclasses: analysers.append(analyser(data)) try: - f = open(os.path.join(dirname, filename), "r") + f = open(pathname, "r") if fulltext: text = f.read() + if parsetype == "tex": + text = re_texcomment.sub("", text) for a in analysers: a.parse(text) else: @@ -282,7 +277,7 @@ def analyseFile(dirname, filename, analyserclasses, parsetype, fulltext=False, c for a in analysers: a.parse(line) except IOError, e: - error(os.path.join(dirname, filename), "could not be analysed: %s"%e) + error(pathname, "could not be analysed: %s"%e) else: f.close() if hasattr(data, "deps") and (recurse @@ -309,7 +304,7 @@ def analyseTex(dirname, filename): return analyseFile(dirname, filename, texanalysers, "tex", fulltext=True, cache=True) def analyseLog(dirname, filename): - return analyseFile(dirname, filename, loganalysers, "log", cache=False) + return analyseFile(dirname, filename, loganalysers, "log", fulltext=True, cache=False) kpsecache = {} kpseproc = {} @@ -319,7 +314,7 @@ def texpath(dirname,filename,pathtype="tex",progname="latex",extlist=("",)): if pathtype=="bib" and extlist==("",): extlist=(".bib", "") for ext in extlist: - if os.path.isfile(os.path.join(dirname,filename+ext)): + if os.path.exists(os.path.join(dirname,filename+ext)): return filename+ext if opts.nokpse: raise ValueError("file not found, not using kpsewhich: %s (extensions: %r)") @@ -365,7 +360,7 @@ def texpath(dirname,filename,pathtype="tex",progname="latex",extlist=("",)): stdin=slave, cwd="/") kpseproc[(pathtype, progname)] = (proc, master) - if select.select([master], [], [], 0.1)[0]: + if select.select([master], [], [], .2)[0]: pathname = os.read(master, 1024) else: pathname = None @@ -444,7 +439,7 @@ if binpath == "$PATH": binpath = binpath.split(os.path.pathsep) def isinpath(name): for p in binpath: - if os.path.isfile(os.path.join(p, name)): + if os.path.exists(os.path.join(p, name)): return True return False @@ -470,7 +465,7 @@ def alltexfiles(arglist): print "%s: skipped because of ignored name"%os.path.normpath(os.path.join(directory,name)) else: yield (directory, name) - elif os.path.isfile(a): + elif os.path.exists(a): if re_texfile.match(a): (dirname, filename) = os.path.split(a) if dirname == "": @@ -478,7 +473,7 @@ def alltexfiles(arglist): yield (dirname, filename) else: error(a, "is no .tex file; skipped") - elif os.path.isfile(a+".tex"): + elif os.path.exists(a+".tex"): (dirname, filename) = os.path.split(a+".tex") if dirname == "": dirname = "." @@ -504,11 +499,12 @@ def needsupdate(dirname, texname, data=None): # check for nonexistant output file outname = jobname + ".pdf" - if not os.path.isfile(os.path.join(dirname, outname)): + outpath = os.path.join(dirname, outname) + if not os.path.exists(outpath): return " (because .pdf does not exist)" # check for updated source and dependency files - outdate = os.path.getmtime(os.path.join(dirname, outname)) + outdate = os.path.getmtime(outpath) if outdate < os.path.getmtime(os.path.join(dirname, texname)): return " (because .tex is newer than .pdf)" for filename, extlist in data.deps: @@ -522,7 +518,7 @@ def needsupdate(dirname, texname, data=None): # check for errors and requests logname = jobname + ".log" - if os.path.isfile(os.path.join(dirname, logname)): + if os.path.exists(os.path.join(dirname, logname)): logdata = analyseLog(dirname, jobname + ".log") if logdata.errors: return " (because of error(s) in .log file)" @@ -540,13 +536,17 @@ def needsupdate(dirname, texname, data=None): MAXRUNS=5 def processTex(dirname, texname, data=None, reason=""): - procfiles.append(os.path.normpath(os.path.join(dirname,texname))) + #strip .tex extension + jobname=texname[:-4] + jobpath = os.path.join(dirname,jobname) + texpath = jobpath + ".tex" + procfiles.append(os.path.normpath(texpath)) if data == None: data = analyseTex(dirname, texname) if opts.verbosity: - print "processing %s%s..."%(os.path.normpath(os.path.join(dirname,texname)),reason) + print "processing %s%s..."%(os.path.normpath(texpath),reason) # list of temporary files to be removed later tmplist = [] @@ -561,10 +561,7 @@ def processTex(dirname, texname, data=None, reason=""): realname = texname if data.rmligs: - realname = preparermligs(texname, dirname, tmplist) - - #strip .tex extension - jobname=texname[:-4] + realname = preparermligs(texname, dirname, texpath, tmplist) # remove all outdated .bbl files (will be recreated by requests) bbls = bblfiles(dirname, jobname) @@ -606,21 +603,20 @@ def processTex(dirname, texname, data=None, reason=""): if rp == p: reason = "" if opts.verbosity: - reason = " (because of request in .aux file, priority %d)"%rp + reason = " (because of request in .log file, priority %d)"%rp if req == "latex": runtex(tex, texname, realname, dirname, reason=reason) elif isinstance(req, tuple): run(req, dirname, reason) else: - error(os.path.join(dirname,jobname+".aux"), "unsupported request: %s"%req) + error(jobpath+".log", "unsupported request: %s"%req) numrun+=1 if numrun==MAXRUNS: - error(os.path.join(dirname, texname), "does not stabilise after %i runs"%MAXRUNS) + error(texpath, "does not stabilise after %i runs"%MAXRUNS) break # update index if it exists - no way of knowing if it was updated - idx = jobname + ".idx" - if os.path.isfile(os.path.join(dirname, idx)): + if os.path.exists(jobpath + ".idx"): run(["makeindex", jobname], dirname, reason=" (because .idx file might have changed)") runtex(tex, texname, realname, dirname, reason=" (because .ind file might have changed)") @@ -643,7 +639,7 @@ def rmtempfile(filenames, dirname, force=False, reason=""): if opts.act: for f in filenames: fullname = os.path.join(dirname, f) - if os.path.isfile(fullname): + if os.path.exists(fullname): os.remove(fullname) else: error(fullname, "could not be removed (does not exist)", warning=True) @@ -756,35 +752,36 @@ def runtex(tex, texname, realname, dirname, reason=""): else: run([tex, "-interaction", opts.interactionmode, texname], dirname, outf=outf, reason=reason) -def preparermligs(texname, dirname, tmplist): +def preparermligs(texname, dirname, texpath, tmplist): try: - texfile = open(os.path.join(dirname, texname)) + texfile = open(texpath) except IOError, (errno, strerror): - error(os.path.join(dirname, texname), "could not be read: %s. Not using rmligs."%strerror) + error(texpath, "could not be read: %s. Not using rmligs."%strerror) return texname else: try: (subdir, texbasename) = os.path.split(texname) rmligsbasename = ".%s.rmligs.tex"%texbasename[:-4] rmligsname = os.path.join(subdir, rmligsbasename) + rmligspath = os.path.join(dirname, rmligsname) if opts.act: - rmligsfile = open(os.path.join(dirname, rmligsname), "w") + rmligsfile = open(rmligspath, "w") else: rmligsfile = null except IOError, (errno, strerror): - error(os.path.join(dirname, rmligsname), "could not be written: %s. Not using rmligs."%strerror) + error(rmligspath, "could not be written: %s. Not using rmligs."%strerror) return texname else: - tmplist.append(rmligsname) + tmplist.append(rmligspath) def rewriteinputrmligs(m): name=m.group(2) - if not os.path.isfile(os.path.join(dirname,name)): + if not os.path.exists(os.path.join(dirname,name)): name+=".tex" - if os.path.isfile(os.path.join(dirname, name)): + if os.path.exists(os.path.join(dirname, name)): name = preparermligs(name, dirname, tmplist) else: - error(os.path.join(dirname, texname), "%s: File could not be located. Not using rmligs."%name, warning=True) + error(texpath, "%s: File could not be located. Not using rmligs."%name, warning=True) return "\\%s{%s}"%(m.group(1), name[:-4]) def filteroutput(d): rmligsfile.write(re_inputinclude.sub(rewriteinputrmligs, d)) @@ -835,29 +832,42 @@ try: if opts.ignorepattern != "": re_ignore = re.compile(opts.ignorepattern) - re_required = re.compile(opts.requiredpattern) - re_texfile = re.compile(".*\.tex$", re.I) - - re_inputinclude = re.compile('\\\\(input|include|@input)\\{([^}]*)\\}') - re_usepackage = re.compile('\\\\usepackage(\\[.*?\\])?\\{([^}]*)\\}') - re_documentclass = re.compile('\\\\documentclass(\\[.*?\\])?\\{([^}]*)\\}') - re_graphics = re.compile('\\\\includegraphics(\\[.*?\\])?\\{([^}]*)\\}') if iswindows: re_systemfile = re.compile("^?:\\\\Program", re.I) else: re_systemfile = re.compile("^/usr/") + + re_texcomment = re.compile("(?