Assert problem in SearchDynamicEventTable() when calling a calltip from within a styled text ctrl Topic is solved

If you are using the main C++ distribution of wxWidgets, Feel free to ask any question related to wxWidgets development here. This means questions regarding to C++ and wxWidgets, not compile problems.
Post Reply
TobiasA
Knows some wx things
Knows some wx things
Posts: 38
Joined: Mon Aug 28, 2017 8:42 am

Assert problem in SearchDynamicEventTable() when calling a calltip from within a styled text ctrl

Post by TobiasA » Fri Oct 12, 2018 11:21 am

Im getting the error "assert "nNew != dynamicEvents.size()" failed in SearchDynamicEventTable()." when showing a call tip with the DWELL_START event from a styledtextctrl although the code worked for quite some time now.

Call stack is:
#0 ?? wxEvtHandler::SearchDynamicEventTable (this=0x833c440, event=...) (../../src/common/event.cpp:1898)
#1 0x3f3b573 wxEvtHandler::TryHereOnly(this=0x833c440, event=...) (../../src/common/event.cpp:1589)
#2 0x3f9e580 wxEvtHandler::TryBeforeAndHere(this=0x833c440, event=...) (../../include/wx/event.h:3873)
#3 0x3f3b3ab wxEvtHandler::ProcessEventLocally(this=0x833c440, event=...) (../../src/common/event.cpp:1526)
#4 0x3f3b34c wxEvtHandler::ProcessEvent(this=0x833c440, event=...) (../../src/common/event.cpp:1499)
#5 0x5a41611 wxStyledTextCtrl::NotifyParent(this=0x833c440, _scn=0x13df6e4) (../../src/stc/stc.cpp:5578)
#6 0x5a4a35b ScintillaWX::NotifyParent(this=0x833c820, scn=...) (../../src/stc/ScintillaWX.cpp:492)
#7 0x5a5ea44 Editor::NotifyDwelling(this=0x833c820, pt=..., state=true) (../../src/stc/scintilla/src/Editor.cxx:2498)
#8 0x5a6b14d Editor::TickFor(this=0x833c820, reason=Editor::tickDwell) (../../src/stc/scintilla/src/Editor.cxx:4978)
#9 0x5b8af20 wxSTCTimer::Notify(this=0x83472c0) (../../src/stc/ScintillaWX.cpp:65)
#10 0x3f9d7e8 wxTimerImpl::Notify(this=0x8347328) (../../include/wx/private/timer.h:47)
#11 0x3f29c70 wxProcessTimer(timer=...) (../../src/msw/timer.cpp:160)
#12 0x3f29cdd wxTimerWndProc(HWND__*, unsigned int, unsigned int, long)@16(hWnd=0x1e192e, message=275, wParam=40, lParam=0) (../../src/msw/timer.cpp:173)
#13 0x75a1e0bb USER32!AddClipboardFormatListener() (C:\Windows\System32\user32.dll:??)
#14 0x75a28849 USER32!EndTask() (C:\Windows\System32\user32.dll:??)
#15 0x3f29c73 wxProcessTimer(timer=...) (../../src/msw/timer.cpp:161)
#16 0x1e192e ?? () (??:??)
#17 0x113 ?? () (??:??)
#18 0x28 ?? () (??:??)
#19 ?? ?? () (??:??)
WxWidgets is 3.1.1 on Windows 10. If I comment the call tip out, it seems that it does not happen (although I'm not sure).
I have all events connected and disconnected properly, but as soon as the call tip pops up, it throws me this.
But: It only happens in about 1% or less of the call tips.
A call tip is shown by connecting the DWELL event and calling CallTipShow(pos,string) inside that function.
I tried wxUpdateLocker since I had the wild guess of having two events called at the same time, but all I can do is mess around with how often it happens.
It did not happen with wxWidgets 3.0.x or Windows 7 however... But that is a wild guess since a lot in the code has changed since then.
Have literally the same code for about a year now... And it happened after a window 10 update right now..?
Any help would be great appreciated.

Seems to happen here according to GDB:

Code: Select all

  if ( needToPruneDeleted )
    {
        size_t nNew = 0;
        for ( size_t n = 0; n != dynamicEvents.size(); n++ )
        {
            if ( dynamicEvents[n] )
                dynamicEvents[nNew++] = dynamicEvents[n];
        }

        wxASSERT( nNew != dynamicEvents.size() );
        dynamicEvents.resize(nNew);  //<<<<<--------------- GDB is in this line when I switch to the frame
    }

    return false;
Thanks for any help!
Last edited by catalin on Fri Oct 12, 2018 11:58 am, edited 1 time in total.
Reason: tags

ONEEYEMAN
Part Of The Furniture
Part Of The Furniture
Posts: 4043
Joined: Sat Apr 16, 2005 7:22 am
Location: USA, Ukraine

Re: Assert problem in SearchDynamicEventTable() when calling a calltip from within a styled text ctrl

Post by ONEEYEMAN » Fri Oct 12, 2018 2:31 pm

Hi,
Did you try the stc sample?

Thank you.

New Pagodi
Super wx Problem Solver
Super wx Problem Solver
Posts: 342
Joined: Tue Jun 20, 2006 6:47 pm
Contact:

Re: Assert problem in SearchDynamicEventTable() when calling a calltip from within a styled text ctrl

Post by New Pagodi » Fri Oct 12, 2018 3:48 pm

There was this commit about a year ago that slightly changed the dwell timer that would be used to trigger the call tip.

But it didn't really change the events used used or thrown by wxSTC in any way, so I don't think it could be responsible. Nevertheless, can you revert to the preceding commit (6c017076276a8f4f4dc00f22eb779d6682d1f68d) and see if that fixes the problem?

TobiasA
Knows some wx things
Knows some wx things
Posts: 38
Joined: Mon Aug 28, 2017 8:42 am

Re: Assert problem in SearchDynamicEventTable() when calling a calltip from within a styled text ctrl

Post by TobiasA » Fri Oct 12, 2018 4:04 pm

Yes, I did. And I already wrote a fully functional editor (some kind of IDE for specific CNC macros and screens) around it. Strange thing is that it did work on windows 7 for more than a year now in wxWidgets 3.0.x and 3.1.1 until now. I did not change a thing, and I can only reproduce it on a specific computer with a specific file (filesize?) with windows 10 enterprise. It even worked under Linux although this is more or less an alpha state there.
But I think I found it just right now.

I can only reproduce it when I actually show the tooltip. If I do not modify the GUI, it works (but doesn't show the tooltip of course).
Which then lead me to the fact that I also connected the OnIdle event to manipulate the GUI. I parse cross references and stuff in a second thread, the OnIdle routine then puts the results on the GUI when the user does not make any inputs. This is done because you can't modify the GUI in any other thread.
What I did now is writing the position and text of the calltip into some member variable, and show the calltip in the OnIdle function which is fired just a blink later than the dwell start event.
I can not reproduce the issue since back then.
My guess is that in some rare cases, the OnIdle and DwellStart event overlap in time and if both modify the GUI, it leads to the corrupted DynamicEventTable. Yes, I also use the STC_modified event which is not modifying the GUI but setting a flag to let the background thread pull the STC's text (this is made in a thread-safe routine, my wife said I'm growing grey hair shortly after :lol: ).
So all these events (which I unfortunately need) are entering a data race, effectively messing up the EventTable #-o At least I think so.
Since it is a little bit hard to reproduce it reliably, time will show if the error occurs again or not. For the time being, I think I can live with my little workaround.
I have quite some stuff going on in the DwellStart event, so it might actually take a few milliseconds to complete. It may be the case that the OnIdle event is fired at exactly the same time when the GUI is drawing the calltip, which is also the way it looks when you get to see the error. It pops up at exactly the time when the calltip is shown.
I have set the dwell time at 1000 in case someone wants to run some tests... But only someone who has in-depth-knowledge about how events of the STC are handled can say if there could actually be a data race in some extremely rare conditions.
I am not connecting or disconnecting events when this happens.

Thanks a lot for taking your time to actually read this wall of text! Input is still welcome to prove or deny my theory- I'm not completely sure if I actually solved the issue since it is very rare.

TobiasA
Knows some wx things
Knows some wx things
Posts: 38
Joined: Mon Aug 28, 2017 8:42 am

Re: Assert problem in SearchDynamicEventTable() when calling a calltip from within a styled text ctrl

Post by TobiasA » Fri Oct 12, 2018 4:17 pm

New Pagodi wrote:There was this commit about a year ago that slightly changed the dwell timer that would be used to trigger the call tip.

But it didn't really change the events used used or thrown by wxSTC in any way, so I don't think it could be responsible. Nevertheless, can you revert to the preceding commit (6c017076276a8f4f4dc00f22eb779d6682d1f68d) and see if that fixes the problem?
It is a bit hard since I can only reproduce the issue on the computer of my employer (while the tool is developed by me) and only very sporadic.
It did not happen with wxWidgets 3.0.x tho and I switched over to 3.1.1 a few months ago, where it happens with only small files, especially (or almost only) on one specific file. On this file, about 1 in 100 calltips fails, on another file, it's like 1 in 1000 and other people besides me didn't even notice yet.
I'm working with the tool on a daily base, it is really the needle in the hay stack. I don't think one can really create a real sample where it happens 100% of the time.
All the minimal samples are really cool with it.
However, I wrote another reply stating a possible reason.

I do not think that this commit could cause the issue, since moving the calltip to another function than DwellStart works. So, I do not think that firing the event is an issue, but only my specific application in the way I handle events and modify the UI does produce the issue. If throwing the event would be an issue, it would also happen when you don't show the calltip (I just commented out m_activeSTC->ShowCalltip(position,Infostring); and it works).
I have some fear that my dwell start time of 1000 is the same time as the OnIdle event... But as far as I can tell now, throwing the event and the commit you mentioned can't be part of the problem.

Post Reply