tecosaur / org-latex-preview-todos

A tracker for the Org LaTeX Preview effort on https://git.tecosaur.net/tec/org-mode
4 stars 0 forks source link

Change org-async process control settings for increased speed #16

Open karthink opened 6 months ago

karthink commented 6 months ago

There are two settings we can use for significant reductions in preview generation time. We're talking up to a 60% speed-up.

(dvisvgm method)
| Time (s) for:  | 330 fragments | 504 fragments | 1200 fragments |
|----------------+---------------+---------------+----------------|
| Before         |          2.34 |          2.93 |           8.08 |
| Now            |          1.88 |          1.79 |           5.72 |
|----------------+---------------+---------------+----------------|
| speed increase |           25% |           63% |            41% |
(dvipng method)
| Time (s) for:  | 330 fragments | 504 fragments | 1200 fragments |
|----------------+---------------+---------------+----------------|
| Before         |          0.57 |          1.08 |           1.96 |
| After          |          0.52 |          1.06 |           1.68 |
|----------------+---------------+---------------+----------------|
| speed increase |           10% |            1% |            14% |

To achieve this speed-up, here are the settings to tweak in org-async.

  1. Set process-adaptive-read-buffering to nil. For whatever reason, Emacs throttles how much it reads in the initial part of the latex/dvisvgm/dvipng process. With this setting it just reads stuff as it comes in.

  2. Set process-connection-type to nil: Use a pipe instead of a pty. With a pty connection, Emacs is capped at 4 KB reads. With a pipe, it's capped at the value of read-process-output-max, which can be anything.

  3. Increase read-process-output-max: We don't want a very large value (> 64 KB), since processing up to this much output at once causes Emacs to become unresponsive. At the same time, we don't want it as low as 4 KB (the default) either.

The question is the following: We cannot let-bind these variables around calls to org-async, because the let-binds won't be active when the filters/sentinels run later. So these have to be either chosen by the user via a keyword argument to org-async, or (this is simpler) org-async must make reasonable choices and apply them to all processes it runs.

I'm in favor of the latter. I suggest simply setting process-adaptive-read-buffering to nil, process-connection-type to t and not setting read-process-output-max at all. (Users tend to be opinionated about this last option.)

On W32 systems, the relevant parameter is w32-pipe-buffer-size.


This diagnosis was achieved after much hair-pulling and discussion. Relevant emacs-devel thread: https://lists.gnu.org/archive/html/emacs-devel/2023-07/msg00722.html

tecosaur commented 6 months ago

Ok, so process-adaptive-read-buffering and process-connection-type can be set to nil everywhere, but I'm not sure what we should/shouldn't do about read-process-output-max (I've currently got it so that it can be set on a per-call basis).

yantar92 commented 6 months ago

We cannot let-bind these variables around calls to org-async, because the let-binds won't be active when the filters/sentinels run later.

You can set these variables buffer-locally, for example.

tecosaur commented 6 months ago

This is how I'm currently solving the problem: https://git.tecosaur.net/tec/org-mode/commit/d1a3a6d126

yantar92 commented 6 months ago

tecosaur @.***> writes:

This is how I'm currently solving the problem: https://git.tecosaur.net/tec/org-mode/commit/d1a3a6d126

That also works. Nitpick: Why not using `assq' in all the cases?

-- Ihor Radchenko // yantar92, Org mode contributor, Learn more about Org mode at https://orgmode.org/. Support Org development at https://liberapay.com/org-mode, or support my work at https://liberapay.com/yantar92

tecosaur commented 6 months ago

Nitpick: Why not using `assq' in all the cases?

Well, nil is a valid value and if we have (or (assq ...) default) then you can't explicitly provide nil. Given that the default is nil I suppose this would be fine here, but that was my thinking while writing the code.

tecosaur commented 5 months ago

@karthink anything left to do here?

karthink commented 5 months ago

We could reduce the pipe size from 64 KB to 16 KB to improve responsiveness on the median computer.