Ping!

Gentlemen, any update about my suggestion below or how we should
proceed?

Arash Esbati <[email protected]> writes:

> Ciao Gabriele,
>
> Gabriele Nicolardi via bug-auctex via Bug reporting list for AUCTeX 
> <[email protected]> writes:
>
>> A regex without lookbehind cannot reliably encode "preceded by an even
>> number of backslashes" through alternation alone. 
>
> Yes, we have to try harder if we want to fix issue.
>
>> The robust fix is to capture the whole backslash run with a single,
>> non-alternating quantifier, and check its parity in Lisp:
>>
>> In texmathp-compile:
>>
>>   texmathp-toggle-regexp
>>   (concat "\\(\\\\*\\)"
>>           (regexp-opt togglers t))
>>
>> In texmathp, the toggle-scanning loop needs a matching change (group 1
>> no longer means "real toggle", it now holds the backslash run, so
>> parity must be checked before deciding to toggle):
>>
>>   (while (re-search-forward texmathp-toggle-regexp pos t)
>>     (when (zerop (mod (length (match-string-no-properties 1)) 2))
>>       (if (setq math-on (not math-on))
>>           (setq sw-match (cons (match-string-no-properties 2) 
>> (match-beginning 2)))
>>         (setq sw-match nil))))
>
> I only had a brief look at this, but within AUCTeX, we have the function
> `TeX-escaped-p' which we can use for this.  My proposal is this (look
> for the ;; Next line changed: and ;; (unless ...) added:):
>
> (defun texmathp-compile ()
>   "Compile the value of `texmathp-tex-commands' into the internal lists.
> Call this when you have changed the value of that variable without using
> customize (customize calls it when setting the variable)."
>   (interactive)
>   ;; Extract lists and regexp.
>   (setq texmathp-macros nil texmathp-environments nil)
>   (setq texmathp-memory
>         (cons texmathp-tex-commands texmathp-tex-commands-default))
>   (setq texmathp-tex-commands1 (append texmathp-tex-commands
>                                        texmathp-tex-commands-default))
>   (let ((list (reverse texmathp-tex-commands1))
>         entry type switches togglers)
>     (while (setq entry (car list))
>       (setq type (nth 1 entry)
>             list (cdr list))
>       (cond ((memq type '(env-on env-off)) (push (car entry) 
> texmathp-environments))
>             ((memq type '(arg-on arg-off)) (push (car entry) texmathp-macros))
>             ((memq type '(sw-on sw-off))   (push (car entry) switches))
>             ((memq type '(sw-toggle))      (push (car entry) togglers))))
>     (setq texmathp-onoff-regexp
>           (concat "\\(?:[^\\]\\|\\`\\)"
>                   (regexp-opt switches t))
>           texmathp-toggle-regexp
>           ;; Next line changed:
>           ;; (concat "\\([^\\$]\\|\\`\\)"
>           (concat "\\(\\`\\|\\)"
>                   (regexp-opt togglers t)))))
>
> (defun texmathp ()
>   "Determine if point is inside (La)TeX math mode.
> Returns t or nil.  Additional info is placed into `texmathp-why'.
> The functions assumes that you have (almost) syntactically correct (La)TeX in
> the buffer.
> See the variable `texmathp-tex-commands' about which commands are checked."
>   (interactive)
>   (let* ((pos (point)) math-on sw-match
>          (bound (save-excursion
>                   (if (re-search-backward
>                        (if (memq major-mode '(doctex-mode docTeX-mode))
>                            "[\n\r]%*[ \t]*[\n\r]"
>                          "[\n\r][ \t]*[\n\r]")
>                        nil 1 texmathp-search-n-paragraphs)
>                       (match-beginning 0)
>                     (point-min))))
>          (mac-match (texmathp-match-macro bound))
>          (env-match (texmathp-match-environment
>                      (if (and mac-match (> (cdr mac-match) bound))
>                          (cdr mac-match)
>                        bound)))
>          (match (cons nil bound)))
>
>     ;; Select the nearer match
>     (and env-match (setq match env-match))
>     ;; Use `>=' instead of `>' in case called inside \ensuremath{..}
>     ;; beginning just at (point-min).
>     (and mac-match (>= (cdr mac-match) (cdr match)) (setq match mac-match))
>     (setq math-on (memq (nth 1 (assoc (car match) texmathp-tex-commands1))
>                         '(env-on arg-on)))
>
>     ;; Check for switches
>     (and (not math-on)
>          (setq sw-match (texmathp-match-switch bound))
>          ;; Use `>=' instead of `>' by similar reason as above. (bug#41559)
>          (>= (cdr sw-match) (cdr match))
>          (eq (nth 1 (assoc (car sw-match) texmathp-tex-commands1)) 'sw-on)
>          (setq match sw-match math-on t))
>
>     ;; Check for togglers
>     (if (not math-on)
>         (save-excursion
>           (goto-char (cdr match))
>           (while (re-search-forward texmathp-toggle-regexp pos t)
>             ;; (unless ...) added:
>             (unless (TeX-escaped-p (1- (point)))
>               (if (setq math-on (not math-on))
>                   (setq sw-match (cons (match-string-no-properties 2) 
> (match-beginning 2)))
>                 (setq sw-match nil))))
>           (and math-on sw-match (setq match sw-match))))
>
>     ;; Store info, show as message when interactive, and return
>     (setq texmathp-why match)
>     ;; Check also if the match is inside a verbatim construct and
>     ;; return immediately nil.  This relies on the function
>     ;; `LaTeX-verbatim-p'.  We add a check here in case this library
>     ;; is used stand-alone without latex.el provided by AUCTeX
>     ;; (bug#61410) and the `major-mode' doesn't derive from `TeX-mode'
>     ;; (bug#69681):
>     (if (and (derived-mode-p 'TeX-mode)
>              (fboundp 'LaTeX-verbatim-p)
>              (LaTeX-verbatim-p (cdr match)))
>         (progn
>           (setq texmathp-why `(nil . ,(cdr match)))
>           (when (called-interactively-p 'any)
>             (message "math-mode is off: Math command in verbatim construct at 
> buffer position %d"
>                      (cdr match)))
>           nil)
>       (and (called-interactively-p 'any)
>            (message "math-mode is %s: %s begins at buffer position %d"
>                     (if math-on "on" "off")
>                     (or (car match) "new paragraph")
>                     (cdr match)))
>       (and math-on t))))
>
>> I tested it against backslash runs from N=0 up to N=101 (even and
>> odd), the original tabular/TikZ case, your \\\$ counterexample, $$
>> display math combined with backslash runs, and multi-cell tabular rows
>> -- all correct. I also confirmed the compiled regexp still lets
>> regexp-opt factor "$" and "$$" exactly as before
>> ("\\(\\\\*\\)\\($\\$?\\)"), so display math is unaffected.
>
> Can you please run your tests with the suggestion above?
>
>> For full transparency, as with my initial report: I used an AI
>> assistant (Claude) throughout this follow-up as well -- to analyze why
>> the paired-backslash regex fails structurally, to design this
>> alternative, and to build and run a test harness (an actual Emacs
>> instance, byte-compiling texmathp.el and exercising the real texmathp
>> function against dozens of cases, including the ones above) rather
>> than reasoning about the regex in the abstract. I independently
>> reviewed the test cases and the reasoning, and I'm satisfied the fix
>> and the testing are sound, but of course I'd still welcome your
>> review, especially given your closer familiarity with texmathp's
>> history and edge cases.
>
> Thanks for the disclaimer above.  Note that currently, the GNU project
> doesn't accept any code generated with LLMs until further notice.  So we
> can't install your suggestion above.  So we either find another solution
> (which I've proposed) or your change has to wait (if we agree on it).
> TBH, I'm not happy with ("\\(\\\\*\\)\\($\\$?\\)").
>
> Best, Arash



_______________________________________________
bug-auctex mailing list
[email protected]
https://lists.gnu.org/mailman/listinfo/bug-auctex
  • bug#81... Gabriele Nicolardi via bug-auctex via Bug reporting list for AUCTeX
    • b... Ikumi Keita
      • ... Gabriele Nicolardi via bug-auctex via Bug reporting list for AUCTeX
        • ... Arash Esbati
          • ... Arash Esbati
            • ... Ikumi Keita
              • ... Arash Esbati
                • ... Ikumi Keita
                • ... Gabriele Nicolardi via bug-auctex via Bug reporting list for AUCTeX
                • ... Arash Esbati
                • ... Ikumi Keita
                • ... Arash Esbati
                • ... Arash Esbati

Reply via email to