diff options
| author | Sebastian Kuhnert | 2008-09-05 14:12:24 +0000 |
|---|---|---|
| committer | Sebastian Kuhnert | 2008-09-05 14:12:24 +0000 |
| commit | 621d9b7f9b4228bbad4fd1acf996c6f0f9d89ea1 (patch) | |
| tree | d123981bf0d234f9139098ae04c418af0b25805a /texall | |
| parent | ac5f48478bee79b00e0895addc2704746385a2e6 (diff) | |
| download | exercisesheets-621d9b7f9b4228bbad4fd1acf996c6f0f9d89ea1.tar.gz exercisesheets-621d9b7f9b4228bbad4fd1acf996c6f0f9d89ea1.tar.bz2 exercisesheets-621d9b7f9b4228bbad4fd1acf996c6f0f9d89ea1.zip | |
texall script: bugfixes and improved performance
Diffstat (limited to 'texall')
| -rwxr-xr-x | texall | 131 |
1 files changed, 82 insertions, 49 deletions
@@ -44,10 +44,10 @@ class TexallOptionParser(OptionParser): dest="interactionmode", choices=("batchmode", "nonstopmode", "scrollmode", "errorstopmode"), help="control the behaviour of latex (on of batchmode (default), nonstopmode (default for -o), scrollmode, errorstopmode)") self.add_option("-I", "--ignore", - action="store", dest="ignorepattern", default=".*vorlage.*|\.\#.*|\..*\.rmligs\.tex", + action="store", dest="ignorepattern", default=".*vorlage|\.\#|.*-rmligs\.tex$", help="regular expression of filenames to ignore") self.add_option("-P", "--required-pattern", - action="store", dest="requiredpattern", default='^\\\\documentclass|%%% TeX-master: t', + action="store", dest="requiredpattern", default='^\\\\documentclass|^%%% TeX-master: t', help="regular expression that must match the file content") self.add_option("-T", "--preserve-tempfiles", action="store_false", dest="deletetempfiles", default=True, @@ -110,10 +110,10 @@ class AnalyseTexRequired(Analyser): d.required = False Analyser.__init__(self,d) def parse(self, text): - if re_required.match(text): + if re_required.search(text): self.d.required = True def merge(self, d): - pass # do not take over master file status + self.d.required |= d.required class AnalyseTexDependencies(Analyser): def __init__(self, d): @@ -123,7 +123,7 @@ class AnalyseTexDependencies(Analyser): def parse(self, text): for m in re_inputinclude.finditer(text): self.d.deps.append((m.group(2), (".tex", ""))) - m = re_documentclass.match(text) + m = re_documentclass.search(text) if m: cls = m.group(2) self.d.deps.append((cls, (".cls", ""))) @@ -141,7 +141,7 @@ class AnalyseTexDependencies(Analyser): def merge(self, d): self.d.deps.extend(d.deps) self.d.grfdeps.extend(d.grfdeps) - def finish(self, _): + def finish(self, dirname): if hasattr(self.d, "needsPS"): if self.d.needsPS: for f in self.d.grfdeps: @@ -149,6 +149,17 @@ class AnalyseTexDependencies(Analyser): else: for f in self.d.grfdeps: self.d.deps.append((f, (".pdf", ".jpg", ".png", ""))) + expandeddeps = [] + for dep, extlist in self.d.deps: + if extlist == None: + expandeddeps.append((dep, extlist)) + else: + try: + expandeddeps.append((texpath(dirname, dep, extlist=extlist), None)) + except ValueError, e: + if opts.verbosity > 2: + error(self.d.name, "ignoring dependency: %s"%e, warning=True) + self.d.deps = expandeddeps class AnalyseTexBibfiles(Analyser): def __init__(self, d): @@ -168,7 +179,7 @@ class AnalyseTexBibfiles(Analyser): try: bibpath = texpath(dirname, bib, pathtype="bib",progname="bibtex") bibpath = strippath(bibpath, dirname) - self.d.deps.append((bibpath, ("",))) + self.d.deps.append((bibpath, None)) bibpaths.append(bibpath) except ValueError, e: error(self.d.name, str(e), warning=True) @@ -181,7 +192,7 @@ class AnalyseTexNeedsPs(Analyser): d.needsPS = False Analyser.__init__(self, d) def parse(self, text): - if re_needsps.match(text): + if re_needsps.search(text): self.d.needsPS = True def merge(self, d): self.d.needsPS |= d.needsPS @@ -191,7 +202,7 @@ class AnalyseTexRmligs(Analyser): d.rmligs = False Analyser.__init__(self, d) def parse(self, text): - if re_rmligs.match(text): + if re_rmligs.search(text): self.d.rmligs = True def merge(self, d): self.d.rmligs |= d.rmligs @@ -203,25 +214,32 @@ class AnalyseLogErrors(Analyser): d.errors = False Analyser.__init__(self, d) def parse(self, text): - if re_error.match(text): + if re_error.search(text): self.d.errors = True class AnalyseLogRequests(Analyser): def __init__(self, d): d.requests = {} + d.requestreason = {} Analyser.__init__(self, d) self.inrequest = False - def addrequest(self, name, priority): + def addrequest(self, name, priority, reason=None): if self.d.requests.has_key(name): - self.d.requests[name] = max(self.d.requests[name], priority) + if self.d.requests[name] < priority: + self.d.requests[name] = priority + if reason: + self.d.reqeustreason[name] = reason + elif not self.d.requestreason[name]: + self.d.requestreason[name] = reason else: self.d.requests[name] = priority + self.d.requestreason[name] = reason def parse(self, text): for m in re_logmatcher.finditer(text): if m.group() == 'LaTeX Warning: There were undefined references.': - self.addrequest("latex",0) + self.addrequest("latex", 0, " (because of undefined references)") elif m.group() == 'LaTeX Warning: Label(s) may have changed. Rerun to get cross-references right.': - self.addrequest("latex",0) + self.addrequest("latex", 0, " (because of changed labels)") elif m.group(1)!=None: self.addrequest(m.group(2), int(m.group(1))) elif m.group(3)!=None: @@ -246,6 +264,9 @@ class AnalyseLogRequests(Analyser): if infile != None: options.append(infile) self.addrequest(tuple(options), pri) + def finish(self, _): + if self.d.errors: + self.addrequest("latex", 0, " (because of errors in .log file)") loganalysers = (AnalyseLogErrors, AnalyseLogRequests) @@ -282,18 +303,21 @@ def analyseFile(dirname, filename, analyserclasses, parsetype, fulltext=False, c f.close() if hasattr(data, "deps") and (recurse or (recurse==None - and hasattr(data, "requrired") + and hasattr(data, "required") and data.required)): # recurse: for dep, extlist in data.deps: - deppath = texpath(dirname, dep, extlist=extlist) + try: + deppath = texpath(dirname, dep, extlist=extlist) + except ValueError, e: + continue if (not recursesystemfiles) and re_systemfile.match(deppath): # skip system files continue depname = strippath(deppath, dirname) - depdata = analyseFile(dirname, depname, fulltext, cache, recurse=True) + depdata = analyseFile(dirname, depname, analyserclasses, parsetype, fulltext, cache, True, recursesystemfiles) for a in analysers: a.merge(depdata) - if hasattr(data, "required") and data.required: + if (hasattr(data, "required") and data.required) or parsetype == "log": for a in analysers: a.finish(dirname) if cache: @@ -309,6 +333,8 @@ def analyseLog(dirname, filename): kpsecache = {} kpseproc = {} def texpath(dirname,filename,pathtype="tex",progname="latex",extlist=("",)): + if extlist == None: + return filename filename = os.path.expanduser(filename) # first try files in current directory if pathtype=="bib" and extlist==("",): @@ -360,7 +386,7 @@ def texpath(dirname,filename,pathtype="tex",progname="latex",extlist=("",)): stdin=slave, cwd="/") kpseproc[(pathtype, progname)] = (proc, master) - if select.select([master], [], [], .2)[0]: + if select.select([master], [], [], .05)[0]: pathname = os.read(master, 1024) else: pathname = None @@ -458,6 +484,10 @@ def alltexfiles(arglist): for directory, subdirs, files in os.walk(a): if not opts.recurse: subdirs[:] = [] + else: + for skipdir in (".svn", ".bzr"): + if skipdir in subdirs: + subdirs.remove(skipdir) for name in files: if re_texfile.match(name): if re_ignore.match(name): @@ -507,14 +537,10 @@ def needsupdate(dirname, texname, data=None): 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: - try: - deppath = texpath(dirname, filename, extlist=extlist) - if outdate < os.path.getmtime(os.path.join(dirname, deppath)): - return " (because %s is newer than .pdf)"%deppath - except ValueError, e: - if opts.verbosity > 2: - error(os.path.join(dirname, texname), "ignored dependency: " + str(e), warning=True) + for deppath, extlist in data.deps: + assert extlist == None + if outdate < os.path.getmtime(os.path.join(dirname, deppath)): + return " (because %s is newer than .pdf)"%deppath # check for errors and requests logname = jobname + ".log" @@ -579,7 +605,7 @@ def processTex(dirname, texname, data=None, reason=""): reason = " (because %s is newer than %s)"%(bib,bbl) else: reason = " (because of --force)" - rmtempfile(bbl, dirname, force=True, reason=reason) + rmtempfile(bblpath, force=True, reason=reason) nextbbls.remove(bbl) bbls = nextbbls @@ -589,8 +615,10 @@ def processTex(dirname, texname, data=None, reason=""): # check for undefined references and run requests numrun=0 reqs=opts.act # ignore requests if programs are not run + logname = jobname + ".log" while reqs: - reqs = analyseLog(dirname, jobname+".log").requests + logdata = analyseLog(dirname, logname) + reqs = logdata.requests if not reqs: break pri = reqs.values() pri.sort(reverse=True) @@ -603,7 +631,9 @@ def processTex(dirname, texname, data=None, reason=""): if rp == p: reason = "" if opts.verbosity: - reason = " (because of request in .log file, priority %d)"%rp + reason = logdata.requestreason[req] + if not reason: + reason = " (because of request in .log file, priority %d)"%rp if req == "latex": runtex(tex, texname, realname, dirname, reason=reason) elif isinstance(req, tuple): @@ -621,16 +651,16 @@ def processTex(dirname, texname, data=None, reason=""): runtex(tex, texname, realname, dirname, reason=" (because .ind file might have changed)") if data.needsPS: - run(["dvips", jobname+".dvi"], dirname) + run(["dvips", jobname+".dvi"], dirname, stderr=subprocess.STDOUT) run(["ps2pdf", jobname+".ps"], dirname) - rmtempfile(tmplist, dirname) + rmtempfile(tmplist) def bblfiles(dirname, jobname): files = dircache.listdir(dirname) return fnmatch.filter(files, "%s*.bbl"%jobname) -def rmtempfile(filenames, dirname, force=False, reason=""): +def rmtempfile(filenames, force=False, reason=""): if (opts.deletetempfiles or force) and filenames: if not isinstance(filenames, list): filenames = [filenames] @@ -638,11 +668,10 @@ def rmtempfile(filenames, dirname, force=False, reason=""): print " removing %s%s"%(", ".join(filenames), reason) if opts.act: for f in filenames: - fullname = os.path.join(dirname, f) - if os.path.exists(fullname): - os.remove(fullname) + if os.path.exists(f): + os.remove(f) else: - error(fullname, "could not be removed (does not exist)", warning=True) + error(f, "could not be removed (does not exist)", warning=True) def run(arglist, dirname, reason="", inf=None, outf=None, stderr=None): """Run a command with optional io redirections. @@ -761,7 +790,7 @@ def preparermligs(texname, dirname, texpath, tmplist): else: try: (subdir, texbasename) = os.path.split(texname) - rmligsbasename = ".%s.rmligs.tex"%texbasename[:-4] + rmligsbasename = "%s-rmligs.tex"%texbasename[:-4] rmligsname = os.path.join(subdir, rmligsbasename) rmligspath = os.path.join(dirname, rmligsname) if opts.act: @@ -773,17 +802,18 @@ def preparermligs(texname, dirname, texpath, tmplist): return texname else: tmplist.append(rmligspath) - def rewriteinputrmligs(m): - name=m.group(2) + name = m.group(2) if not os.path.exists(os.path.join(dirname,name)): name+=".tex" - if os.path.exists(os.path.join(dirname, name)): - name = preparermligs(name, dirname, tmplist) + path = os.path.join(dirname, name) + if os.path.exists(path): + name = preparermligs(name, dirname, path, tmplist) else: 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): + d = re_commentinclude.sub("", d) rmligsfile.write(re_inputinclude.sub(rewriteinputrmligs, d)) return None run([rmligs_name, "-f"], dirname, inf=texfile, outf=filteroutput) @@ -835,14 +865,17 @@ try: re_texfile = re.compile(".*\.tex$", re.I) if iswindows: re_systemfile = re.compile("^?:\\\\Program", re.I) + re_nonlocal = re.compile("^?:\\\\") else: re_systemfile = re.compile("^/usr/") + re_nonlocal = re.compile("^/") re_texcomment = re.compile("(?<!\\\\)%.*?$", re.M) re_required = re.compile(opts.requiredpattern) re_inputinclude = re.compile('\\\\(input|include|@input)\\{([^}]*)\\}') + re_commentinclude = re.compile('(?<!\\\\)%[^%\n\r]*\\\\(input|include|@input)\\{([^}]*?)\\}[^%\n\r]*?$', re.M) re_documentclass = re.compile('\\\\documentclass(\\[.*?\\])?\\{([^}]*)\\}') re_usepackage = re.compile('\\\\usepackage(\\[.*?\\])?\\{([^}]*)\\}') re_usetheme = re.compile('\\\\use(|color|font|inner|outer)theme(\\[.*?\\])?\\{([^}]*)\\}') @@ -859,15 +892,15 @@ try: re_longreq = re.compile("^(binary|option|infile)=(.*?)$", re.M) re_error = re.compile('^! ', re.M) - re_rmligsfile = re.compile("\\.([^/ ]+)\\.rmligs\\.tex") + re_rmligsfile = re.compile("([^/ ]+)-rmligs\\.tex") if __name__ == "__main__": -# import cProfile -# import pstats -# cProfile.run("main(programargs)", "mystats") -# p = pstats.Stats("mystats") -# p.sort_stats('time').print_stats() - + #import cProfile + #import pstats + #cProfile.run("main(programargs)", "mystats") + #p = pstats.Stats("mystats") + #p.sort_stats('time').print_stats() + main(programargs) except KeyboardInterrupt: |
