unofficial mirror of bug-gnu-emacs@gnu.org 
 help / color / mirror / code / Atom feed
* bug#10941: [24.0.93.3] cc-mode: error in message buffer when "typing fast", characters eaten
@ 2012-03-04 18:14 Paul Pogonyshev
  2012-03-29 21:48 ` Alan Mackenzie
  0 siblings, 1 reply; 6+ messages in thread
From: Paul Pogonyshev @ 2012-03-04 18:14 UTC (permalink / raw)
  To: 10941

[-- Attachment #1: Type: Text/Plain, Size: 918 bytes --]

Sometimes (quite often) when opening a different syntax region --- a
quoted string, or block comment --- in C++ mode, the first character
after it gets eaten with some error message shown in the echo area.  I
managed to create a surefire (at least here) way to reproduce it.

* save the attached file as 'test.cpp' (it is quite large, but when I
  tried to shorten it substantially, error disappeared);

* start Emacs as 'emacs -Q test.cpp';

* issue Elisp command right at the start of the buffer with M-: (this
  emulates fast typing):

      (progn (insert "/*") (insert " "))

  note that two separate inserts are essential, with one "/* " error
  is not triggered;

* observer the following error:

      Debugger entered--Lisp error: (error "Invalid search bound
      (wrong side of point)")

Full Emacs version: GNU Emacs 24.0.93.3 (x86_64-unknown-linux-gnu,
GTK+ Version 2.24.10) of 2012-02-25 on gonzo

Paul

[-- Attachment #2: test.cpp --]
[-- Type: text/x-c++src, Size: 3990 bytes --]

namespace mct
{

  // Templated structure specifying how given type could be used by its container (in
  // broad sense), i.e. "externally".  Default is no external use; it can be enabled by
  // specializing the structure.
  template <typename Type, typename = void>
  struct external_use
  { };


  template <typename Type, typename = Type>
  struct supports_external_use : impl::false_type
  { };

  template <typename Type>
  struct supports_external_use <Type, typename external_use <Type>::type> : impl::true_type
  { };


  template <typename Type, typename Value, Value Type::* field,
            bool direct_access = (impl::is_integral <Value>::value
                                  && !impl::is_same <Value, bool>::value),
            bool recurse       = supports_external_use <Value>::value>
  struct extern_use_field;

  template <typename Type, typename Value, Value Type::* field>
  struct extern_use_field <Type, Value, field, true, false>
  {
    typedef  Type   type;
    typedef  Value  value_type;

    static  const value_type&
    get (const type& structure)
    {  return structure.*field;  }

    static  void
    set (type& structure, const value_type& value)
    {  structure.*field = value;  }
  };

  template <typename Type, typename Value, Value Type::* field>
  struct extern_use_field <Type, Value, field, false, true>
  {
    typedef  Type                                       type;
    typedef  typename external_use <Value>::value_type  value_type;

    static  const value_type&
    get (const type& structure)
    {
      return external_use <Value>::get (structure.*field);
    }

    static  void
    set (type& structure, const value_type& value)
    {
      external_use <Value>::set (structure.*field, value);
    }
  };


  template <typename First, typename Second>
  struct external_use <std::pair <First, Second>,
                       typename impl::enable_if <supports_external_use <First>::value>::type>
    : extern_use_field <std::pair <First, Second>, First, &std::pair <First, Second>::first>
  { };

  template <typename First, typename Second>
  struct external_use <std::pair <First, Second>,
                       typename impl::enable_if <supports_external_use <Second>::value
                                                 && !supports_external_use <First>::value>::type>
    : extern_use_field <std::pair <First, Second>, Second, &std::pair <First, Second>::second>
  { };


  namespace impl
  {

    // By default the structure is empty.  'intrusive_storage' below makes sure to never
    // use it when it's empty, i.e. of size 1.
    template <typename type, typename = void>
    struct extern_use_wrapper
    { };


# if 0

    // Ideally we'd want this, but see comment in the preprocessor-enabled branch.
    template <typename type>
    struct extern_use_wrapper <type, typename impl::enable_if <std::is_class <type>::value>::type>
      : type
    // ...

# else

    // We currently specialize 'extern_use_wrapper' very conservatively.  At least GCC up
    // to 4.6 doesn't provide 'std::is_class', so there is no reliable way to determine if
    // 'type' is subclassable without requiring a recent compiler.  The most important
    // case, especially for maps, is 'std::pair', so we limit ourselves to that for now.
    template <typename First, typename Second>
    struct extern_use_wrapper <std::pair <First, Second> > : std::pair <First, Second>
    {
      typedef  std::pair <First, Second>  base_type;

      char  _unused;

      extern_use_wrapper&
      operator= (const extern_use_wrapper& that)
      {
        return static_cast <extern_use_wrapper&> (base_type::operator= (that));
      }

#   if MCT_CXX0X_SUPPORTED

      extern_use_wrapper&
      operator= (extern_use_wrapper&& that)
      {
        return static_cast <extern_use_wrapper&> (base_type::operator=
                                                  (std::forward <base_type> (that)));
      }

#   endif
    };

# endif

  }

}

^ permalink raw reply	[flat|nested] 6+ messages in thread

* bug#10941: [24.0.93.3] cc-mode: error in message buffer when "typing fast", characters eaten
  2012-03-04 18:14 bug#10941: [24.0.93.3] cc-mode: error in message buffer when "typing fast", characters eaten Paul Pogonyshev
@ 2012-03-29 21:48 ` Alan Mackenzie
  2012-03-29 22:11   ` Paul Pogonyshev
  2012-04-11 18:19   ` Alan Mackenzie
  0 siblings, 2 replies; 6+ messages in thread
From: Alan Mackenzie @ 2012-03-29 21:48 UTC (permalink / raw)
  To: Paul Pogonyshev, 10941

Hi, Paul.

Thanks for this report.  I can reproduce the error.  However, looking at
the code, it "can't possibly happen".  :-(  A few questions:

> Sometimes (quite often) when opening a different syntax region --- a
> quoted string, or block comment --- in C++ mode, the first character
> after it gets eaten with some error message shown in the echo area.  I
> managed to create a surefire (at least here) way to reproduce it.

What exactly do you mean by "opening a different syntax region"?  Do you
mean moving point into it, or scrolling to see it?

> * save the attached file as 'test.cpp' (it is quite large, but when I
>   tried to shorten it substantially, error disappeared);

Aha!  It's 3991 bytes long.  I'm going to try a binary chop on the
length.  I have a strange feeling the threshold length of the file
(before insertion of "/* ") will be 2048.

> * start Emacs as 'emacs -Q test.cpp';

> * issue Elisp command right at the start of the buffer with M-: (this
>   emulates fast typing):

>       (progn (insert "/*") (insert " "))

>   note that two separate inserts are essential, with one "/* " error
>   is not triggered;

OK.  I have a suspicion it could be something like two
before-change-functions being invoked without the after-change-function
which should come between them.

Strangely, though, once this error has happened, it doesn't happen again
in the same Emacs session, even if the buffer is killed and the file
reloaded.

> * observer the following error:

>       Debugger entered--Lisp error: (error "Invalid search bound
>       (wrong side of point)")

> Full Emacs version: GNU Emacs 24.0.93.3 (x86_64-unknown-linux-gnu,
> GTK+ Version 2.24.10) of 2012-02-25 on gonzo

Paul

-- 
Alan Mackenzie (Nuremberg, Germany).





^ permalink raw reply	[flat|nested] 6+ messages in thread

* bug#10941: [24.0.93.3] cc-mode: error in message buffer when "typing fast", characters eaten
  2012-03-29 21:48 ` Alan Mackenzie
@ 2012-03-29 22:11   ` Paul Pogonyshev
  2012-03-30 22:19     ` Alan Mackenzie
  2012-04-11 18:19   ` Alan Mackenzie
  1 sibling, 1 reply; 6+ messages in thread
From: Paul Pogonyshev @ 2012-03-29 22:11 UTC (permalink / raw)
  To: Alan Mackenzie; +Cc: 10941

Alan Mackenzie wrote:
> > Sometimes (quite often) when opening a different syntax region --- a
> > quoted string, or block comment --- in C++ mode, the first character
> > after it gets eaten with some error message shown in the echo area.  I
> > managed to create a surefire (at least here) way to reproduce it.
> 
> What exactly do you mean by "opening a different syntax region"?  Do you
> mean moving point into it, or scrolling to see it?

Just typing, similarly to the testcase.  When you quickly type an
opening quote (") or inline comment starter (/*) and then instantly
continue typing whatever is going to be inside, this error happens.
Far from always, but often enough to be annoying.

> OK.  I have a suspicion it could be something like two
> before-change-functions being invoked without the after-change-function
> which should come between them.

I have a different suspicion that sometimes cc-mode relies on data
found in font-lock only and that data may or may not be present (or up
to date) depending on how fast lazy font-locking happens.  But of
course you know the code better to decide if that is possible at all.

Paul





^ permalink raw reply	[flat|nested] 6+ messages in thread

* bug#10941: [24.0.93.3] cc-mode: error in message buffer when "typing fast", characters eaten
  2012-03-29 22:11   ` Paul Pogonyshev
@ 2012-03-30 22:19     ` Alan Mackenzie
  2012-03-31 20:27       ` Paul Pogonyshev
  0 siblings, 1 reply; 6+ messages in thread
From: Alan Mackenzie @ 2012-03-30 22:19 UTC (permalink / raw)
  To: Paul Pogonyshev; +Cc: 10941

Hello, Paul.

On Fri, Mar 30, 2012 at 01:11:05AM +0300, Paul Pogonyshev wrote:
> Alan Mackenzie wrote:
> > > Sometimes (quite often) when opening a different syntax region --- a
> > > quoted string, or block comment --- in C++ mode, the first character
> > > after it gets eaten with some error message shown in the echo area.  I
> > > managed to create a surefire (at least here) way to reproduce it.

> > What exactly do you mean by "opening a different syntax region"?  Do you
> > mean moving point into it, or scrolling to see it?

> Just typing, similarly to the testcase.  When you quickly type an
> opening quote (") or inline comment starter (/*) and then instantly
> continue typing whatever is going to be inside, this error happens.
> Far from always, but often enough to be annoying.

Thanks for the description.

I think I've found the trouble.  It was a simple mistake in calculating a
search limit.  I don't understand how this only bites when the buffer is
newly loaded, but whatever.

Would you please try out this patch and let me know whether it solves the
problem.


diff -r 002a49d7b836 cc-engine.el
--- a/cc-engine.el	Fri Mar 16 13:14:22 2012 +0000
+++ b/cc-engine.el	Fri Mar 30 22:13:40 2012 +0000
@@ -5414,7 +5414,7 @@
 	  new-beg new-end need-new-beg need-new-end)
       ;; Locate the barrier before the changed region
       (goto-char  (if beg-lit-limits (car beg-lit-limits) beg))
-      (c-syntactic-skip-backward "^;{}" (max (- beg 2048) (point-min)))
+      (c-syntactic-skip-backward "^;{}" (c-determine-limit 512))
       (setq new-beg (point))
 
       ;; Remove the syntax-table/category properties from each pertinent <...>
@@ -5426,8 +5426,7 @@
 
       ;; Locate the barrier after END.
       (goto-char (if end-lit-limits (cdr end-lit-limits) end))
-      (c-syntactic-re-search-forward "[;{}]"
-				     (min (+ end 2048) (point-max)) 'end)
+      (c-syntactic-re-search-forward "[;{}]" (c-determine-+ve-limit 512) 'end)
       (setq new-end (point))
 
       ;; Remove syntax-table properties from the remaining pertinent <...>

> Paul

-- 
Alan Mackenzie (Nuremberg, Germany).





^ permalink raw reply	[flat|nested] 6+ messages in thread

* bug#10941: [24.0.93.3] cc-mode: error in message buffer when "typing fast", characters eaten
  2012-03-30 22:19     ` Alan Mackenzie
@ 2012-03-31 20:27       ` Paul Pogonyshev
  0 siblings, 0 replies; 6+ messages in thread
From: Paul Pogonyshev @ 2012-03-31 20:27 UTC (permalink / raw)
  To: Alan Mackenzie; +Cc: 10941

Alan Mackenzie wrote:
> Would you please try out this patch and let me know whether it solves the
> problem.

Sorry, I can't because that'd require a lot of coding (the bug is not
deterministic) to see if the problem is gone and I don't code
currently.  Just commit it and close the bug as long as it solves the
original testcase.

Paul





^ permalink raw reply	[flat|nested] 6+ messages in thread

* bug#10941: [24.0.93.3] cc-mode: error in message buffer when "typing fast", characters eaten
  2012-03-29 21:48 ` Alan Mackenzie
  2012-03-29 22:11   ` Paul Pogonyshev
@ 2012-04-11 18:19   ` Alan Mackenzie
  1 sibling, 0 replies; 6+ messages in thread
From: Alan Mackenzie @ 2012-04-11 18:19 UTC (permalink / raw)
  To: 10941-done

(At least partially) fixed.

-- 
Alan Mackenzie (Nuremberg, Germany).





^ permalink raw reply	[flat|nested] 6+ messages in thread

end of thread, other threads:[~2012-04-11 18:19 UTC | newest]

Thread overview: 6+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2012-03-04 18:14 bug#10941: [24.0.93.3] cc-mode: error in message buffer when "typing fast", characters eaten Paul Pogonyshev
2012-03-29 21:48 ` Alan Mackenzie
2012-03-29 22:11   ` Paul Pogonyshev
2012-03-30 22:19     ` Alan Mackenzie
2012-03-31 20:27       ` Paul Pogonyshev
2012-04-11 18:19   ` Alan Mackenzie

Code repositories for project(s) associated with this public inbox

	https://git.savannah.gnu.org/cgit/emacs.git

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).