Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit bf71732

Browse files
committed
Use luatex in --luaonly mode to query kpsewhich.
`luatex --luaonly` runs a *lua* interpreter with relevant tex libraries available, which avoids both the overhead of repeatedly initializing kpathsea (the old approach, very slow on macos and windows). An alternative approach would be to use `luatex` followed by `\directlua` calls, but on windows it appears that one needs to use `lualatex` to get a working interactive prompt, and just loading the latex format takes seconds(!). For the simple following benchmark: ```sh python -c 'from pylab import *; mpl.use("pdf"); rcParams["text.usetex"] = True; plot(); savefig("test.pdf", backend="pdf")' ``` On a macos machine, this patch brings runtime from ~4.5s to ~2.5s. On a windows machine, this patch brings runtime from ~6.5s to ~1.7s. We also need to figure out how to best advertise this (do we emit a warning suggesting to install luatex on windows and macos if luatex is not present?).
1 parent 266be12 commit bf71732

File tree

3 files changed

+39
-0
lines changed

3 files changed

+39
-0
lines changed
Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
The *format* parameter of ``dviread.find_tex_file``
2+
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
3+
... is deprecated (with no replacement).

lib/matplotlib/dviread.py

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@
2525
from pathlib import Path
2626
import re
2727
import struct
28+
import subprocess
2829
import sys
2930
import textwrap
3031

@@ -1040,7 +1041,30 @@ def _parse_enc(path):
10401041
"Failed to parse {} as Postscript encoding".format(path))
10411042

10421043

1044+
class _LuatexKpsewhich:
1045+
@lru_cache() # A singleton.
1046+
def __new__(cls):
1047+
self = object.__new__(cls)
1048+
self._proc = self._new_proc()
1049+
return self
1050+
1051+
def _new_proc(self):
1052+
return subprocess.Popen(
1053+
["luatex", "--luaonly",
1054+
str(cbook._get_data_path("kpsewhich.lua"))],
1055+
stdin=subprocess.PIPE, stdout=subprocess.PIPE)
1056+
1057+
def search(self, filename):
1058+
if self._proc.poll() is not None: # Dead, restart it.
1059+
self._proc = self._new_proc()
1060+
self._proc.stdin.write(os.fsencode(filename) + b"\n")
1061+
self._proc.stdin.flush()
1062+
out = self._proc.stdout.readline().rstrip()
1063+
return "" if out == b"nil" else os.fsdecode(out)
1064+
1065+
10431066
@lru_cache()
1067+
@_api.delete_parameter("3.5", "format")
10441068
def find_tex_file(filename, format=None):
10451069
"""
10461070
Find a file in the texmf tree.
@@ -1058,6 +1082,7 @@ def find_tex_file(filename, format=None):
10581082
format : str or bytes
10591083
Used as the value of the ``--format`` option to :program:`kpsewhich`.
10601084
Could be e.g. 'tfm' or 'vf' to limit the search to that type of files.
1085+
Deprecated.
10611086
10621087
References
10631088
----------
@@ -1072,6 +1097,14 @@ def find_tex_file(filename, format=None):
10721097
if isinstance(format, bytes):
10731098
format = format.decode('utf-8', errors='replace')
10741099

1100+
if format is None:
1101+
try:
1102+
lk = _LuatexKpsewhich()
1103+
except FileNotFoundError:
1104+
pass # Fallback to directly calling kpsewhich, as below.
1105+
else:
1106+
return lk.search(filename)
1107+
10751108
if os.name == 'nt':
10761109
# On Windows only, kpathsea can use utf-8 for cmd args and output.
10771110
# The `command_line_encoding` environment variable is set to force it

lib/matplotlib/mpl-data/kpsewhich.lua

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
-- see dviread._LuatexKpsewhich
2+
kpse.set_program_name("tex")
3+
while true do print(kpse.lookup(io.read():gsub("\r", ""))) end

0 commit comments

Comments
 (0)