Subject: bug#16526: 24.3.50; scroll-conservatively & c-mode regression

From: Alan Mackenzie <[email-masked]>
Date: Sun, 29 Jun 2014 17:49:53 +0000

Hi, Martin.

On Sun, Jun 29, 2014 at 06:01:58PM +0200, martin rudalics wrote:
>  > scan-lists, a primitive, must be utterly robust.  syntax-ppss is too
>  > fragile to be used here without a lot of hardening.

>  > syntax-ppss's cache is rendered invalid at any operation which changes
>  > the syntax table (e.g. `modify-syntax-entry'), or changes to a different
>  > syntax table (e.g. `with-syntax-table'), or when a syntax-table text
>  > property/overlay is applied to the buffer, or even when a symbol's
>  > property list is changed when that symbol is the value of a category
>  > text property.  CC Mode does all these things, and does all of them
>  > apart from the first during run time, not merely at mode initialisation.

> How can any of these affect the cached start position of a defun before
> the position where the buffer contents were changed?

In this context, the "start of defun" means an outermost paren of some
sort, nothing more, nothing less.  Any of the changes above could disturb
this:  For example, adding an open-paren syntax-table property to a
character which thereby becomes the BOD.  Or temporarily switching to the
Pascal syntax table, where "{" and "}" are comment brackets.  I'm not
saying that something like this will happen on a regular basis, but it's
definitely possible.

>  > Also, the syntax-ppss cache's functioning is dependent upon
>  > before-change-functions, which can be bound to nil by any program at any
>  > time.

> There's an appropriate advice what to do in such case.

Primitive functions are deaf to advice.  You're surely not suggesting
that a primitive like scan-lists should become vulnerable to high-level
programmers failing to follow advice?  If this were to be done,
scan-lists would only work most of the time, not all of the time.  This
would be catastrophic for Emacs.

>  > If one were to harden syntax-ppss against all these things, one would
>  > probably end up calculating the cache from scratch every time, in
>  > effect.

> Can you give an example?

An example of what?  What I meant was, each time you used syntax-ppss
from scan-lists, you'd somehow need to be sure that a syntax-table entry
hadn't been changed, etc.  I can't really see how this would be possible.
You'd somehow need to handle constructs like

    (with-syntax-table c++-template-syntax-table
      ....
      (scan-lists (point) -1 1)
      ....)

.

>  > scan-lists is a primitive, and must function correctly regardless of any
>  > trickery which might be played on it.

> You can easily play trickery on `scan-lists' if you start it within a
> comment or string.

No.  scan-lists works according to its spec even if you start it inside a
comment/string.  It's effect is well defined.  For example if you write
parens inside a comment, C-M-n and friends do the right thing there.

> So `syntax-ppss' is at least as primitive as `scan-lists' (especially
> when the latter is used with negative COUNT).

Sorry, but that's utter rubbish.  syntax-ppss is a high-level convenience
function, which if used carefully by the lisp programmer gives correct
results.

By contrast, scan-lists does precisely what it says, no ifs and no buts.
Even with a negative COUNT.

> Anyway, IIUC this implies that CC mode can't work with `syntax-ppss' at
> all.  If that is true, then `open-paren-in-column-0-is-defun-start' was
> indeed the last resort that made editing larger files possible.

CC Mode doesn't use syntax-ppss, but I can't see how that's implied by
anything we've been discussing so far.  It does maintain its own caches
which fulfil the same purpose.  For example, there's a syntactic cache
which treats preprocessor constructs as comments, something syntax-ppss
can't do.

open-..-start being t is a kludge which works for certain types of files
and situations and not others.  It was causing hard to fathom errors in
CC Mode, particularly C and C++.

Do I take it you're not keen on enhancing find_defun_start in the manner
I suggested?

> martin

-- 
Alan Mackenzie (Nuremberg, Germany).