Created attachment 132077 [details] Open files and Backtrace PREPARATION: Install node.js and npm. Install svelte-language-server with npm install -g svelte-language-server@0.10.128 Enable LSP Client. In Settings / Configure Kate... / LSP Client / User Server Settings, paste { "servers": { "html": { "command": ["node","/user/local/lib/node_modules/svelte-language-server/bin/server.js","--stdio"], "rootIndicationFileNames": ["package.json", "package-lock.json"], "highlightingModeRegex": "^.*HTML.*$", "root": "." } } } Adjust the path if your npm prefix is different from /usr/local (determine it with 'npm config get prefix'). REPRODUCING THE CRASH: 1. Extract import.html and export.js from the attached file (kate_lsp_crash.tar.gz) in the same directory. 2. Open import.html . 3. Right-click the word 'constant', and in the context menu, choose LSP Client / Go to Definition. 3'. Alternatively, do the same with the word './export'. Either way, Kate crashes. The crash can be reproduced every time. SOFTWARE VERSIONS: Qt Version: 5.15.1 Frameworks Version: 5.74.0 Operating System: Linux 5.8.10-1-default x86_64 Windowing system: X11 Distribution: "openSUSE Tumbleweed" -- Backtrace: Application: Kate (kate), signal: Segmentation fault [KCrash Handler] #4 QStandardItemPrivate::rowCount (this=<error reading variable: Cannot access memory at address 0x8>) at ../../include/QtGui/5.15.1/QtGui/private/../../../../../src/gui/itemmodels/qstandarditemmodel_p.h:166 #5 QStandardItem::rowCount (this=this@entry=0x0) at itemmodels/qstandarditemmodel.cpp:1595 #6 0x00007f70547b924e in QStandardItem::appendRow (aitem=0x563acc2ff620, this=0x0) at /usr/include/qt5/QtGui/qstandarditemmodel.h:320 #7 LSPClientActionView::makeTree (this=0x563acc1a3df0, locations=..., snapshot=0x563acd3453e0) at /usr/src/debug/kate-20.08.1-1.1.x86_64/addons/lspclient/lspclientpluginview.cpp:1059 #8 0x00007f70547c4ea1 in LSPClientActionView::processLocations<LSPLocation, true, std::function<void (QList<LSPLocation> const&)> >(QString const&, utils::identity<std::function<LSPClientServer::RequestHandle (LSPClientServer&, QUrl const&, KTextEditor::Cursor const&, QObject const*, std::function<void (QList<LSPLocation> const&)> const&)> >::type const&, bool, std::function<LSPClientActionView::RangeItem (LSPLocation const&)> const&, QPointer<QTreeView>*)::{lambda(QList<LSPLocation> const&)#1}::operator()(QList<LSPLocation> const&) const (defs=..., this=<optimized out>) at /usr/include/qt5/QtCore/qscopedpointer.h:138 #9 std::__invoke_impl<void, LSPClientActionView::processLocations<LSPLocation, true, std::function<void (QList<LSPLocation> const&)> >(QString const&, utils::identity<std::function<LSPClientServer::RequestHandle (LSPClientServer&, QUrl const&, KTextEditor::Cursor const&, QObject const*, std::function<void (QList<LSPLocation> const&)> const&)> >::type const&, bool, std::function<LSPClientActionView::RangeItem (LSPLocation const&)> const&, QPointer<QTreeView>*)::{lambda(QList<LSPLocation> const&)#1}&, QList<LSPLocation> const&>(std::__invoke_other, LSPClientActionView::processLocations<LSPLocation, true, std::function<void (QList<LSPLocation> const&)> >(QString const&, utils::identity<std::function<LSPClientServer::RequestHandle (LSPClientServer&, QUrl const&, KTextEditor::Cursor const&, QObject const*, std::function<void (QList<LSPLocation> const&)> const&)> >::type const&, bool, std::function<LSPClientActionView::RangeItem (LSPLocation const&)> const&, QPointer<QTreeView>*)::{lambda(QList<LSPLocation> const&)#1}&, QList<LSPLocation> const&) (__f=...) at /usr/include/c++/10/bits/invoke.h:60 #10 std::__invoke_r<void, LSPClientActionView::processLocations<LSPLocation, true, std::function<void (QList<LSPLocation> const&)> >(QString const&, utils::identity<std::function<LSPClientServer::RequestHandle (LSPClientServer&, QUrl const&, KTextEditor::Cursor const&, QObject const*, std::function<void (QList<LSPLocation> const&)> const&)> >::type const&, bool, std::function<LSPClientActionView::RangeItem (LSPLocation const&)> const&, QPointer<QTreeView>*)::{lambda(QList<LSPLocation> const&)#1}&, QList<LSPLocation> const&>(std::__is_invocable&&, (LSPClientActionView::processLocations<LSPLocation, true, std::function<void (QList<LSPLocation> const&)> >(QString const&, utils::identity<std::function<LSPClientServer::RequestHandle (LSPClientServer&, QUrl const&, KTextEditor::Cursor const&, QObject const*, std::function<void (QList<LSPLocation> const&)> const&)> >::type const&, bool, std::function<LSPClientActionView::RangeItem (LSPLocation const&)> const&, QPointer<QTreeView>*)::{lambda(QList<LSPLocation> const&)#1}&)...) (__fn=...) at /usr/include/c++/10/bits/invoke.h:153 #11 std::_Function_handler<void (QList<LSPLocation> const&), LSPClientActionView::processLocations<LSPLocation, true, std::function<void (QList<LSPLocation> const&)> >(QString const&, utils::identity<std::function<LSPClientServer::RequestHandle (LSPClientServer&, QUrl const&, KTextEditor::Cursor const&, QObject const*, std::function<void (QList<LSPLocation> const&)> const&)> >::type const&, bool, std::function<LSPClientActionView::RangeItem (LSPLocation const&)> const&, QPointer<QTreeView>*)::{lambda(QList<LSPLocation> const&)#1}>::_M_invoke(std::_Any_data const&, QList<LSPLocation> const&) (__functor=..., __args#0=...) at /usr/include/c++/10/bits/std_function.h:291 #12 0x00007f70547d3c33 in std::function<void (QList<LSPLocation> const&)>::operator()(QList<LSPLocation> const&) const (__args#0=..., this=0x7f7050014b40) at /usr/include/c++/10/bits/std_function.h:617 #13 operator() (m=..., this=0x7f7050014b30) at /usr/src/debug/kate-20.08.1-1.1.x86_64/addons/lspclient/lspclientserver.cpp:1291 #14 std::__invoke_impl<void, make_handler<QList<LSPLocation> >::<lambda(const GenericReplyType&)>&, const QJsonValue&> (__f=...) at /usr/include/c++/10/bits/invoke.h:60 #15 std::__invoke_r<void, make_handler<QList<LSPLocation> >::<lambda(const GenericReplyType&)>&, const QJsonValue&> (__fn=...) at /usr/include/c++/10/bits/invoke.h:153 #16 std::_Function_handler<void(const QJsonValue&), make_handler<QList<LSPLocation> >::<lambda(const GenericReplyType&)> >::_M_invoke(const std::_Any_data &, const QJsonValue &) (__functor=..., __args#0=...) at /usr/include/c++/10/bits/std_function.h:291 #17 0x00007f70547ce87d in std::function<void (QJsonValue const&)>::operator()(QJsonValue const&) const (__args#0=..., this=0x7ffd3b2c85e0) at /usr/include/c++/10/bits/std_function.h:617 #18 LSPClientServer::LSPClientServerPrivate::read (this=<optimized out>) at /usr/src/debug/kate-20.08.1-1.1.x86_64/addons/lspclient/lspclientserver.cpp:972 #19 0x00007f705b56f646 in QtPrivate::QSlotObjectBase::call (a=0x7ffd3b2c8700, r=0x563acd1e8038, this=0x563acd324690) at ../../include/QtCore/../../src/corelib/kernel/qobjectdefs_impl.h:398 #20 doActivate<false> (sender=0x563acd1e8038, signal_index=3, argv=0x7ffd3b2c8700, argv@entry=0x0) at kernel/qobject.cpp:3886 #21 0x00007f705b5689a0 in QMetaObject::activate (sender=sender@entry=0x563acd1e8038, m=m@entry=0x7f705b8192c0, local_signal_index=local_signal_index@entry=0, argv=argv@entry=0x0) at kernel/qobject.cpp:3946 #22 0x00007f705b46a8b0 in QIODevice::readyRead (this=this@entry=0x563acd1e8038) at .moc/moc_qiodevice.cpp:190 #23 0x00007f705b4ac677 in QProcessPrivate::tryReadFromChannel (this=0x563acd2f2a70, channel=0x563acd2f2b80) at io/qprocess.cpp:1068 #24 0x00007f705b4aca95 in QProcessPrivate::_q_canReadStandardError (this=<optimized out>) at io/qprocess.cpp:1084 #25 QProcess::qt_static_metacall (_o=<optimized out>, _c=<optimized out>, _id=<optimized out>, _a=0x7ffd3b2c88d0) at .moc/moc_qprocess.cpp:210 #26 0x00007f705b56f680 in doActivate<false> (sender=0x563acd126d90, signal_index=3, argv=argv@entry=0x7ffd3b2c88d0) at ../../include/QtCore/../../src/corelib/kernel/qobjectdefs_impl.h:395 #27 0x00007f705b5689a0 in QMetaObject::activate (sender=sender@entry=0x563acd126d90, m=m@entry=0x7f705b81cb00 <QSocketNotifier::staticMetaObject>, local_signal_index=local_signal_index@entry=0, argv=argv@entry=0x7ffd3b2c88d0) at kernel/qobject.cpp:3946 #28 0x00007f705b572a7f in QSocketNotifier::activated (this=this@entry=0x563acd126d90, _t1=..., _t2=<optimized out>, _t3=...) at .moc/moc_qsocketnotifier.cpp:178 #29 0x00007f705b57327b in QSocketNotifier::event (this=0x563acd126d90, e=0x7ffd3b2c89e0) at kernel/qsocketnotifier.cpp:302 #30 0x00007f705c0d514f in QApplicationPrivate::notify_helper (this=<optimized out>, receiver=0x563acd126d90, e=0x7ffd3b2c89e0) at kernel/qapplication.cpp:3630 #31 0x00007f705b53905a in QCoreApplication::notifyInternal2 (receiver=0x563acd126d90, event=0x7ffd3b2c89e0) at ../../include/QtCore/5.15.1/QtCore/private/../../../../../src/corelib/thread/qthread_p.h:325 #32 0x00007f705b591165 in socketNotifierSourceDispatch (source=0x563acbc2cb70) at kernel/qeventdispatcher_glib.cpp:107 #33 0x00007f70595442b7 in g_main_context_dispatch () from /usr/lib64/libglib-2.0.so.0 #34 0x00007f7059544638 in ?? () from /usr/lib64/libglib-2.0.so.0 #35 0x00007f70595446ef in g_main_context_iteration () from /usr/lib64/libglib-2.0.so.0 #36 0x00007f705b5905af in QEventDispatcherGlib::processEvents (this=0x563acbc2f450, flags=...) at kernel/qeventdispatcher_glib.cpp:423 #37 0x00007f705b537a1b in QEventLoop::exec (this=this@entry=0x7ffd3b2c8bf0, flags=..., flags@entry=...) at ../../include/QtCore/../../src/corelib/global/qflags.h:141 #38 0x00007f705b53fc90 in QCoreApplication::exec () at ../../include/QtCore/../../src/corelib/global/qflags.h:121 #39 0x0000563acaaff959 in main (argc=<optimized out>, argv=<optimized out>) at /usr/src/debug/kate-20.08.1-1.1.x86_64/kate/main.cpp:633 [Inferior 1 (process 29378) detached]
Git commit ea4fe985c9123adc3f67d07c1ae60bac4da52813 by Christoph Cullmann. Committed on 03/10/2020 at 15:07. Pushed by cullmann into branch 'master'. ensure that even if the url is empty, we create some parent to avoid accessing nullptr parent M +2 -1 addons/lspclient/lspclientpluginview.cpp https://invent.kde.org/utilities/kate/commit/ea4fe985c9123adc3f67d07c1ae60bac4da52813
Thanks for well done report, the back trace was very useful. If you can, you could try to test a kate master branch version with this fix. See https://kate-editor.org/build-it/
Created attachment 132105 [details] LSP's input
Created attachment 132106 [details] LSP's output
Thank you, it doesn't crash anymore. However, it still doesn't actually go to the definition: it does nothing. I attach the language server's input and output after I try to go to the definition of 'constant' in 'import.html' (from the earlier attachment). I'm not familiar with the language server protocol, so I don't know if the server's reply is conformant, but it seems to contain the relevant information. Should I open a separate bug report for this one?
Perhaps Mark has some idea for that. But good that it at least no longer crashs, that shouldn't happen with any input, sorry that we had that :/ Let's reopen the bug until that is clarified.
Git commit 229443cc15e61fd23e5d616a46cdc3b36bb1d128 by Christoph Cullmann. Committed on 04/10/2020 at 13:44. Pushed by cullmann into branch 'release/20.08'. ensure that even if the url is empty, we create some parent to avoid accessing nullptr parent (cherry picked from commit ea4fe985c9123adc3f67d07c1ae60bac4da52813) M +2 -1 addons/lspclient/lspclientpluginview.cpp https://invent.kde.org/utilities/kate/commit/229443cc15e61fd23e5d616a46cdc3b36bb1d128
Oops, the crash is obviously bad, but is fortunately plugged now. As for it not working (and the Url turning empty), that is actually a server-side problem. As specified (https://microsoft.github.io/language-server-protocol/specifications/specification-current/#textDocument_definition) the reply to a 'textDocument/definition') can be one of Location, or Location[] or LocationLink[]. However, the latter depends on the client specifying it is so capable (which allows extending the protocol without surprising existing client). As it stands, the client does not support that reply nor does it claim to in reported capabilities, so the server should not resort to sending that type of reply. It's not difficult to extend parsing to handle that reply as well (and will likely do so in the coming days), but such is the background of the situation.
(In reply to Mark Nauwelaerts from comment #8) > As for it not working (and the Url turning empty), that is actually a > server-side problem. Thank you for looking at it, I've reported it to the server project ( https://github.com/sveltejs/language-tools/issues/592 ).
Git commit 98876895d629baa573e50f9337ec4e06ed0f9c6d by Mark Nauwelaerts. Committed on 06/10/2020 at 17:46. Pushed by mnauwelaerts into branch 'master'. lspclient: also secretly accept LocationLink in some replies M +22 -1 addons/lspclient/lspclientserver.cpp https://invent.kde.org/utilities/kate/commit/98876895d629baa573e50f9337ec4e06ed0f9c6d
The above commit adds some additional (fallback) parsing client-side, so it should be able to handle the response now.