bugGNU Octave - Bugs: bug #57234, 'dbquit' in graphics system...

 
 

bug #57234: 'dbquit' in graphics system callback function can cause segfault

Submitter:  Guillaume <gyom>
Submitted:  Thu 14 Nov 2019 11:02:00 AM UTC
   
 
Category:  Interpreter Severity:  3 - Normal
Priority:  3 - Low Item Group:  Segfault, Bus Error, etc.
Status:  Patch Submitted Assigned to:  None
Originator Name:  Guillaume Open/Closed:  * Open
Release:  * dev Operating System:  * GNU/Linux
Fixed Release:  None Planned Release:  None
* Mandatory Fields

Add a New Comment Rich Markup
   

Jump to the original submission

Thu 19 Dec 2019 05:51:53 PM UTC, comment #16: 

This is not great, but I don't think we should spend excessive programmer time on what amounts to a very small fraction of Octave running time (How much time to people really spend, in the debugger, and then within graphics system callbacks?).  If there is a relatively simple way to plug up the hole and stop segfaults that would be nice, but creating an entire edifice for instantiating multiple readline instances doesn't sound like a good use of time.

Rik <rik5>
Group administrator
Thu 19 Dec 2019 05:44:18 PM UTC, comment #15: 

I think I can prevent the crash, but properly handling input inside a callback function is going to be difficult.

As far as I can tell, calling readline recursively is not going to work.  Looking at the code in main_window::run_file_in_terminal, it seems that someone must have already recognized this problem.  There, an attempt is made to jump out of the readline input loop and execute code as a function call, followed by restoring any pending input the next time readline is called.  But even that is only a partial solution since the internal readline state won't be saved and restored properly if it is called again for a separate input sequence (debugging vs. the normal command prompt).  There are functions in readline for saving and restoring part of the internal state (rl_save_state and rl_restore_state) but they appear to be incomplete and not fully functional.

I just don't see a way to fix this problem without fixing readline so that multiple instances can be created and used simultaneously.  Then the debugger (or anything that wants to get user input) could create a new readline object, use that, and then restore/redisplay the previous readline prompt when finished.

John W. Eaton <jwe>
Group administrator
Fri 13 Dec 2019 04:54:01 PM UTC, comment #14: 

Pantxo, your patch from comment #13 is a change in the right direction but there is a simpler way.  In the catch block for the execution_exception, you can just write


catch (octave::execution_exception& e)
  {
    m_interpreter.handle_exception (e);
  }


There is a lot more going on in this bug.  The reason we see the error


 terminate called after throwing an instance of 'octave::quit_debug_exception'


is that in the debugger::repl function the quitting_debugger function throws that exception outside of any try/catch block that can catch it.  Fixing that by moving the quitting_debugger call inside the try/catch block that immediately follows the call leads to an infinite loop because the execution state remains unchanged.  Fixing that mostly works but leads to a strange error  message about "dbquit may only be used when debugging" when the user presses ENTER.  That's happening because we are making recursive calls to readline without saving and restoring readline's internal state.

I'm working on fixes for all these issues but it may take a little time.  With some luck, maybe I won't break anything else!

John W. Eaton <jwe>
Group administrator
Wed 11 Dec 2019 08:35:05 PM UTC, comment #13: 

Here is the patch I have been using to show the full stack trace, as if the error hadn't been caught.

It is not exactly what Matlab does, i.e. the stack trace is populated and the error message is the original one, not the "execution error in graphics callback function" which doesn't look very useful.

(file #48047)

Pantxo Diribarne <pantxo>
Group Member
Wed 11 Dec 2019 02:38:47 PM UTC, comment #12: 

@Pantxo: Yes, you get the error message and the full stack trace:


>> testme
>> Unrecognized function or variable 'throw_an_error'.

Error in testme>clbk (line 7)
  throw_an_error ();

Error while evaluating UIControl Callback.

>> lasterr

ans =

    'Error while evaluating UIControl Callback.'

>> lasterror

ans =

  struct with fields:

       message: 'Error while evaluating UIControl Callback.'
    identifier: 'MATLAB:UndefinedFunction'
         stack: [0x1 struct]


Guillaume <gyom>
Wed 11 Dec 2019 02:28:39 PM UTC, comment #11: 

@Guillaume: About the original issue in comment #0, does Matlab show error messages in graphics callbacks? Does it show the stack trace? Does "lasterr" contain the error message or is the error somewhat cast into a warning?

Pantxo Diribarne <pantxo>
Group Member
Sat 07 Dec 2019 03:43:15 PM UTC, comment #10: 

Here's another way to demonstrate the problem.  Define the following function (can be at the command line):


function fff ()
  remove_input_event_hook ("fff");
  error ("foobar!");
endfunction


then execute


debug_on_error (true);
add_input_event_hook ("fff");


that should put you at a debug prompt.  Then enter a dbquit command and Octave will crash with


terminate called after throwing an instance of 'octave::quit_debug_exception'


I'm working on a fix so that quit_debug_exception is handled properly when it is thrown from a function that is executed in the readline event loop.

John W. Eaton <jwe>
Group administrator
Fri 06 Dec 2019 10:51:32 PM UTC, comment #9: 

Oh, I was going by the statement in comment #4 that said it was sufficient to just press enter at the prompt.  Will try to duplicate the other problem(s) now.

John W. Eaton <jwe>
Group administrator
Fri 06 Dec 2019 10:43:32 PM UTC, comment #8: 

Yes sorry, the bisection in comment #4 was done using code from bug #57354 and pressing <return>. This is closer to bug #57244, which is fixed by the patch.

If run the code from comment #3 I observe the very same as described by Rik, including the strange "pseudo-debug mode" after dbcont or dbnext.

Pantxo Diribarne <pantxo>
Group Member
Fri 06 Dec 2019 10:14:25 PM UTC, comment #7: 

The patch works fine.  But, it solves the issue over in bug #57244 (Return at debug prompt causes segfault) rather than this one.

Rik <rik5>
Group administrator
Fri 06 Dec 2019 09:41:03 PM UTC, comment #6: 

The attached change seems to fix the problem for me.  If it works for you and there are no additional problems I will push a proper changeset.


(file #48020)

John W. Eaton <jwe>
Group administrator
Fri 06 Dec 2019 07:46:44 AM UTC, comment #5: 

I'll try to take a look at this problem.

John W. Eaton <jwe>
Group administrator
Wed 04 Dec 2019 08:45:21 PM UTC, comment #4: 

As Guillaume said in bug #27544, <return> (instead of dbquit) is enough to trigger the crash.
I bisected and found that the revision that introduced this issue is


changeset:   27504:7a31b25e3252
user:        John W. Eaton <jwe@octave.org>
summary:     use shared_ptr for storing classdef and statement_list objects in parser


Adding jwe to the recepients of this report.

Pantxo Diribarne <pantxo>
Group Member
Fri 15 Nov 2019 11:03:33 PM UTC, comment #3: 

Confirmed.  I've attached an augmented test file called tst_cberr.m shown below.


function tst_cberr ()
  F = figure ();
  uicontrol (F, 'String', 'Button', 'Callback', @clbk1);
endfunction


function clbk1 (h, e)
  x = pi;
  clbk2 (h, e);
endfunction

function clbk2 (h, e)
  throw_an_error ();
endfunction


To reproduce, start Octave and then


debug_on_error (1)
tst_cberr
## Click on button in figure window
dbstack
dbquit


The dbstack command works for me and shows the chain of clbk1 and clbk2.

The dbquit command produces


terminate called after throwing an instance of 'octave::quit_debug_exception'
fatal: caught signal Aborted -- stopping myself...
Abort (core dumped)


Interestingly, if instead of dbquit, I use dbnext, I get


execution error in graphics callback function


debug> dbwhere
at top level
debug> dbnext
error: dbstep: can only be called in debug mode
octave:4>


The debugger is in a strange state where it is at the top-level, but the "debug>" prompt is still displayed.  Executing another "dbnext" is required to leave this pseudo-debug mode and return to the real Octave prompt.

Rik <rik5>
Group administrator
Fri 15 Nov 2019 09:51:29 AM UTC, comment #2: 

Ah, sorry, there was a typo in the formatting:
https://lists.gnu.org/archive/html/octave-bug-tracker/2019-11/msg00386.html

Debugging errors in callbacks is difficult as the call stack is not displayed
and only this error message appears:


execution error in graphics callback function


as, for example, here:


function testme
  F = figure ();
  uicontrol (F, 'String', 'Button', 'Callback', @clbk);
endfunction

function clbk (h, e)
  throw_an_error ();
endfunction


then if one use 'dbstop if error', click the button and type 'dbquit', there's a segfault.

Guillaume <gyom>
Thu 14 Nov 2019 08:03:34 PM UTC, comment #1: 

@Guillaume: It seems that your bug report was truncated.  I don't see what the error message is.

Also, do you have an example that can be used for testing?

Rik <rik5>
Group administrator
Thu 14 Nov 2019 11:02:00 AM UTC, original submission:  

Debugging errors in callbacks is difficult as the call stack is not displayed and only this error message appears:


execution error in graphics callback function
-verbatim+

as, for example, here:

+verbatim+
function testme
  F = figure ();
  uicontrol (F, 'String', 'Button', 'Callback', @clbk);
endfunction

function clbk (h, e)
  throw_an_error ();
endfunction


then if one use 'dbstop if error', click the button and type 'dbquit', there's a segfault.

Guillaume <gyom>

 

(Note: upload size limit is set to 16384 kB, after insertion of the required escape characters.)

Attach Files:
   
   
Comment:
   

Attached Files
file #48047:  bug#57234_show_stack.patch added by pantxo (2KiB - text/x-patch)
file #48020:  diffs.txt added by jwe (2KiB - text/plain)

 

Carbon-Copy List
  • -email is unavailable- added by jwe (Posted a comment)
  • -email is unavailable- added by pantxo (Posted a comment)
  • -email is unavailable- added by pantxo
  • -email is unavailable- added by rik5 (Posted a comment)
  • -email is unavailable- added by gyom (Submitted the item)
  •  

    There are 0 votes so far. Votes easily highlight which items people would like to see resolved in priority, independently of the priority of the item set by tracker managers.

    Only group members can vote.

     

    Follow 10 latest changes.

    Date Changed by Updated Field Previous Value => Replaced by
    2021-04-28 rik5 Dependencies- bugs #60463 is dependent
    2019-12-31 rik5 Priority5 - Normal 3 - Low
    2019-12-11 pantxo Attached File- Added bug#57234_show_stack.patch, #48047
    2019-12-06 jwe Attached File- Added diffs.txt, #48020
        StatusConfirmed Patch Submitted
    2019-12-04 pantxo Carbon-Copy- Added jwe
    2019-12-04 pantxo Dependencies- bugs #57354 is dependent
    2019-11-15 rik5 StatusNeed Info Confirmed
        SummaryUse of debugger in callbacks 'dbquit' in graphics system callback function can cause segfault
    2019-11-14 rik5 StatusNone Need Info

    Back to the top

    Powered by Savane 3.13-4448.
    Corresponding source code