Bug 485093 - openconnect plugin crashes after receiving answer from Palo Alto Networks GlobalProtect auth
Summary: openconnect plugin crashes after receiving answer from Palo Alto Networks Glo...
Status: CONFIRMED
Alias: None
Product: plasmashell
Classification: Plasma
Component: Networks widget (show other bugs)
Version: master
Platform: Other Linux
: NOR crash
Target Milestone: 1.0
Assignee: Plasma Bugs List
URL:
Keywords:
: 486660 (view as bug list)
Depends on:
Blocks:
 
Reported: 2024-04-05 16:10 UTC by Thiago Macieira
Modified: 2024-12-23 18:25 UTC (History)
3 users (show)

See Also:
Latest Commit:
Version Fixed In:
Sentry Crash Report:


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description Thiago Macieira 2024-04-05 16:10:42 UTC
SUMMARY
When trying to authenticate with PAN's GP server, the openconnect plugin reliably crashes kded6 after receiving the answer. I am unsure if this is a regression or not: I did manage to log in a few times, initially, but I don't know if there's some setting stored away that may be influencing the result.

STEPS TO REPRODUCE
1. Start the VPN with PAN GP
2. Perform the OAuth2 authentication (including, in my case, the Microsoft Authenticator's approval)

OBSERVED RESULT
The dialog disappears, the VPN does not come on, and kded6 has crashed.

EXPECTED RESULT
Connection comes up

SOFTWARE/OS VERSIONS
KDE Plasma Version: 6.0.3
KDE Frameworks Version: 6.0.0
Qt Version: 6.6.3

ADDITIONAL INFORMATION
Backtrace:
#3  0x00007f2200241240 in <signal handler called> () at /lib64/libc.so.6
#4  0x00007f21db52e67b in OpenconnectAuthWidget::formLoginClicked() (this=<optimized out>)
    at /usr/src/debug/plasma-nm-6.0.3/vpn/openconnect/openconnectauth.cpp:833
#5  0x00007f2200bbb441 in QObject::event(QEvent*) () at /lib64/glibc-hwcaps/x86-64-v4/libQt6Core.so.6.6.3
#6  0x00007f2201fc1a7e in QApplicationPrivate::notify_helper(QObject*, QEvent*) () at /lib64/libQt6Widgets.so.6
#7  0x00007f2200b782f8 in QCoreApplication::notifyInternal2(QObject*, QEvent*) () at /lib64/glibc-hwcaps/x86-64-v4/libQt6Core.so.6.6.3
#8  0x00007f2200b78635 in QCoreApplicationPrivate::sendPostedEvents(QObject*, int, QThreadData*) () at /lib64/glibc-hwcaps/x86-64-v4/libQt6Core.so.6.6.3
#9  0x00007f2200da0c73 in  () at /lib64/glibc-hwcaps/x86-64-v4/libQt6Core.so.6.6.3
#10 0x00007f2200912710 in  () at /lib64/libglib-2.0.so.0
#11 0x00007f2200914358 in  () at /lib64/libglib-2.0.so.0
#12 0x00007f2200914a0c in g_main_context_iteration () at /lib64/libglib-2.0.so.0
#13 0x00007f2200d9e8ec in QEventDispatcherGlib::processEvents(QFlags<QEventLoop::ProcessEventsFlag>) ()
    at /lib64/glibc-hwcaps/x86-64-v4/libQt6Core.so.6.6.3
#14 0x00007f2200b829bb in QEventLoop::exec(QFlags<QEventLoop::ProcessEventsFlag>) () at /lib64/glibc-hwcaps/x86-64-v4/libQt6Core.so.6.6.3
#15 0x00007f2200b7b752 in QCoreApplication::exec() () at /lib64/glibc-hwcaps/x86-64-v4/libQt6Core.so.6.6.3
#16 0x000055e1abd58522 in  ()
#17 0x00007f220022a1f0 in __libc_start_call_main () at /lib64/libc.so.6
#18 0x00007f220022a2b9 in __libc_start_main_impl () at /lib64/libc.so.6

Line 833 in this version is <https://invent.kde.org/plasma/plasma-nm/-/blob/v6.0.3/vpn/openconnect/openconnectauth.cpp?ref_type=tags#L833>:
    QLayout *layout = d->ui.loginBoxLayout->itemAt(d->passwordFormIndex)->layout();

The debuggers says this is a null pointer dereference. Because both itemAt() and layout() are virtual functions, it's hard to follow in the disassembly where exactly we are in this statement. I think it's between itemAt() and layout().

The d pointer is valid:
(gdb) p d
$3 = {ui = {verticalLayout = 0x55e1ad165530, horizontalLayout_3 = 0x55e1ad7aa670, label_3 = 0x55e1ad102a30, cmbHosts = 0x55e1ad7aa750, 
    btnConnect = 0x55e1ad5ff8f0, chkAutoconnect = 0x55e1ad5ff530, chkStorePasswords = 0x55e1ad5ff560, loginBox = 0x55e1ad110820, 
    loginBoxLayout = 0x55e1ad5ff590, serverLogBox = 0x55e1ad602df0, logLayout = 0x55e1ad602e20, horizontalLayout_2 = 0x55e1ad603140, 
    viewServerLog = 0x55e1ad603330, lblLogLevel = 0x55e1ad5b9f30, cmbLogLevel = 0x55e1ad5b9f90, serverLog = 0x55e1ad5b6bd0}, setting = {
    value = 0x55e1ad14b320, d = 0x55e1ad4050a0}, vpninfo = 0x55e1ad7ab500, secrets = {d = {d = 0x55e1ad5ff1b0}}, tmpSecrets = {d = {d = 0x0}}, 
  mutex = {<QBasicMutex> = {d_ptr = {_q_value = std::atomic<QMutexPrivate *> = { 0x0 }}}, <No data fields>}, workerWaiting = {d = 0x55e1ad5bb230}, 
  worker = 0x55e1ad5fa120, 
  hosts = {<QListSpecialMethods<<unnamed struct> >> = {<QListSpecialMethodsBase<<unnamed struct> >> = {<No data fields>}, <No data fields>}, d = {
      d = 0x55e1ad5ff150, ptr = 0x55e1ad5ff160, size = 1}}, userQuit = false, formGroupChanged = true, cancelPipes = {48, 52}, 
  serverLog = {<QListSpecialMethods<std::pair<QString, int> >> = {<QListSpecialMethodsBase<std::pair<QString, int> >> = {<No data fields>}, <No data fields>}, d = {d = 0x55e1ade09460, ptr = 0x55e1ade09470, size = 49}}, passwordFormIndex = 1, tokenMode = {d = {d = 0x55e1ad7ac500, 
      ptr = 0x55e1ad7ac510 "disabled", size = 8}}, token = {tokenMode = OC_TOKEN_MODE_NONE, tokenSecret = {d = {d = 0x0, ptr = 0x0, size = 0}}}, 
  waitForWebEngineFinish = {<QBasicAtomicPointer<QSemaphore>> = {_q_value = std::atomic<QSemaphore *> = { 0x0 }}, <No data fields>}}

and so is d->ui.loginBoxLayout:
(gdb) p *d->ui.loginBoxLayout
$2 = {<QBoxLayout> = {<QLayout> = {<QObject> = {<No data fields>}, <QLayoutItem> = {_vptr.QLayoutItem = 0x7f2202534268 <vtable for QVBoxLayout+304>, 
        align = {i = 0}}, }, }, }

It says QObject has no data fields because I didn't have the debugging info for QtCore installed during this. But decoding memory shows its d pointer to be 0x55e1ad0cbe10, which is valid and decodes to:

$3 = {<QLayoutPrivate> = {<QObjectPrivate> = {<No data fields>}, insideSpacing = -1, userLeftMargin = -1, userTopMargin = -1, userRightMargin = -1, 
    userBottomMargin = -1, topLevel = 1, enabled = 1, activated = 0, autoNewChild = 0, constraint = QLayout::SetDefaultConstraint, rect = {x1 = 0, 
      y1 = 0, x2 = -1, y2 = -1}, menubar = 0x0}, 
  list = {<QListSpecialMethods<QBoxLayoutItem*>> = {<QListSpecialMethodsBase<QBoxLayoutItem*>> = {<No data fields>}, <No data fields>}, d = {
      d = 0x55e1ade80da0, ptr = 0x55e1ade80dc0, size = 0}}, 
  geomArray = {<QListSpecialMethods<QLayoutStruct>> = {<QListSpecialMethodsBase<QLayoutStruct>> = {<No data fields>}, <No data fields>}, d = {
      d = 0x7f21050dffa0, ptr = 0x7f21050dffb0, size = 0}}, hfwWidth = -1, hfwHeight = -1, hfwMinHeight = 18, sizeHint = {wd = 18, ht = 12}, minSize = {
    wd = 18, ht = 12}, maxSize = {wd = 524299, ht = 1048586}, leftMargin = 6, topMargin = 6, rightMargin = 6, bottomMargin = 6, expanding = {i = 0}, 
  hasHfw = 0, dirty = 1, dir = QBoxLayout::TopToBottom, spacing = -1}

Since d->passwordFormIndex == 1, we QBoxLayout::itemAt will have returned nullptr (see size = 0):
    return index >= 0 && index < d->list.size() ? d->list.at(index)->item : nullptr;

Conclusion: the stored layout seems to have become rather empty.

Possibly related to bug 484874.
Comment 1 Thiago Macieira 2024-04-25 14:38:14 UTC
Still happening on 6.0.4

Backtrace:
#3  0x00007f7d3ae41240 in <signal handler called> () at /lib64/libc.so.6
#4  0x00007f7d16065a0b in OpenconnectAuthWidget::formLoginClicked() (this=<optimized out>)
    at /usr/src/debug/plasma-nm-6.0.4/vpn/openconnect/openconnectauth.cpp:833
#5  0x00007f7d3b7c2c41 in QObject::event(QEvent*) () at /lib64/glibc-hwcaps/x86-64-v4/libQt6Core.so.6.7.0
#6  0x00007f7d3cbc2f1e in QApplicationPrivate::notify_helper(QObject*, QEvent*) () at /lib64/libQt6Widgets.so.6
#7  0x00007f7d3b77e618 in QCoreApplication::notifyInternal2(QObject*, QEvent*) () at /lib64/glibc-hwcaps/x86-64-v4/libQt6Core.so.6.7.0
#8  0x00007f7d3b77e95e in QCoreApplicationPrivate::sendPostedEvents(QObject*, int, QThreadData*) () at /lib64/glibc-hwcaps/x86-64-v4/libQt6Core.so.6.7.0
#9  0x00007f7d3b9af653 in  () at /lib64/glibc-hwcaps/x86-64-v4/libQt6Core.so.6.7.0
#10 0x00007f7d3b112710 in  () at /lib64/libglib-2.0.so.0
#11 0x00007f7d3b114358 in  () at /lib64/libglib-2.0.so.0
#12 0x00007f7d3b114a0c in g_main_context_iteration () at /lib64/libglib-2.0.so.0
#13 0x00007f7d3b9ad09c in QEventDispatcherGlib::processEvents(QFlags<QEventLoop::ProcessEventsFlag>) () at /lib64/glibc-hwcaps/x86-64-v4/libQt6Core.so.6.7.0
#14 0x00007f7d3b78953b in QEventLoop::exec(QFlags<QEventLoop::ProcessEventsFlag>) () at /lib64/glibc-hwcaps/x86-64-v4/libQt6Core.so.6.7.0
#15 0x00007f7d3b782082 in QCoreApplication::exec() () at /lib64/glibc-hwcaps/x86-64-v4/libQt6Core.so.6.7.0
#16 0x000055882d76f532 in  ()
#17 0x00007f7d3ae2a1f0 in __libc_start_call_main () at /lib64/libc.so.6
#18 0x00007f7d3ae2a2b9 in __libc_start_main_impl () at /lib64/libc.so.6
#19 0x000055882d76f895 in  ()

As before, d->passwordFormIndex = 1 and the layout's item list is:
$6 = {
  <QListSpecialMethods<QBoxLayoutItem*>> = {
    <QListSpecialMethodsBase<QBoxLayoutItem*>> = {<No data fields>}, <No data fields>}, 
  members of QList<QBoxLayoutItem*>:
  d = {
    d = 0x5588307c9270,
    ptr = 0x5588307c9290,
    size = 0
  }
}
Comment 2 Nicolas Fella 2024-05-07 22:16:17 UTC
*** Bug 486660 has been marked as a duplicate of this bug. ***
Comment 3 Thiago Macieira 2024-05-16 14:19:52 UTC
I think you can reproduce this without having a valid login. Just start connecting so the web view shows, then click anywhere outside of that. kded will crash.
Comment 4 Ben Cooksley 2024-12-23 18:25:47 UTC
Bulk transfer as requested in T17796