diff --git a/CMakeLists.txt b/CMakeLists.txt index 7e3896c6..0a7c19f4 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,132 +1,135 @@ cmake_minimum_required(VERSION 3.0) project(plasma-networkmanagement) set(PROJECT_VERSION "5.18.80") set(PROJECT_VERSION_MAJOR 5) set(QT_MIN_VERSION "5.13.0") set(KF5_MIN_VERSION "5.66.0") set(CMAKE_CXX_STANDARD 14) set(CMAKE_CXX_STANDARD_REQUIRED On) ################# set KDE specific information ################# find_package(ECM ${KF5_MIN_VERSION} REQUIRED NO_MODULE) set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} ${ECM_MODULE_PATH} ${ECM_KDE_MODULE_DIR} ${CMAKE_CURRENT_SOURCE_DIR}/cmake) include(KDEInstallDirs) include(KDECMakeSettings) include(KDECompilerSettings NO_POLICY_SCOPE) include(KDEClangFormat) include(ECMQMLModules) include(FeatureSummary) find_package(Qt5 ${QT_MIN_VERSION} CONFIG REQUIRED COMPONENTS Core DBus Quick QuickWidgets Widgets ) -find_package(KF5 REQUIRED +find_package(KF5 ${KF5_MIN_VERSION} REQUIRED + Config ConfigWidgets CoreAddons + DBusAddons Declarative I18n IconThemes Kirigami2 - KDELibs4Support + KIO Notifications Plasma Service + WidgetsAddons WindowSystem Wallet ) find_package(KF5NetworkManagerQt REQUIRED 5.42.0) find_package(KF5ModemManagerQt ${KF5_MIN_VERSION}) set_package_properties(KF5ModemManagerQt PROPERTIES TYPE OPTIONAL) ecm_find_qmlmodule(org.kde.prison 1.0) find_package(KF5Kirigami2 ${KF5_MIN_VERSION} CONFIG) set_package_properties(KF5Kirigami2 PROPERTIES DESCRIPTION "A QtQuick based components set" PURPOSE "Required at runtime by the KCMs" TYPE RUNTIME ) # Required only for getting information about NetworkManager version in CMake find_package(NetworkManager 1.4.0) set_package_properties(NetworkManager PROPERTIES TYPE REQUIRED) find_package(MobileBroadbandProviderInfo) set_package_properties(MobileBroadbandProviderInfo PROPERTIES DESCRIPTION "Database of mobile broadband service providers" URL "https://wiki.gnome.org/action/show/Projects/NetworkManager/MobileBroadband/ServiceProviders" TYPE OPTIONAL) find_package(Qca-qt5 2.1.0) set_package_properties(Qca-qt5 PROPERTIES DESCRIPTION "Support for encryption" URL "https://download.kde.org/stable/qca-qt5/" TYPE REQUIRED) find_package(KF5Prison ${KF5_MIN_VERSION}) set_package_properties(KF5Prison PROPERTIES DESCRIPTION "Prison library" URL "https://commits.kde.org/prison" TYPE RUNTIME PURPOSE "Needed to create mobile barcodes for WiFi networks" ) if (DISABLE_MODEMMANAGER_SUPPORT) message(STATUS "Disabling ModemManager support") set(WITH_MODEMMANAGER_SUPPORT 0) else() if (KF5ModemManagerQt_FOUND) message(STATUS "Enabling ModemManager support") set(WITH_MODEMMANAGER_SUPPORT 1) else() message(STATUS "ModemManager or ModemManagerQt not found") set(WITH_MODEMMANAGER_SUPPORT 0) endif() endif() add_definitions(-DQT_DISABLE_DEPRECATED_BEFORE=0) add_definitions(-DQT_USE_FAST_OPERATOR_PLUS) add_definitions(-DQT_NO_URL_CAST_FROM_STRING) remove_definitions(-DQT_NO_CAST_FROM_ASCII -DQT_NO_CAST_FROM_BYTEARRAY) add_definitions(-DWITH_MODEMMANAGER_SUPPORT=${WITH_MODEMMANAGER_SUPPORT}) include_directories(${CMAKE_CURRENT_SOURCE_DIR}/libs ${CMAKE_CURRENT_SOURCE_DIR}/libs/editor/) add_subdirectory(applet) add_subdirectory(kded) add_subdirectory(kcm) add_subdirectory(libs) add_subdirectory(vpn) if (BUILD_MOBILE) add_subdirectory(mobile) endif() # Enable unit testing if (BUILD_TESTING) add_subdirectory(tests) endif() # add clang-format target for all our real source files file(GLOB_RECURSE ALL_CLANG_FORMAT_SOURCE_FILES *.cpp *.h) kde_clang_format(${ALL_CLANG_FORMAT_SOURCE_FILES}) feature_summary(WHAT ALL INCLUDE_QUIET_PACKAGES FATAL_ON_MISSING_REQUIRED_PACKAGES) diff --git a/libs/CMakeLists.txt b/libs/CMakeLists.txt index 3bbca44d..70d3baad 100644 --- a/libs/CMakeLists.txt +++ b/libs/CMakeLists.txt @@ -1,32 +1,33 @@ add_definitions(-DTRANSLATION_DOMAIN=\"plasmanetworkmanagement-libs\") set(plasmanm_internal_SRCS configuration.cpp debug.cpp handler.cpp uiutils.cpp ) add_library(plasmanm_internal SHARED ${plasmanm_internal_SRCS}) target_link_libraries(plasmanm_internal +PUBLIC KF5::NetworkManagerQt +PRIVATE KF5::ConfigCore KF5::CoreAddons KF5::I18n KF5::IconThemes KF5::Notifications KF5::Service - KF5::Wallet KF5::WindowSystem - ${NETWORKMANAGER_LIBRARIES} + KF5::Wallet ) if (WITH_MODEMMANAGER_SUPPORT) - target_link_libraries(plasmanm_internal KF5::ModemManagerQt) + target_link_libraries(plasmanm_internal PUBLIC KF5::ModemManagerQt) endif() install(TARGETS plasmanm_internal ${INSTALL_TARGETS_DEFAULT_ARGS}) add_subdirectory(declarative) add_subdirectory(editor) diff --git a/libs/editor/CMakeLists.txt b/libs/editor/CMakeLists.txt index 73d16265..442b52ee 100644 --- a/libs/editor/CMakeLists.txt +++ b/libs/editor/CMakeLists.txt @@ -1,49 +1,56 @@ include_directories(${CMAKE_CURRENT_SOURCE_DIR}/widgets) set(plasmanm_editor_SRCS # FIXME ../debug.cpp settings/connectionsettings.cpp settings/setting.cpp settings/wirelesssetting.cpp widgets/passwordfield.cpp widgets/settingwidget.cpp listvalidator.cpp simpleipv4addressvalidator.cpp simpleipv6addressvalidator.cpp simpleiplistvalidator.cpp wireguardkeyvalidator.cpp vpnuiplugin.cpp ) if (WITH_MODEMMANAGER_SUPPORT) set(plasmanm_editor_SRCS ${plasmanm_editor_SRCS} widgets/mobileconnectionwizard.cpp mobileproviders.cpp) endif() add_library(plasmanm_editor SHARED ${plasmanm_editor_SRCS}) target_link_libraries(plasmanm_editor - plasmanm_internal - Qt5::DBus +PUBLIC + KF5::NetworkManagerQt Qt5::Widgets +PRIVATE + Qt5::DBus + KF5::ConfigCore + KF5::Completion KF5::CoreAddons - KF5::KDELibs4Support KF5::I18n - KF5::NetworkManagerQt + KF5::IconThemes + KF5::KIOFileWidgets + KF5::Notifications + KF5::Solid + KF5::Wallet + plasmanm_internal # KF5::Declarative -# KF5::Notifications # qca-qt5 ) if (WITH_MODEMMANAGER_SUPPORT) - target_link_libraries(plasmanm_editor KF5::ModemManagerQt) + target_link_libraries(plasmanm_editor PUBLIC KF5::ModemManagerQt) endif() install(TARGETS plasmanm_editor ${INSTALL_TARGETS_DEFAULT_ARGS}) install(FILES plasma-networkmanagement-vpnuiplugin.desktop DESTINATION ${KDE_INSTALL_KSERVICETYPES5DIR}) diff --git a/libs/editor/widgets/settingwidget.h b/libs/editor/widgets/settingwidget.h index fd06e115..44a5ca57 100644 --- a/libs/editor/widgets/settingwidget.h +++ b/libs/editor/widgets/settingwidget.h @@ -1,64 +1,62 @@ /* Copyright 2013 Jan Grulich This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) version 3, or any later version accepted by the membership of KDE e.V. (or its successor approved by the membership of KDE e.V.), which shall act as a proxy defined in Section 6 of version 3 of the license. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library. If not, see . */ #ifndef SETTING_WIDGET_H #define SETTING_WIDGET_H #include #include -#include - class Q_DECL_EXPORT SettingWidget : public QWidget { Q_OBJECT public: class EnumPasswordStorageType { public: enum PasswordStorageType {Store = 0, AlwaysAsk, NotRequired}; }; explicit SettingWidget(const NetworkManager::Setting::Ptr &setting = NetworkManager::Setting::Ptr(), QWidget* parent = nullptr, Qt::WindowFlags f = {}); ~SettingWidget() override; virtual void loadConfig(const NetworkManager::Setting::Ptr &setting); virtual void loadSecrets(const NetworkManager::Setting::Ptr &setting); virtual QVariantMap setting() const = 0; // Do not forget to call this function in the inherited class once initialized void watchChangedSetting(); QString type() const; virtual bool isValid() const { return true; } protected Q_SLOTS: void slotWidgetChanged(); Q_SIGNALS: void validChanged(bool isValid); void settingChanged(); private: QString m_type; }; #endif // SETTING_WIDGET_H diff --git a/vpn/fortisslvpn/fortisslvpnauth.cpp b/vpn/fortisslvpn/fortisslvpnauth.cpp index e6dee4a4..442e60f9 100644 --- a/vpn/fortisslvpn/fortisslvpnauth.cpp +++ b/vpn/fortisslvpn/fortisslvpnauth.cpp @@ -1,78 +1,80 @@ /* Copyright 2016 Jan Grulich This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) version 3, or any later version accepted by the membership of KDE e.V. (or its successor approved by the membership of KDE e.V.), which shall act as a proxy defined in Section 6 of version 3 of the license. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library. If not, see . */ #include "fortisslvpnauth.h" #include "ui_fortisslvpnauth.h" #include "nm-fortisslvpn-service.h" #include +#include + class FortisslvpnAuthDialogPrivate { public: Ui_FortisslvpnAuth ui; NetworkManager::VpnSetting::Ptr setting; }; FortisslvpnAuthDialog::FortisslvpnAuthDialog(const NetworkManager::VpnSetting::Ptr &setting, QWidget *parent) : SettingWidget(setting, parent) , d_ptr(new FortisslvpnAuthDialogPrivate) { Q_D(FortisslvpnAuthDialog); d->ui.setupUi(this); d->setting = setting; const NMStringMap data = d->setting->data(); const NetworkManager::Setting::SecretFlags otpFlag = static_cast(data.value(NM_FORTISSLVPN_KEY_OTP"-flags").toInt()); d->ui.otpFrame->setVisible(otpFlag == NetworkManager::Setting::NotSaved); KAcceleratorManager::manage(this); } FortisslvpnAuthDialog::~FortisslvpnAuthDialog() { delete d_ptr; } QVariantMap FortisslvpnAuthDialog::setting() const { Q_D(const FortisslvpnAuthDialog); const NMStringMap data = d->setting->data(); NMStringMap secrets; QVariantMap secretData; if (!d->ui.password->text().isEmpty()) { secrets.insert(QLatin1String(NM_FORTISSLVPN_KEY_PASSWORD), d->ui.password->text()); } if (!data.value(NM_FORTISSLVPN_KEY_OTP"-flags").isEmpty()) { const NetworkManager::Setting::SecretFlags otpFlag = static_cast(data.value(NM_FORTISSLVPN_KEY_OTP"-flags").toInt()); if (otpFlag == NetworkManager::Setting::NotSaved && !d->ui.otp->text().isEmpty()) { secrets.insert(QLatin1String(NM_FORTISSLVPN_KEY_OTP), d->ui.otp->text()); } } secretData.insert("secrets", QVariant::fromValue(secrets)); return secretData; } diff --git a/vpn/fortisslvpn/fortisslvpnwidget.cpp b/vpn/fortisslvpn/fortisslvpnwidget.cpp index f2c31208..d1b13ac7 100644 --- a/vpn/fortisslvpn/fortisslvpnwidget.cpp +++ b/vpn/fortisslvpn/fortisslvpnwidget.cpp @@ -1,245 +1,247 @@ /* Copyright 2017 Jan Grulich This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) version 3, or any later version accepted by the membership of KDE e.V. (or its successor approved by the membership of KDE e.V.), which shall act as a proxy defined in Section 6 of version 3 of the license. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library. If not, see . */ #include "fortisslvpnwidget.h" #include "ui_fortisslvpn.h" #include "ui_fortisslvpnadvanced.h" #include "nm-fortisslvpn-service.h" #include #include #include +#include + class FortisslvpnWidgetPrivate { public: Ui::FortisslvpnWidget ui; Ui::FortisslvpnAdvancedWidget advUi; NetworkManager::VpnSetting::Ptr setting; QDialog *advancedDlg; QWidget *advancedWid; }; FortisslvpnWidget::FortisslvpnWidget(const NetworkManager::VpnSetting::Ptr &setting, QWidget *parent, Qt::WindowFlags f) : SettingWidget(setting, parent, f) , d_ptr(new FortisslvpnWidgetPrivate) { Q_D(FortisslvpnWidget); d->setting = setting; d->ui.setupUi(this); d->ui.password->setPasswordOptionsEnabled(true); d->ui.password->setPasswordNotRequiredEnabled(true); // Connect for setting check watchChangedSetting(); // Connect for validity check connect(d->ui.gateway, &QLineEdit::textChanged, this, &FortisslvpnWidget::slotWidgetChanged); // Advanced configuration connect(d->ui.advancedButton, &QPushButton::clicked, this, &FortisslvpnWidget::showAdvanced); d->advancedDlg = new QDialog(this); d->advancedWid = new QWidget(this); d->advUi.setupUi(d->advancedWid); QVBoxLayout * layout = new QVBoxLayout(d->advancedDlg); layout->addWidget(d->advancedWid); d->advancedDlg->setLayout(layout); QDialogButtonBox* buttons = new QDialogButtonBox(QDialogButtonBox::Ok|QDialogButtonBox::Cancel, d->advancedDlg); connect(buttons, &QDialogButtonBox::accepted, d->advancedDlg, &QDialog::accept); connect(buttons, &QDialogButtonBox::rejected, d->advancedDlg, &QDialog::reject); layout->addWidget(buttons); KAcceleratorManager::manage(this); // Remove these from setting check: // Just popping up the advancedDlg changes nothing disconnect(d->ui.advancedButton, &QPushButton::clicked, this, &SettingWidget::settingChanged); // But the accept button does connect(buttons, &QDialogButtonBox::accepted, this, &SettingWidget::settingChanged); if (setting && !setting->isNull()) { loadConfig(setting); } } FortisslvpnWidget::~FortisslvpnWidget() { delete d_ptr; } void FortisslvpnWidget::loadConfig(const NetworkManager::Setting::Ptr &setting) { Q_D(FortisslvpnWidget); const NMStringMap data = d->setting->data(); const QString gateway = data.value(NM_FORTISSLVPN_KEY_GATEWAY); if (!gateway.isEmpty()) { d->ui.gateway->setText(gateway); } const QString username = data.value(NM_FORTISSLVPN_KEY_USER); if (!username.isEmpty()) { d->ui.username->setText(username); } const NetworkManager::Setting::SecretFlags passwordFlag = static_cast(data.value(NM_FORTISSLVPN_KEY_PASSWORD"-flags").toInt()); if (passwordFlag == NetworkManager::Setting::None) { d->ui.password->setPasswordOption(PasswordField::StoreForAllUsers); } else if (passwordFlag == NetworkManager::Setting::AgentOwned) { d->ui.password->setPasswordOption(PasswordField::StoreForUser); } else if (passwordFlag == NetworkManager::Setting::NotSaved) { d->ui.password->setPasswordOption(PasswordField::AlwaysAsk); } else { d->ui.password->setPasswordOption(PasswordField::NotRequired); } const QString caCert = data.value(NM_FORTISSLVPN_KEY_CA); if (!caCert.isEmpty()) { d->ui.caCert->setText(caCert); } const QString userCert = data.value(NM_FORTISSLVPN_KEY_CERT); if (!userCert.isEmpty()) { d->ui.userCert->setText(userCert); } const QString userKey = data.value(NM_FORTISSLVPN_KEY_KEY); if (!userKey.isEmpty()) { d->ui.userKey->setText(userKey); } // From advanced dialog const QString trustedCert = data.value(NM_FORTISSLVPN_KEY_TRUSTED_CERT); if (!trustedCert.isEmpty()) { d->advUi.trustedCert->setText(trustedCert); } if (!data.value(NM_FORTISSLVPN_KEY_OTP"-flags").isEmpty()) { const NetworkManager::Setting::SecretFlags otpFlag = static_cast(data.value(NM_FORTISSLVPN_KEY_OTP"-flags").toInt()); if (otpFlag & NetworkManager::Setting::NotSaved) { d->advUi.otp->setChecked(true); } } const QString realm = data.value(NM_FORTISSLVPN_KEY_REALM); if (!realm.isEmpty()) { d->advUi.realm->setText(realm); } loadSecrets(setting); } void FortisslvpnWidget::loadSecrets(const NetworkManager::Setting::Ptr &setting) { Q_D(FortisslvpnWidget); NetworkManager::VpnSetting::Ptr vpnSetting = setting.staticCast(); if (vpnSetting) { const NMStringMap secrets = vpnSetting->secrets(); const QString password = secrets.value(NM_FORTISSLVPN_KEY_PASSWORD); if (!password.isEmpty()) { d->ui.password->setText(password); } } } QVariantMap FortisslvpnWidget::setting() const { Q_D(const FortisslvpnWidget); NetworkManager::VpnSetting setting; setting.setServiceType(QLatin1String(NM_DBUS_SERVICE_FORTISSLVPN)); NMStringMap data; NMStringMap secrets; data.insert(NM_FORTISSLVPN_KEY_GATEWAY, d->ui.gateway->text()); if (!d->ui.username->text().isEmpty()) { data.insert(NM_FORTISSLVPN_KEY_USER, d->ui.username->text()); } if (!d->ui.password->text().isEmpty()) { secrets.insert(NM_FORTISSLVPN_KEY_PASSWORD, d->ui.password->text()); } if (d->ui.password->passwordOption() == PasswordField::StoreForAllUsers) { data.insert(NM_FORTISSLVPN_KEY_PASSWORD"-flags", QString::number(NetworkManager::Setting::None)); } else if (d->ui.password->passwordOption() == PasswordField::StoreForUser) { data.insert(NM_FORTISSLVPN_KEY_PASSWORD"-flags", QString::number(NetworkManager::Setting::AgentOwned)); } else if (d->ui.password->passwordOption() == PasswordField::AlwaysAsk) { data.insert(NM_FORTISSLVPN_KEY_PASSWORD"-flags", QString::number(NetworkManager::Setting::NotSaved)); } else { data.insert(NM_FORTISSLVPN_KEY_PASSWORD"-flags", QString::number(NetworkManager::Setting::NotRequired)); } if (!d->ui.caCert->url().isEmpty()) { data.insert(NM_FORTISSLVPN_KEY_CA, d->ui.caCert->url().toLocalFile()); } if (!d->ui.userCert->url().isEmpty()) { data.insert(NM_FORTISSLVPN_KEY_CERT, d->ui.userCert->url().toLocalFile()); } if (!d->ui.userKey->url().isEmpty()) { data.insert(NM_FORTISSLVPN_KEY_KEY, d->ui.userKey->url().toLocalFile()); } // From advanced if (!d->advUi.trustedCert->text().isEmpty()) { data.insert(NM_FORTISSLVPN_KEY_TRUSTED_CERT, d->advUi.trustedCert->text()); } if (d->advUi.otp->isChecked()) { data.insert(QLatin1String(NM_FORTISSLVPN_KEY_OTP"-flags"), QString::number(NetworkManager::Setting::NotSaved)); } else { data.insert(QLatin1String(NM_FORTISSLVPN_KEY_OTP"-flags"), QString::number(NetworkManager::Setting::None)); } if (!d->advUi.realm->text().isEmpty()) { data.insert(NM_FORTISSLVPN_KEY_REALM, d->advUi.realm->text()); } setting.setData(data); setting.setSecrets(secrets); return setting.toMap(); } void FortisslvpnWidget::showAdvanced() { Q_D(FortisslvpnWidget); d->advancedDlg->show(); } bool FortisslvpnWidget::isValid() const { Q_D(const FortisslvpnWidget); return !d->ui.gateway->text().isEmpty(); } diff --git a/vpn/iodine/iodineauth.cpp b/vpn/iodine/iodineauth.cpp index 1179f2e4..3c44b0ba 100644 --- a/vpn/iodine/iodineauth.cpp +++ b/vpn/iodine/iodineauth.cpp @@ -1,64 +1,66 @@ /* Copyright 2016 Jan Grulich This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) version 3, or any later version accepted by the membership of KDE e.V. (or its successor approved by the membership of KDE e.V.), which shall act as a proxy defined in Section 6 of version 3 of the license. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library. If not, see . */ #include "iodineauth.h" #include "ui_iodineauth.h" #include "nm-iodine-service.h" #include +#include + class IodineAuthDialogPrivate { public: Ui_IodineAuth ui; NetworkManager::VpnSetting::Ptr setting; }; IodineAuthDialog::IodineAuthDialog(const NetworkManager::VpnSetting::Ptr &setting, QWidget *parent) : SettingWidget(setting, parent) , d_ptr(new IodineAuthDialogPrivate) { Q_D(IodineAuthDialog); d->ui.setupUi(this); d->setting = setting; KAcceleratorManager::manage(this); } IodineAuthDialog::~IodineAuthDialog() { delete d_ptr; } QVariantMap IodineAuthDialog::setting() const { Q_D(const IodineAuthDialog); NMStringMap secrets; QVariantMap secretData; if (!d->ui.le_password->text().isEmpty()) { secrets.insert(QLatin1String(NM_IODINE_KEY_PASSWORD), d->ui.le_password->text()); } secretData.insert("secrets", QVariant::fromValue(secrets)); return secretData; } diff --git a/vpn/iodine/iodinewidget.cpp b/vpn/iodine/iodinewidget.cpp index 07caf42a..3a71c1b2 100644 --- a/vpn/iodine/iodinewidget.cpp +++ b/vpn/iodine/iodinewidget.cpp @@ -1,143 +1,145 @@ /* Copyright 2016 Jan Grulich This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) version 3, or any later version accepted by the membership of KDE e.V. (or its successor approved by the membership of KDE e.V.), which shall act as a proxy defined in Section 6 of version 3 of the license. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library. If not, see . */ #include "iodinewidget.h" #include "ui_iodine.h" #include "nm-iodine-service.h" #include #include +#include + IodineWidget::IodineWidget(const NetworkManager::VpnSetting::Ptr &setting, QWidget *parent, Qt::WindowFlags f) : SettingWidget(setting, parent, f) , m_ui(new Ui::IodineWidget) , m_setting(setting) { qDBusRegisterMetaType(); m_ui->setupUi(this); m_ui->le_password->setPasswordOptionsEnabled(true); // Connect for setting check watchChangedSetting(); // Connect for validity check connect(m_ui->le_toplevelDomain, &QLineEdit::textChanged, this, &IodineWidget::slotWidgetChanged); KAcceleratorManager::manage(this); if (setting && !setting->isNull()) { loadConfig(setting); } } IodineWidget::~IodineWidget() { delete m_ui; } void IodineWidget::loadConfig(const NetworkManager::Setting::Ptr &setting) { const NMStringMap data = m_setting->data(); const QString toplevelDomain = data.value(NM_IODINE_KEY_TOPDOMAIN); if (!toplevelDomain.isEmpty()) { m_ui->le_toplevelDomain->setText(toplevelDomain); } const QString nameserver = data.value(NM_IODINE_KEY_NAMESERVER); if (!nameserver.isEmpty()) { m_ui->le_nameserver->setText(nameserver); } const NetworkManager::Setting::SecretFlags passwordFlag = static_cast(data.value(NM_IODINE_KEY_PASSWORD"-flags").toInt()); if (passwordFlag == NetworkManager::Setting::None) { m_ui->le_password->setPasswordOption(PasswordField::StoreForAllUsers); } else if (passwordFlag == NetworkManager::Setting::AgentOwned) { m_ui->le_password->setPasswordOption(PasswordField::StoreForUser); } else { m_ui->le_password->setPasswordOption(PasswordField::AlwaysAsk); } const QString fragSize = data.value(NM_IODINE_KEY_FRAGSIZE); if (!fragSize.isEmpty()) { m_ui->sb_fragmentSize->setValue(fragSize.toInt()); } loadSecrets(setting); } void IodineWidget::loadSecrets(const NetworkManager::Setting::Ptr &setting) { NetworkManager::VpnSetting::Ptr vpnSetting = setting.staticCast(); if (vpnSetting) { const NMStringMap secrets = vpnSetting->secrets(); const QString password = secrets.value(NM_IODINE_KEY_PASSWORD); if (!password.isEmpty()) { m_ui->le_password->setText(password); } } } QVariantMap IodineWidget::setting() const { NetworkManager::VpnSetting setting; setting.setServiceType(QLatin1String(NM_DBUS_SERVICE_IODINE)); NMStringMap data; NMStringMap secrets; if (!m_ui->le_toplevelDomain->text().isEmpty()) { data.insert(NM_IODINE_KEY_TOPDOMAIN, m_ui->le_toplevelDomain->text()); } if (!m_ui->le_nameserver->text().isEmpty()) { data.insert(NM_IODINE_KEY_NAMESERVER, m_ui->le_nameserver->text()); } if (!m_ui->le_password->text().isEmpty()) { secrets.insert(NM_IODINE_KEY_PASSWORD, m_ui->le_password->text()); } if (m_ui->le_password->passwordOption() == PasswordField::StoreForAllUsers) { data.insert(NM_IODINE_KEY_PASSWORD"-flags", QString::number(NetworkManager::Setting::None)); } else if (m_ui->le_password->passwordOption() == PasswordField::StoreForUser) { data.insert(NM_IODINE_KEY_PASSWORD"-flags", QString::number(NetworkManager::Setting::AgentOwned)); } else { data.insert(NM_IODINE_KEY_PASSWORD"-flags", QString::number(NetworkManager::Setting::NotSaved)); } if (m_ui->sb_fragmentSize->value()) { data.insert(NM_IODINE_KEY_FRAGSIZE, QString::number(m_ui->sb_fragmentSize->value())); } setting.setData(data); setting.setSecrets(secrets); return setting.toMap(); } bool IodineWidget::isValid() const { return !m_ui->le_toplevelDomain->text().isEmpty(); } diff --git a/vpn/l2tp/l2tpauth.cpp b/vpn/l2tp/l2tpauth.cpp index e69f657b..b9b6bf23 100644 --- a/vpn/l2tp/l2tpauth.cpp +++ b/vpn/l2tp/l2tpauth.cpp @@ -1,130 +1,131 @@ /* Copyright 2011 Ilia Kats Copyright 2013 Lukáš Tinkl Copyright 2020 Douglas Kosovic This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License or (at your option) version 3 or any later version accepted by the membership of KDE e.V. (or its successor approved by the membership of KDE e.V.), which shall act as a proxy defined in Section 14 of version 3 of the license. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see . */ #include "l2tpauth.h" #include "passwordfield.h" #include #include #include #include #include +#include #include "nm-l2tp-service.h" class L2tpAuthWidgetPrivate { public: NetworkManager::VpnSetting::Ptr setting; QFormLayout *layout; }; L2tpAuthWidget::L2tpAuthWidget(const NetworkManager::VpnSetting::Ptr &setting, QWidget * parent) : SettingWidget(setting, parent) , d_ptr(new L2tpAuthWidgetPrivate) { Q_D(L2tpAuthWidget); d->setting = setting; d->layout = new QFormLayout(this); setLayout(d->layout); readSecrets(); KAcceleratorManager::manage(this); } L2tpAuthWidget::~L2tpAuthWidget() { delete d_ptr; } void L2tpAuthWidget::readSecrets() { Q_D(L2tpAuthWidget); const NMStringMap secrets = d->setting->secrets(); const NMStringMap dataMap = d->setting->data(); const QString userAType = dataMap[NM_L2TP_KEY_USER_AUTH_TYPE]; const QString machineAType = dataMap[NM_L2TP_KEY_MACHINE_AUTH_TYPE]; QLabel *label; PasswordField *lineEdit; NetworkManager::Setting::SecretFlags passType = (NetworkManager::Setting::SecretFlags)dataMap[NM_L2TP_KEY_PASSWORD"-flags"].toInt(); NetworkManager::Setting::SecretFlags userCertType = (NetworkManager::Setting::SecretFlags)dataMap[NM_L2TP_KEY_USER_CERTPASS"-flags"].toInt(); NetworkManager::Setting::SecretFlags machineCertType = (NetworkManager::Setting::SecretFlags)dataMap[NM_L2TP_KEY_MACHINE_CERTPASS"-flags"].toInt(); if ((userAType.isEmpty() || userAType == QLatin1String(NM_L2TP_AUTHTYPE_PASSWORD)) && !(passType.testFlag(NetworkManager::Setting::NotRequired))) { label = new QLabel(this); label->setText(i18n("User Password:")); lineEdit = new PasswordField(this); lineEdit->setPasswordModeEnabled(true); lineEdit->setProperty("nm_secrets_key", QLatin1String(NM_L2TP_KEY_PASSWORD)); lineEdit->setText(secrets.value(QLatin1String(NM_L2TP_KEY_PASSWORD))); d->layout->addRow(label, lineEdit); } else if (userAType == QLatin1String(NM_L2TP_AUTHTYPE_TLS) && !(userCertType.testFlag(NetworkManager::Setting::NotRequired))) { label = new QLabel(this); label->setText(i18n("User Certificate Password:")); lineEdit = new PasswordField(this); lineEdit->setPasswordModeEnabled(true); lineEdit->setProperty("nm_secrets_key", QLatin1String(NM_L2TP_KEY_USER_CERTPASS)); lineEdit->setText(secrets.value(QLatin1String(NM_L2TP_KEY_USER_CERTPASS))); d->layout->addRow(label, lineEdit); } if (machineAType == QLatin1String(NM_L2TP_AUTHTYPE_TLS)) { if (!(machineCertType.testFlag(NetworkManager::Setting::NotRequired))) { label = new QLabel(this); label->setText(i18n("Machine Certificate Password:")); lineEdit = new PasswordField(this); lineEdit->setPasswordModeEnabled(true); lineEdit->setProperty("nm_secrets_key", QLatin1String(NM_L2TP_KEY_MACHINE_CERTPASS)); lineEdit->setText(secrets.value(QLatin1String(NM_L2TP_KEY_MACHINE_CERTPASS))); d->layout->addRow(label, lineEdit); } } for (int i = 0; i < d->layout->rowCount(); i++) { PasswordField *le = qobject_cast(d->layout->itemAt(i, QFormLayout::FieldRole)->widget()); if (le && le->text().isEmpty()) { le->setFocus(Qt::OtherFocusReason); break; } } } QVariantMap L2tpAuthWidget::setting() const { Q_D(const L2tpAuthWidget); NMStringMap secrets; QVariantMap secretData; for (int i = 0; i < d->layout->rowCount(); i++) { PasswordField *le = qobject_cast(d->layout->itemAt(i, QFormLayout::FieldRole)->widget()); if (le && !le->text().isEmpty()) { const QString key = le->property("nm_secrets_key").toString(); secrets.insert(key, le->text()); } } secretData.insert("secrets", QVariant::fromValue(secrets)); return secretData; } diff --git a/vpn/l2tp/l2tpwidget.cpp b/vpn/l2tp/l2tpwidget.cpp index fc17e2bf..743f1bdd 100644 --- a/vpn/l2tp/l2tpwidget.cpp +++ b/vpn/l2tp/l2tpwidget.cpp @@ -1,311 +1,313 @@ /* Copyright 2013 Jan Grulich Copyright 2020 Douglas Kosovic This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) version 3, or any later version accepted by the membership of KDE e.V. (or its successor approved by the membership of KDE e.V.), which shall act as a proxy defined in Section 6 of version 3 of the license. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library. If not, see . */ #include "l2tpwidget.h" #include "l2tpipsecwidget.h" #include "l2tppppwidget.h" #include "ui_l2tp.h" #include "nm-l2tp-service.h" #include #include #include +#include + L2tpWidget::L2tpWidget(const NetworkManager::VpnSetting::Ptr &setting, QWidget* parent, Qt::WindowFlags f) : SettingWidget(setting, parent, f) , m_ui(new Ui::L2tpWidget) , m_setting(setting) { qDBusRegisterMetaType(); m_ui->setupUi(this); m_ui->password->setPasswordOptionsEnabled(true); m_ui->userKeyPassword->setPasswordOptionsEnabled(true); m_ui->userKeyPassword->setPasswordNotRequiredEnabled(true); // use requesters' urlSelected signals to set other requester's startDirs to save clicking // around the filesystem, also if it is a .p12 file, set the other URLs to that .p12 file. QList requesters; requesters << m_ui->userCA << m_ui->userCert << m_ui->userKey; for (const KUrlRequester *requester : requesters) { connect(requester, &KUrlRequester::urlSelected, this, &L2tpWidget::updateStartDirUrl); } if (L2tpIpsecWidget::hasIpsecDaemon()) { connect(m_ui->btnIPSecSettings, &QPushButton::clicked, this, &L2tpWidget::showIpsec); } else { m_ui->btnIPSecSettings->setDisabled(true); } connect(m_ui->btnPPPSettings, &QPushButton::clicked, this, &L2tpWidget::showPpp); // Connect for setting check watchChangedSetting(); // Connect for validity check connect(m_ui->gateway, &QLineEdit::textChanged, this, &L2tpWidget::slotWidgetChanged); KAcceleratorManager::manage(this); if (setting && !setting->isNull()) { loadConfig(setting); } } L2tpWidget::~L2tpWidget() { m_tmpIpsecSetting.clear(); m_tmpPppSetting.clear(); delete m_ui; } void L2tpWidget::loadConfig(const NetworkManager::Setting::Ptr &setting) { Q_UNUSED(setting); const NMStringMap dataMap = m_setting->data(); m_ui->gateway->setText(dataMap[NM_L2TP_KEY_GATEWAY]); if (dataMap[NM_L2TP_KEY_USER_AUTH_TYPE].isEmpty() || dataMap[NM_L2TP_KEY_USER_AUTH_TYPE] == QLatin1String(NM_L2TP_AUTHTYPE_PASSWORD)) { m_ui->cmbAuthType->setCurrentIndex(AuthType::Password); m_ui->stackedWidget->setCurrentIndex(AuthType::Password); m_ui->username->setText(dataMap[NM_L2TP_KEY_USER]); const NetworkManager::Setting::SecretFlags userPassType = static_cast(dataMap[NM_L2TP_KEY_PASSWORD"-flags"].toInt()); if (userPassType.testFlag(NetworkManager::Setting::None)) { m_ui->password->setPasswordOption(PasswordField::StoreForAllUsers); } else if (userPassType.testFlag(NetworkManager::Setting::AgentOwned)) { m_ui->password->setPasswordOption(PasswordField::StoreForUser); } else { m_ui->password->setPasswordOption(PasswordField::AlwaysAsk); } m_ui->domain->setText(dataMap[NM_L2TP_KEY_DOMAIN]); } else { // NM_L2TP_AUTHTYPE_TLS m_ui->cmbAuthType->setCurrentIndex(AuthType::TLS); m_ui->stackedWidget->setCurrentIndex(AuthType::TLS); m_ui->userCA->setUrl(QUrl::fromLocalFile(dataMap[NM_L2TP_KEY_USER_CA])); m_ui->userCert->setUrl(QUrl::fromLocalFile(dataMap[NM_L2TP_KEY_USER_CERT])); m_ui->userKey->setUrl(QUrl::fromLocalFile(dataMap[NM_L2TP_KEY_USER_KEY])); const NetworkManager::Setting::SecretFlags userKeyPassType = static_cast(dataMap[NM_L2TP_KEY_USER_CERTPASS"-flags"].toInt()); if (userKeyPassType.testFlag(NetworkManager::Setting::None)) { m_ui->userKeyPassword->setPasswordOption(PasswordField::StoreForAllUsers); } else if (userKeyPassType.testFlag(NetworkManager::Setting::AgentOwned)) { m_ui->userKeyPassword->setPasswordOption(PasswordField::StoreForUser); } else if (userKeyPassType.testFlag(NetworkManager::Setting::NotSaved)) { m_ui->userKeyPassword->setPasswordOption(PasswordField::AlwaysAsk); } else if (userKeyPassType.testFlag(NetworkManager::Setting::NotRequired)) { m_ui->userKeyPassword->setPasswordOption(PasswordField::NotRequired); } } loadSecrets(setting); } void L2tpWidget::loadSecrets(const NetworkManager::Setting::Ptr &setting) { NetworkManager::VpnSetting::Ptr vpnSetting = setting.staticCast(); if (vpnSetting) { const QString authType = m_setting->data().value(NM_L2TP_KEY_USER_AUTH_TYPE); const NMStringMap secrets = vpnSetting->secrets(); if (authType == QLatin1String(NM_L2TP_AUTHTYPE_TLS)) { m_ui->userKeyPassword->setText(secrets.value(NM_L2TP_KEY_USER_CERTPASS)); } else { // NM_L2TP_AUTHTYPE_PASSWORD m_ui->password->setText(secrets.value(NM_L2TP_KEY_PASSWORD)); } } } QVariantMap L2tpWidget::setting() const { NetworkManager::VpnSetting setting; setting.setServiceType(QLatin1String(NM_DBUS_SERVICE_L2TP)); NMStringMap data; NMStringMap secrets; if (!m_tmpIpsecSetting.isNull()) { data = m_tmpIpsecSetting->data(); secrets = m_tmpIpsecSetting->secrets(); } else { // retrieve the settings if the dialog has not been opened QScopedPointer ipsec(new L2tpIpsecWidget(m_setting, nullptr)); data = ipsec->setting(); secrets = ipsec->secrets(); } if (!m_tmpPppSetting.isNull()) { data.unite(m_tmpPppSetting->data()); } else { const bool need_peer_eap = m_ui->cmbAuthType->currentIndex() != AuthType::Password; // retrieve the settings if the dialog has not been opened QScopedPointer ppp(new L2tpPPPWidget(m_setting, nullptr, need_peer_eap)); data.unite(ppp->setting()); } if (!m_ui->gateway->text().isEmpty()) { data.insert(NM_L2TP_KEY_GATEWAY, m_ui->gateway->text()); } if (m_ui->cmbAuthType->currentIndex() == AuthType::Password) { if (!m_ui->username->text().isEmpty()) { data.insert(NM_L2TP_KEY_USER, m_ui->username->text()); } if (!m_ui->password->text().isEmpty()) { secrets.insert(NM_L2TP_KEY_PASSWORD, m_ui->password->text()); } else { secrets.remove(NM_L2TP_KEY_PASSWORD); } switch (m_ui->password->passwordOption()) { case PasswordField::StoreForAllUsers: data.insert(NM_L2TP_KEY_PASSWORD"-flags", QString::number(NetworkManager::Setting::None)); break; case PasswordField::StoreForUser: data.insert(NM_L2TP_KEY_PASSWORD"-flags", QString::number(NetworkManager::Setting::AgentOwned)); break; default: data.insert(NM_L2TP_KEY_PASSWORD"-flags", QString::number(NetworkManager::Setting::NotSaved)); }; if (!m_ui->domain->text().isEmpty()) { data.insert(NM_L2TP_KEY_DOMAIN, m_ui->domain->text()); } } else { // EnumAuthType::TLS data.insert(NM_L2TP_KEY_USER_AUTH_TYPE, NM_L2TP_AUTHTYPE_TLS); data.insert(NM_L2TP_KEY_USER_CA, m_ui->userCA->url().toLocalFile()); data.insert(NM_L2TP_KEY_USER_CERT, m_ui->userCert->url().toLocalFile()); data.insert(NM_L2TP_KEY_USER_KEY, m_ui->userKey->url().toLocalFile()); // key password if (!m_ui->userKeyPassword->text().isEmpty()) { secrets.insert(NM_L2TP_KEY_USER_CERTPASS, m_ui->userKeyPassword->text()); } else { secrets.remove(NM_L2TP_KEY_USER_CERTPASS); } switch (m_ui->userKeyPassword->passwordOption()) { case PasswordField::StoreForAllUsers: data.insert(NM_L2TP_KEY_USER_CERTPASS"-flags", QString::number(NetworkManager::Setting::None)); break; case PasswordField::StoreForUser: data.insert(NM_L2TP_KEY_USER_CERTPASS"-flags", QString::number(NetworkManager::Setting::AgentOwned)); break; case PasswordField::AlwaysAsk: data.insert(NM_L2TP_KEY_USER_CERTPASS"-flags", QString::number(NetworkManager::Setting::NotSaved)); break; case PasswordField::NotRequired: data.insert(NM_L2TP_KEY_USER_CERTPASS"-flags", QString::number(NetworkManager::Setting::NotRequired)); break; }; } setting.setData(data); setting.setSecrets(secrets); return setting.toMap(); } void L2tpWidget::updateStartDirUrl(const QUrl &url) { QList requesters; requesters << m_ui->userCA << m_ui->userCert << m_ui->userKey; bool isP12 = url.toString().endsWith(QLatin1String(".p12")); for (KUrlRequester *requester : requesters) { requester->setStartDir(url.adjusted(QUrl::RemoveFilename | QUrl::StripTrailingSlash)); if (isP12) { requester->setUrl(url); } } } void L2tpWidget::showIpsec() { QPointer ipsec; if (m_tmpIpsecSetting.isNull()) { ipsec = new L2tpIpsecWidget(m_setting, this); } else { ipsec = new L2tpIpsecWidget(m_tmpIpsecSetting, this); } connect(ipsec.data(), &L2tpIpsecWidget::accepted, [ipsec, this] () { NMStringMap ipsecData = ipsec->setting(); if (!ipsecData.isEmpty()) { if (m_tmpIpsecSetting.isNull()) { m_tmpIpsecSetting = NetworkManager::VpnSetting::Ptr(new NetworkManager::VpnSetting); } m_tmpIpsecSetting->setData(ipsecData); } }); connect(ipsec.data(), &L2tpIpsecWidget::finished, [ipsec] () { if (ipsec) { ipsec->deleteLater(); } }); ipsec->setModal(true); ipsec->show(); } void L2tpWidget::showPpp() { QPointer ipsec; bool need_peer_eap = m_ui->cmbAuthType->currentIndex() != AuthType::Password; if (m_tmpPppSetting.isNull()) { ipsec = new L2tpPPPWidget(m_setting, this, need_peer_eap); } else { ipsec = new L2tpPPPWidget(m_tmpPppSetting, this, need_peer_eap); } connect(ipsec.data(), &L2tpPPPWidget::accepted, [ipsec, this] () { NMStringMap ipsecData = ipsec->setting(); if (!ipsecData.isEmpty()) { if (m_tmpPppSetting.isNull()) { m_tmpPppSetting = NetworkManager::VpnSetting::Ptr(new NetworkManager::VpnSetting); } m_tmpPppSetting->setData(ipsecData); } }); connect(ipsec.data(), &L2tpPPPWidget::finished, [ipsec] () { if (ipsec) { ipsec->deleteLater(); } }); ipsec->setModal(true); ipsec->show(); } bool L2tpWidget::isValid() const { return !m_ui->gateway->text().isEmpty(); } diff --git a/vpn/openconnect/openconnectauth.cpp b/vpn/openconnect/openconnectauth.cpp index 8f72f76a..a617a197 100644 --- a/vpn/openconnect/openconnectauth.cpp +++ b/vpn/openconnect/openconnectauth.cpp @@ -1,785 +1,786 @@ /* Copyright 2011 Ilia Kats Copyright 2013 Lukáš Tinkl This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) version 3, or any later version accepted by the membership of KDE e.V. (or its successor approved by the membership of KDE e.V.), which shall act as a proxy defined in Section 6 of version 3 of the license. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library. If not, see . */ #include "openconnectauth.h" #include "openconnectauthworkerthread.h" #include "ui_openconnectauth.h" #include "debug.h" #include "passwordfield.h" #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include +#include #include #include #include "nm-openconnect-service.h" #include extern "C" { #include #include #include } #if !OPENCONNECT_CHECK_VER(2,1) #define __openconnect_set_token_mode(...) -EOPNOTSUPP #elif !OPENCONNECT_CHECK_VER(2,2) #define __openconnect_set_token_mode(vpninfo, mode, secret) openconnect_set_stoken_mode(vpninfo, 1, secret) #else #define __openconnect_set_token_mode openconnect_set_token_mode #endif #if OPENCONNECT_CHECK_VER(3,4) static int updateToken(void*, const char*); #endif // name/address: IP/domain name of the host (OpenConnect accepts both, so no difference here) // group: user group on the server typedef struct { QString name; QString group; QString address; } VPNHost; typedef struct { oc_token_mode_t tokenMode; QByteArray tokenSecret; } Token; class OpenconnectAuthWidgetPrivate { public: Ui_OpenconnectAuth ui; NetworkManager::VpnSetting::Ptr setting; struct openconnect_info *vpninfo; NMStringMap secrets; NMStringMap tmpSecrets; QMutex mutex; QWaitCondition workerWaiting; OpenconnectAuthWorkerThread *worker; QList hosts; bool userQuit; bool formGroupChanged; int cancelPipes[2]; QList > serverLog; int passwordFormIndex; QByteArray tokenMode; Token token; enum LogLevels {Error = 0, Info, Debug, Trace}; }; OpenconnectAuthWidget::OpenconnectAuthWidget(const NetworkManager::VpnSetting::Ptr &setting, QWidget * parent) : SettingWidget(setting, parent) , d_ptr(new OpenconnectAuthWidgetPrivate) { Q_D(OpenconnectAuthWidget); d->setting = setting; d->ui.setupUi(this); d->userQuit = false; d->formGroupChanged = false; if (pipe2(d->cancelPipes, O_NONBLOCK|O_CLOEXEC)) { // Should never happen. Just don't do real cancellation if it does d->cancelPipes[0] = -1; d->cancelPipes[1] = -1; } connect(d->ui.cmbLogLevel, QOverload::of(&QComboBox::currentIndexChanged), this, &OpenconnectAuthWidget::logLevelChanged); connect(d->ui.viewServerLog, &QCheckBox::toggled, this, &OpenconnectAuthWidget::viewServerLogToggled); connect(d->ui.btnConnect, &QPushButton::clicked, this, &OpenconnectAuthWidget::connectHost); d->ui.cmbLogLevel->setCurrentIndex(OpenconnectAuthWidgetPrivate::Debug); d->ui.btnConnect->setIcon(QIcon::fromTheme("network-connect")); d->ui.viewServerLog->setChecked(false); d->worker = new OpenconnectAuthWorkerThread(&d->mutex, &d->workerWaiting, &d->userQuit, &d->formGroupChanged, d->cancelPipes[0]); // gets the pointer to struct openconnect_info (defined in openconnect.h), which contains data that OpenConnect needs, // and which needs to be populated with settings we get from NM, like host, certificate or private key d->vpninfo = d->worker->getOpenconnectInfo(); connect(d->worker, QOverload::of(&OpenconnectAuthWorkerThread::validatePeerCert), this, &OpenconnectAuthWidget::validatePeerCert); connect(d->worker, &OpenconnectAuthWorkerThread::processAuthForm, this, &OpenconnectAuthWidget::processAuthForm); connect(d->worker, &OpenconnectAuthWorkerThread::updateLog, this, &OpenconnectAuthWidget::updateLog); connect(d->worker, QOverload::of(&OpenconnectAuthWorkerThread::writeNewConfig), this, &OpenconnectAuthWidget::writeNewConfig); connect(d->worker, &OpenconnectAuthWorkerThread::cookieObtained, this, &OpenconnectAuthWidget::workerFinished); connect(d->worker, &OpenconnectAuthWorkerThread::initTokens, this, &OpenconnectAuthWidget::initTokens); readConfig(); readSecrets(); #if OPENCONNECT_CHECK_VER(3,4) openconnect_set_token_callbacks(d->vpninfo, &d->secrets, NULL, &updateToken); #endif // This might be set by readSecrets() so don't connect it until now connect(d->ui.cmbHosts, QOverload::of(&QComboBox::currentIndexChanged), this, &OpenconnectAuthWidget::connectHost); KAcceleratorManager::manage(this); } OpenconnectAuthWidget::~OpenconnectAuthWidget() { Q_D(OpenconnectAuthWidget); d->userQuit = true; if (write(d->cancelPipes[1], "x", 1)) { // not a lot we can do } d->workerWaiting.wakeAll(); d->worker->wait(); ::close(d->cancelPipes[0]); ::close(d->cancelPipes[1]); deleteAllFromLayout(d->ui.loginBoxLayout); delete d->worker; delete d; } void OpenconnectAuthWidget::readConfig() { Q_D(OpenconnectAuthWidget); const NMStringMap dataMap = d->setting->data(); if (!dataMap[NM_OPENCONNECT_KEY_GATEWAY].isEmpty()) { const QString gw = dataMap[NM_OPENCONNECT_KEY_GATEWAY]; VPNHost host; const int index = gw.indexOf(QLatin1Char('/')); if (index > -1) { host.name = host.address = gw.left(index); host.group = gw.right(gw.length() - index - 1); } else { host.name = host.address = gw; } d->hosts.append(host); } if (!dataMap[NM_OPENCONNECT_KEY_CACERT].isEmpty()) { const QByteArray crt = QFile::encodeName(dataMap[NM_OPENCONNECT_KEY_CACERT]); openconnect_set_cafile(d->vpninfo, OC3DUP(crt.data())); } if (dataMap[NM_OPENCONNECT_KEY_CSD_ENABLE] == "yes") { char *wrapper; wrapper = nullptr; if (!dataMap[NM_OPENCONNECT_KEY_CSD_WRAPPER].isEmpty()) { const QByteArray wrapperScript = QFile::encodeName(dataMap[NM_OPENCONNECT_KEY_CSD_WRAPPER]); wrapper = strdup(wrapperScript.data()); } openconnect_setup_csd(d->vpninfo, getuid(), 1, wrapper); } if (!dataMap[NM_OPENCONNECT_KEY_PROXY].isEmpty()) { const QByteArray proxy = QFile::encodeName(dataMap[NM_OPENCONNECT_KEY_PROXY]); openconnect_set_http_proxy(d->vpninfo, OC3DUP(proxy.data())); } if (!dataMap[NM_OPENCONNECT_KEY_USERCERT].isEmpty()) { const QByteArray crt = QFile::encodeName(dataMap[NM_OPENCONNECT_KEY_USERCERT]); const QByteArray key = QFile::encodeName(dataMap[NM_OPENCONNECT_KEY_PRIVKEY]); openconnect_set_client_cert (d->vpninfo, OC3DUP(crt.data()), OC3DUP(key.data())); if (!crt.isEmpty() && dataMap[NM_OPENCONNECT_KEY_PEM_PASSPHRASE_FSID] == "yes") { openconnect_passphrase_from_fsid(d->vpninfo); } } if (!dataMap[NM_OPENCONNECT_KEY_PROTOCOL].isEmpty()) { const QString protocol = dataMap[NM_OPENCONNECT_KEY_PROTOCOL]; openconnect_set_protocol(d->vpninfo, OC3DUP(protocol == "juniper" ? "nc" : protocol.toUtf8().data())); } d->tokenMode = dataMap[NM_OPENCONNECT_KEY_TOKEN_MODE].toUtf8(); } void OpenconnectAuthWidget::readSecrets() { Q_D(OpenconnectAuthWidget); d->secrets = d->setting->secrets(); if (!d->secrets["xmlconfig"].isEmpty()) { const QByteArray config = QByteArray::fromBase64(d->secrets["xmlconfig"].toLatin1()); QCryptographicHash hash(QCryptographicHash::Sha1); hash.addData(config.data(), config.size()); const char *sha1_text = hash.result().toHex(); openconnect_set_xmlsha1 (d->vpninfo, (char *)sha1_text, strlen(sha1_text)+1); QDomDocument xmlconfig; xmlconfig.setContent(config); const QDomNode anyConnectProfile = xmlconfig.elementsByTagName(QLatin1String("AnyConnectProfile")).at(0); bool matchedGw = false; const QDomNode serverList = anyConnectProfile.firstChildElement(QLatin1String("ServerList")); for (QDomElement entry = serverList.firstChildElement(QLatin1String("HostEntry")); !entry.isNull(); entry = entry.nextSiblingElement(QLatin1String("HostEntry"))) { VPNHost host; host.name = entry.firstChildElement(QLatin1String("HostName")).text(); host.group = entry.firstChildElement(QLatin1String("UserGroup")).text(); host.address = entry.firstChildElement(QLatin1String("HostAddress")).text(); // We added the originally configured host in readConfig(). But if // it matches one of the ones in the XML config (as presumably it // should), remove the original and use the one with the pretty name. if (!matchedGw && host.address == d->hosts.at(0).address) { d->hosts.removeFirst(); matchedGw = true; } d->hosts.append(host); } } for (int i = 0; i < d->hosts.size(); i++) { d->ui.cmbHosts->addItem(d->hosts.at(i).name, i); if (d->secrets["lasthost"] == d->hosts.at(i).name || d->secrets["lasthost"] == d->hosts.at(i).address) { d->ui.cmbHosts->setCurrentIndex(i); } } if (d->secrets["autoconnect"] == "yes") { d->ui.chkAutoconnect->setChecked(true); QTimer::singleShot(0, this, &OpenconnectAuthWidget::connectHost); } if (d->secrets["save_passwords"] == "yes") { d->ui.chkStorePasswords->setChecked(true); } d->token.tokenMode = OC_TOKEN_MODE_NONE; d->token.tokenSecret = nullptr; if (!d->tokenMode.isEmpty()) { int ret = 0; QByteArray tokenSecret = d->secrets[NM_OPENCONNECT_KEY_TOKEN_SECRET].toUtf8(); if (d->tokenMode == QStringLiteral("manual") && !tokenSecret.isEmpty()) { ret = __openconnect_set_token_mode(d->vpninfo, OC_TOKEN_MODE_STOKEN, tokenSecret); } else if (d->tokenMode ==QStringLiteral("stokenrc")) { ret = __openconnect_set_token_mode(d->vpninfo, OC_TOKEN_MODE_STOKEN, NULL); } else if (d->tokenMode == QStringLiteral("totp") && !tokenSecret.isEmpty()) { ret = __openconnect_set_token_mode(d->vpninfo, OC_TOKEN_MODE_TOTP, tokenSecret); } #if OPENCONNECT_CHECK_VER(3,4) else if (d->tokenMode == QStringLiteral("hotp") && !tokenSecret.isEmpty()) { ret = __openconnect_set_token_mode(d->vpninfo, OC_TOKEN_MODE_HOTP, tokenSecret); } #endif #if OPENCONNECT_CHECK_VER(5,0) else if (d->tokenMode == "yubioath") { /* This needs to be done from a thread because it can call back to ask for the PIN */ d->token.tokenMode = OC_TOKEN_MODE_YUBIOATH; if (!tokenSecret.isEmpty()) { d->token.tokenSecret = tokenSecret; } } #endif if (ret) { addFormInfo(QLatin1String("dialog-error"), i18n("Failed to initialize software token: %1", ret)); } } } void OpenconnectAuthWidget::acceptDialog() { // Find top-level widget as this should be the QDialog itself QWidget *widget = parentWidget(); while (widget->parentWidget() != nullptr) { widget = widget->parentWidget(); } QDialog *dialog = qobject_cast(widget); if (dialog) { dialog->accept(); } } // This starts the worker thread, which connects to the selected AnyConnect host // and retrieves the login form void OpenconnectAuthWidget::connectHost() { Q_D(OpenconnectAuthWidget); d->userQuit = true; if (write(d->cancelPipes[1], "x", 1)) { // not a lot we can do } d->workerWaiting.wakeAll(); d->worker->wait(); d->userQuit = false; /* Suck out the cancel byte(s) */ char buf; while (read(d->cancelPipes[0], &buf, 1) == 1) { ; } deleteAllFromLayout(d->ui.loginBoxLayout); int i = d->ui.cmbHosts->currentIndex(); if (i == -1) { return; } i = d->ui.cmbHosts->itemData(i).toInt(); const VPNHost &host = d->hosts.at(i); if (openconnect_parse_url(d->vpninfo, host.address.toLatin1().data())) { qCWarning(PLASMA_NM) << "Failed to parse server URL" << host.address; openconnect_set_hostname(d->vpninfo, OC3DUP(host.address.toLatin1().data())); } if (!openconnect_get_urlpath(d->vpninfo) && !host.group.isEmpty()) { openconnect_set_urlpath(d->vpninfo, OC3DUP(host.group.toLatin1().data())); } d->secrets["lasthost"] = host.name; addFormInfo(QLatin1String("dialog-information"), i18n("Contacting host, please wait...")); d->worker->start(); } void OpenconnectAuthWidget::initTokens() { Q_D(OpenconnectAuthWidget); if (d->token.tokenMode != OC_TOKEN_MODE_NONE) { __openconnect_set_token_mode(d->vpninfo, d->token.tokenMode, d->token.tokenSecret); } } QVariantMap OpenconnectAuthWidget::setting() const { Q_D(const OpenconnectAuthWidget); NMStringMap secrets; QVariantMap secretData; secrets.unite(d->secrets); QString host(openconnect_get_hostname(d->vpninfo)); const QString port = QString::number(openconnect_get_port(d->vpninfo)); secrets.insert(QLatin1String(NM_OPENCONNECT_KEY_GATEWAY), host + ':' + port); secrets.insert(QLatin1String(NM_OPENCONNECT_KEY_COOKIE), QLatin1String(openconnect_get_cookie(d->vpninfo))); openconnect_clear_cookie(d->vpninfo); #if OPENCONNECT_CHECK_VER(5,0) const char *fingerprint = openconnect_get_peer_cert_hash(d->vpninfo); #else OPENCONNECT_X509 *cert = openconnect_get_peer_cert(d->vpninfo); char fingerprint[41]; openconnect_get_cert_sha1(d->vpninfo, cert, fingerprint); #endif secrets.insert(QLatin1String(NM_OPENCONNECT_KEY_GWCERT), QLatin1String(fingerprint)); secrets.insert(QLatin1String("autoconnect"), d->ui.chkAutoconnect->isChecked() ? "yes" : "no"); secrets.insert(QLatin1String("save_passwords"), d->ui.chkStorePasswords->isChecked() ? "yes" : "no"); NMStringMap::iterator i = secrets.begin(); while (i != secrets.end()) { if (i.value().isEmpty()) { i = secrets.erase(i); } else { i++; } } secretData.insert("secrets", QVariant::fromValue(secrets)); // These secrets are not officially part of the secrets which would be returned back to NetworkManager. We just // need to somehow get them to our secret agent which will handle them separately and store them. if (!d->tmpSecrets.isEmpty()) { secretData.insert("tmp-secrets", QVariant::fromValue(d->tmpSecrets)); } return secretData; } #if OPENCONNECT_CHECK_VER(3,4) static int updateToken(void *cbdata, const char *tok) { NMStringMap *secrets = static_cast(cbdata); secrets->insert(QLatin1String(NM_OPENCONNECT_KEY_TOKEN_SECRET), QLatin1String(tok)); return 0; } #endif void OpenconnectAuthWidget::writeNewConfig(const QString & buf) { Q_D(OpenconnectAuthWidget); d->secrets["xmlconfig"] = buf; } void OpenconnectAuthWidget::updateLog(const QString &message, const int &level) { Q_D(OpenconnectAuthWidget); QPair pair; pair.first = message; if (pair.first.endsWith(QLatin1String("\n"))) { pair.first.chop(1); } switch (level) { case PRG_ERR: pair.second = OpenconnectAuthWidgetPrivate::Error; break; case PRG_INFO: pair.second = OpenconnectAuthWidgetPrivate::Info; break; case PRG_DEBUG: pair.second = OpenconnectAuthWidgetPrivate::Debug; break; case PRG_TRACE: pair.second = OpenconnectAuthWidgetPrivate::Trace; break; } if (pair.second <= d->ui.cmbLogLevel->currentIndex()) { d->ui.serverLog->append(pair.first); } d->serverLog.append(pair); if (d->serverLog.size() > 100) { d->serverLog.removeFirst(); } } void OpenconnectAuthWidget::logLevelChanged(int newLevel) { Q_D(OpenconnectAuthWidget); d->ui.serverLog->clear(); QList >::const_iterator i; for (i = d->serverLog.constBegin(); i != d->serverLog.constEnd(); ++i) { QPair pair = *i; if(pair.second <= newLevel) { d->ui.serverLog->append(pair.first); } } } void OpenconnectAuthWidget::addFormInfo(const QString &iconName, const QString &message) { Q_D(OpenconnectAuthWidget); QHBoxLayout *layout = new QHBoxLayout(); QLabel *icon = new QLabel(this); QSizePolicy sizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed); sizePolicy.setHorizontalStretch(0); sizePolicy.setVerticalStretch(0); sizePolicy.setHeightForWidth(icon->sizePolicy().hasHeightForWidth()); icon->setSizePolicy(sizePolicy); icon->setMinimumSize(QSize(16, 16)); icon->setMaximumSize(QSize(16, 16)); layout->addWidget(icon); QLabel *text = new QLabel(this); text->setAlignment(Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter); text->setWordWrap(true); layout->addWidget(text); icon->setPixmap(QIcon::fromTheme(iconName).pixmap(KIconLoader::SizeSmall)); text->setText(message); d->ui.loginBoxLayout->addLayout(layout); } void OpenconnectAuthWidget::processAuthForm(struct oc_auth_form *form) { Q_D(OpenconnectAuthWidget); deleteAllFromLayout(d->ui.loginBoxLayout); if (form->banner) { addFormInfo(QLatin1String("dialog-information"), form->banner); } if (form->message) { addFormInfo(QLatin1String("dialog-information"), form->message); } if (form->error) { addFormInfo(QLatin1String("dialog-error"), form->error); } struct oc_form_opt *opt; QFormLayout *layout = new QFormLayout(); QSizePolicy policy(QSizePolicy::Expanding, QSizePolicy::Fixed); bool focusSet = false; for (opt = form->opts; opt; opt = opt->next) { if (opt->type == OC_FORM_OPT_HIDDEN || IGNORE_OPT(opt)) { continue; } QLabel *text = new QLabel(this); text->setAlignment(Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter); text->setText(QString(opt->label)); QWidget *widget = nullptr; const QString key = QString("form:%1:%2").arg(QLatin1String(form->auth_id)).arg(QLatin1String(opt->name)); const QString value = d->secrets.value(key); if (opt->type == OC_FORM_OPT_PASSWORD || opt->type == OC_FORM_OPT_TEXT) { PasswordField *le = new PasswordField(this); le->setText(value); if (opt->type == OC_FORM_OPT_PASSWORD) { le->setPasswordModeEnabled(true); } if (!focusSet && le->text().isEmpty()) { le->setFocus(Qt::OtherFocusReason); focusSet = true; } widget = qobject_cast(le); } else if (opt->type == OC_FORM_OPT_SELECT) { QComboBox *cmb = new QComboBox(this); struct oc_form_opt_select *sopt = reinterpret_cast(opt); #if !OPENCONNECT_CHECK_VER(8,0) const QString protocol = d->setting->data()[NM_OPENCONNECT_KEY_PROTOCOL]; #endif for (int i = 0; i < sopt->nr_choices; i++) { cmb->addItem(QString::fromUtf8(FORMCHOICE(sopt, i)->label), QString::fromUtf8(FORMCHOICE(sopt, i)->name)); if (value == QString::fromUtf8(FORMCHOICE(sopt, i)->name)) { cmb->setCurrentIndex(i); #if !OPENCONNECT_CHECK_VER(8,0) if (protocol != QLatin1String("nc") && sopt == AUTHGROUP_OPT(form) && i != AUTHGROUP_SELECTION(form)) { #else if (sopt == AUTHGROUP_OPT(form) && i != AUTHGROUP_SELECTION(form)) { #endif QTimer::singleShot(0, this, &OpenconnectAuthWidget::formGroupChanged); } } } #if !OPENCONNECT_CHECK_VER(8,0) if (protocol != QLatin1String("nc") && sopt == AUTHGROUP_OPT(form)) { #else if (sopt == AUTHGROUP_OPT(form)) { #endif connect(cmb, QOverload::of(&QComboBox::currentIndexChanged), this, &OpenconnectAuthWidget::formGroupChanged); } widget = qobject_cast(cmb); } if (widget) { widget->setProperty("openconnect_opt", (quintptr)opt); widget->setSizePolicy(policy); layout->addRow(text, widget); } } d->ui.loginBoxLayout->addLayout(layout); d->passwordFormIndex = d->ui.loginBoxLayout->count() - 1; QDialogButtonBox *box = new QDialogButtonBox(this); QPushButton *btn = box->addButton(QDialogButtonBox::Ok); btn->setText(i18nc("Verb, to proceed with login", "Login")); btn->setDefault(true); d->ui.loginBoxLayout->addWidget(box); box->setProperty("openconnect_form", (quintptr)form); connect(box, &QDialogButtonBox::accepted, this, &OpenconnectAuthWidget::formLoginClicked); } void OpenconnectAuthWidget::validatePeerCert(const QString &fingerprint, const QString &peerCert, const QString &reason, bool *accepted) { Q_D(OpenconnectAuthWidget); const QString host = QLatin1String(openconnect_get_hostname(d->vpninfo)); const QString port = QString::number(openconnect_get_port(d->vpninfo)); const QString key = QString("certificate:%1:%2").arg(host, port); const QString value = d->secrets.value(key); #if !OPENCONNECT_CHECK_VER(5,0) #define openconnect_check_peer_cert_hash(v,d) strcmp(d, fingerprint.toUtf8().data()) #endif if (openconnect_check_peer_cert_hash(d->vpninfo, value.toUtf8().data())) { QWidget *widget = new QWidget(); QVBoxLayout *verticalLayout; QHBoxLayout *horizontalLayout; QLabel *icon; QLabel *infoText; QTextBrowser *certificate; verticalLayout = new QVBoxLayout(widget); horizontalLayout = new QHBoxLayout(widget); icon = new QLabel(widget); QSizePolicy sizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed); sizePolicy.setHorizontalStretch(0); sizePolicy.setVerticalStretch(0); sizePolicy.setHeightForWidth(icon->sizePolicy().hasHeightForWidth()); icon->setSizePolicy(sizePolicy); icon->setMinimumSize(QSize(48, 48)); icon->setMaximumSize(QSize(48, 48)); horizontalLayout->addWidget(icon); infoText = new QLabel(widget); infoText->setAlignment(Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter); horizontalLayout->addWidget(infoText); verticalLayout->addLayout(horizontalLayout); certificate = new QTextBrowser(widget); certificate->setTextInteractionFlags(Qt::TextSelectableByMouse); certificate->setOpenLinks(false); verticalLayout->addWidget(certificate); icon->setPixmap(QIcon::fromTheme("dialog-information").pixmap(KIconLoader::SizeLarge)); infoText->setText(i18n("Check failed for certificate from VPN server \"%1\".\n" "Reason: %2\nAccept it anyway?", openconnect_get_hostname(d->vpninfo),reason)); infoText->setWordWrap(true); certificate->setText(peerCert); QPointer dialog = new QDialog(this); dialog.data()->setWindowModality(Qt::WindowModal); dialog->setLayout(new QVBoxLayout); QDialogButtonBox* buttons = new QDialogButtonBox(QDialogButtonBox::Ok|QDialogButtonBox::Cancel, dialog); connect(buttons, &QDialogButtonBox::accepted, dialog.data(), &QDialog::accept); connect(buttons, &QDialogButtonBox::rejected, dialog.data(), &QDialog::reject); dialog->layout()->addWidget(widget); dialog->layout()->addWidget(buttons); const NMStringMap dataMap = d->setting->data(); buttons->button(QDialogButtonBox::Ok)->setEnabled(dataMap[NM_OPENCONNECT_KEY_PREVENT_INVALID_CERT] != "yes"); if(dialog.data()->exec() == QDialog::Accepted) { *accepted = true; } else { *accepted = false; } if (dialog) { dialog.data()->deleteLater(); } widget->deleteLater(); } else { *accepted = true; } if (*accepted) { d->secrets.insert(key, QString(fingerprint)); } d->mutex.lock(); d->workerWaiting.wakeAll(); d->mutex.unlock(); } void OpenconnectAuthWidget::formGroupChanged() { Q_D(OpenconnectAuthWidget); d->formGroupChanged = true; formLoginClicked(); } // Writes the user input from the form into the oc_auth_form structs we got from // libopenconnect, and wakes the worker thread up to try to log in and obtain a // cookie with this data void OpenconnectAuthWidget::formLoginClicked() { Q_D(OpenconnectAuthWidget); const int lastIndex = d->ui.loginBoxLayout->count() - 1; QLayout *layout = d->ui.loginBoxLayout->itemAt(d->passwordFormIndex)->layout(); struct oc_auth_form *form = (struct oc_auth_form *) d->ui.loginBoxLayout->itemAt(lastIndex)->widget()->property("openconnect_form").value(); for (int i = 0; i < layout->count(); i++) { QLayoutItem *item = layout->itemAt(i); QWidget *widget = item->widget(); if (widget && widget->property("openconnect_opt").isValid()) { struct oc_form_opt *opt = (struct oc_form_opt *) widget->property("openconnect_opt").value(); const QString key = QString("form:%1:%2").arg(QLatin1String(form->auth_id)).arg(QLatin1String(opt->name)); if (opt->type == OC_FORM_OPT_PASSWORD || opt->type == OC_FORM_OPT_TEXT) { PasswordField *le = qobject_cast(widget); QByteArray text = le->text().toUtf8(); openconnect_set_option_value(opt, text.data()); if (opt->type == OC_FORM_OPT_TEXT) { d->secrets.insert(key, le->text()); } else { d->tmpSecrets.insert(key, le->text()); } } else if (opt->type == OC_FORM_OPT_SELECT) { QComboBox *cbo = qobject_cast(widget); QByteArray text = cbo->itemData(cbo->currentIndex()).toString().toLatin1(); openconnect_set_option_value(opt, text.data()); d->secrets.insert(key,cbo->itemData(cbo->currentIndex()).toString()); } } } deleteAllFromLayout(d->ui.loginBoxLayout); d->workerWaiting.wakeAll(); } void OpenconnectAuthWidget::workerFinished(const int &ret) { Q_D(OpenconnectAuthWidget); if (ret < 0) { QString message; QList >::const_iterator i; for (i = d->serverLog.constEnd()-1; i >= d->serverLog.constBegin(); --i) { QPair pair = *i; if(pair.second <= OpenconnectAuthWidgetPrivate::Error) { message = pair.first; break; } } if (message.isEmpty()) { message = i18n("Connection attempt was unsuccessful."); } deleteAllFromLayout(d->ui.loginBoxLayout); addFormInfo(QLatin1String("dialog-error"), message); } else { deleteAllFromLayout(d->ui.loginBoxLayout); acceptDialog(); } } void OpenconnectAuthWidget::deleteAllFromLayout(QLayout *layout) { while (QLayoutItem *item = layout->takeAt(0)) { if (QLayout *itemLayout = item->layout()) { deleteAllFromLayout(itemLayout); itemLayout->deleteLater(); } else { item->widget()->deleteLater(); } delete item; } layout->invalidate(); } void OpenconnectAuthWidget::viewServerLogToggled(bool toggled) { Q_D(OpenconnectAuthWidget); d->ui.lblLogLevel->setVisible(toggled); d->ui.cmbLogLevel->setVisible(toggled); if (toggled) { delete d->ui.verticalLayout->takeAt(5); QSizePolicy policy = d->ui.serverLogBox->sizePolicy(); policy.setVerticalPolicy(QSizePolicy::Expanding); d->ui.serverLogBox->setSizePolicy(policy); d->ui.serverLog->setVisible(true); } else { QSpacerItem *verticalSpacer = new QSpacerItem(0, 0, QSizePolicy::Minimum, QSizePolicy::Expanding); d->ui.verticalLayout->addItem(verticalSpacer); d->ui.serverLog->setVisible(false); QSizePolicy policy = d->ui.serverLogBox->sizePolicy(); policy.setVerticalPolicy(QSizePolicy::Fixed); d->ui.serverLogBox->setSizePolicy(policy); } } diff --git a/vpn/openconnect/openconnectwidget.cpp b/vpn/openconnect/openconnectwidget.cpp index 9d8e7963..be970018 100644 --- a/vpn/openconnect/openconnectwidget.cpp +++ b/vpn/openconnect/openconnectwidget.cpp @@ -1,340 +1,342 @@ /* Copyright 2011 Ilia Kats Copyright 2013 Lukas Tinkl This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) version 3, or any later version accepted by the membership of KDE e.V. (or its successor approved by the membership of KDE e.V.), which shall act as a proxy defined in Section 6 of version 3 of the license. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library. If not, see . */ #include "openconnectwidget.h" #include #include #include #include "ui_openconnectprop.h" #include "ui_openconnecttoken.h" #include #include #include "nm-openconnect-service.h" #include #ifndef OPENCONNECT_CHECK_VER #define OPENCONNECT_CHECK_VER(x,y) 0 #endif #if !OPENCONNECT_CHECK_VER(2,1) #define openconnect_has_stoken_support() 0 #endif #if !OPENCONNECT_CHECK_VER(2,2) #define openconnect_has_oath_support() 0 #endif #if !OPENCONNECT_CHECK_VER(5,0) #define openconnect_has_yubioath_support() 0 #endif typedef struct { int tokenIndex; QString tokenSecret; } Token; +#include + class OpenconnectSettingWidgetPrivate { public: Ui_OpenconnectProp ui; Ui::OpenConnectToken tokenUi; NetworkManager::VpnSetting::Ptr setting; QDialog *tokenDlg; Token token; }; OpenconnectSettingWidget::OpenconnectSettingWidget(const NetworkManager::VpnSetting::Ptr &setting, QWidget * parent) : SettingWidget(setting, parent) , d_ptr(new OpenconnectSettingWidgetPrivate) { Q_D(OpenconnectSettingWidget); d->ui.setupUi(this); d->setting = setting; // Connect for validity check connect(d->ui.leGateway, &QLineEdit::textChanged, this, &OpenconnectSettingWidget::slotWidgetChanged); connect(d->ui.buTokens, &QPushButton::clicked, this, &OpenconnectSettingWidget::showTokens); d->tokenDlg = new QDialog(this); d->tokenUi.setupUi(d->tokenDlg); d->tokenUi.leTokenSecret->setPasswordModeEnabled(true); d->tokenUi.leTokenSecret->setPasswordOptionsEnabled(true); QVBoxLayout * layout = new QVBoxLayout(d->tokenDlg); layout->addWidget(d->tokenDlg); d->tokenDlg->setLayout(layout); connect(d->tokenUi.buttonBox, &QDialogButtonBox::accepted, d->tokenDlg, &QDialog::accept); connect(d->tokenUi.buttonBox, &QDialogButtonBox::rejected, d->tokenDlg, &QDialog::reject); connect(d->tokenDlg, &QDialog::rejected, this, &OpenconnectSettingWidget::restoreTokens); connect(d->tokenDlg, &QDialog::accepted, this, &OpenconnectSettingWidget::saveTokens); connect(d->tokenUi.cmbTokenMode, QOverload::of(&QComboBox::currentIndexChanged), this, QOverload::of((&OpenconnectSettingWidget::handleTokenSecret))); // Connect for setting check watchChangedSetting(); // Remove these from setting check: // Just popping up the tokenDlg changes nothing disconnect(d->ui.buTokens, &QPushButton::clicked, this, &SettingWidget::settingChanged); // User cancels means nothing should change here disconnect(d->tokenUi.buttonBox->button(QDialogButtonBox::Cancel), &QPushButton::clicked, this, &SettingWidget::settingChanged); d->tokenUi.gbToken->setVisible(initTokenGroup()); KAcceleratorManager::manage(this); if (d->setting) { loadConfig(d->setting); } } OpenconnectSettingWidget::~OpenconnectSettingWidget() { delete d_ptr; } void OpenconnectSettingWidget::handleTokenSecret(int index) { Q_D(const OpenconnectSettingWidget); QVariant mode = d->tokenUi.cmbTokenMode->itemData(index); if (mode == QStringLiteral("disabled")) { d->tokenUi.leTokenSecret->setEnabled(false); d->tokenUi.leTokenSecret->setToolTip("No secrets needed."); } else if (mode == QStringLiteral("stokenrc")) { d->tokenUi.leTokenSecret->setEnabled(false); d->tokenUi.leTokenSecret->setToolTip("No secrets needed; will read them from ~/.stokenrc."); } else if (mode == QStringLiteral("manual")) { d->tokenUi.leTokenSecret->setToolTip("Insert the secret here. See the openconnect documentation for syntax."); d->tokenUi.leTokenSecret->setEnabled(true); } else if (mode == QStringLiteral("totp")) { d->tokenUi.leTokenSecret->setEnabled(true); d->tokenUi.leTokenSecret->setToolTip("Insert the secret here, with a sha specification and a leading '0x' or 'base32:'. See the openconnect documentation for syntax."); } else if (mode ==QStringLiteral("hotp")) { d->tokenUi.leTokenSecret->setEnabled(true); d->tokenUi.leTokenSecret->setToolTip("Insert the secret here, with a leading '0x' or 'base32:' and a trailing counter after a comma (','), See the openconnect documentation for syntax."); } else if (mode == QStringLiteral("yubioath")) { d->tokenUi.leTokenSecret->setEnabled(true); d->tokenUi.leTokenSecret->setToolTip("Insert the token Id here, in the form company:username. Make sure to set your Yubikey in CCID mode"); } else { // Not really needed now, but who knows? d->tokenUi.leTokenSecret->setEnabled(false); d->tokenUi.leTokenSecret->setToolTip(""); } } bool OpenconnectSettingWidget::initTokenGroup() { Q_D(const OpenconnectSettingWidget); int validRows = 0; QStringList tokenLabelList = QStringList() << "Disabled" << "RSA SecurID — read from ~/.stokenrc" << "RSA SecurID — manually entered" << "TOTP — manually entered" << "HOTP — manually entered" << "Yubikey"; QStringList tokenModeList = QStringList() << "disabled" << "stokenrc" << "manual" << "totp" << "hotp" << "yubioath"; QComboBox *combo = d->tokenUi.cmbTokenMode; combo->addItem(tokenLabelList[validRows]); combo->setItemData(validRows, tokenModeList[validRows], Qt::UserRole); validRows++; if (openconnect_has_stoken_support ()) { for ( ; validRows < 3; validRows++) { combo->addItem(tokenLabelList[validRows]); combo->setItemData(validRows, tokenModeList[validRows], Qt::UserRole); } } if (openconnect_has_oath_support ()) { combo->addItem(tokenLabelList[validRows]); combo->setItemData(validRows, tokenModeList[validRows], Qt::UserRole); validRows++; if (OPENCONNECT_CHECK_VER(3,4)) { combo->addItem(tokenLabelList[validRows]); combo->setItemData(validRows, tokenModeList[validRows], Qt::UserRole); validRows++; } } if (openconnect_has_yubioath_support ()) { combo->addItem(tokenLabelList[validRows]); combo->setItemData(validRows, tokenModeList[validRows], Qt::UserRole); } return validRows > 0; } void OpenconnectSettingWidget::loadConfig(const NetworkManager::Setting::Ptr &setting) { Q_D(OpenconnectSettingWidget); // General settings const NMStringMap dataMap = setting.staticCast()->data(); int cmbProtocolIndex; if (dataMap[NM_OPENCONNECT_KEY_PROTOCOL] == QLatin1String("anyconnect")) { cmbProtocolIndex = 0; } else if (dataMap[NM_OPENCONNECT_KEY_PROTOCOL] == QLatin1String("nc")) { cmbProtocolIndex = 1; } else { cmbProtocolIndex = 2; // paloAlto/GlobalProtect (gp) } d->ui.cmbProtocol->setCurrentIndex(cmbProtocolIndex); d->ui.leGateway->setText(dataMap[NM_OPENCONNECT_KEY_GATEWAY]); d->ui.leCaCertificate->setUrl(QUrl::fromLocalFile(dataMap[NM_OPENCONNECT_KEY_CACERT])); d->ui.leProxy->setText(dataMap[NM_OPENCONNECT_KEY_PROXY]); d->ui.chkAllowTrojan->setChecked(dataMap[NM_OPENCONNECT_KEY_CSD_ENABLE] == "yes"); d->ui.leCsdWrapperScript->setUrl(QUrl::fromLocalFile(dataMap[NM_OPENCONNECT_KEY_CSD_WRAPPER])); d->ui.leUserCert->setUrl(QUrl::fromLocalFile(dataMap[NM_OPENCONNECT_KEY_USERCERT])); d->ui.leUserPrivateKey->setUrl(QUrl::fromLocalFile(dataMap[NM_OPENCONNECT_KEY_PRIVKEY])); d->ui.chkUseFsid->setChecked(dataMap[NM_OPENCONNECT_KEY_PEM_PASSPHRASE_FSID] == "yes"); d->ui.preventInvalidCert->setChecked(dataMap[NM_OPENCONNECT_KEY_PREVENT_INVALID_CERT] == "yes"); // Token settings const NetworkManager::Setting::SecretFlags tokenSecretFlag = static_cast(dataMap.value(NM_OPENCONNECT_KEY_TOKEN_SECRET"-flags").toInt()); if (tokenSecretFlag == NetworkManager::Setting::None) { d->tokenUi.leTokenSecret->setPasswordOption(PasswordField::StoreForAllUsers); } else if (tokenSecretFlag == NetworkManager::Setting::AgentOwned) { d->tokenUi.leTokenSecret->setPasswordOption(PasswordField::StoreForUser); } else { d->tokenUi.leTokenSecret->setPasswordOption(PasswordField::AlwaysAsk); } for (int index = 0; index < d->tokenUi.cmbTokenMode->count(); index++) { if (d->tokenUi.cmbTokenMode->itemData(index, Qt::UserRole) == dataMap[NM_OPENCONNECT_KEY_TOKEN_MODE]) { d->tokenUi.cmbTokenMode->setCurrentIndex(index); d->token.tokenIndex = index; if (index > 1) { loadSecrets(d->setting); } break; } } } void OpenconnectSettingWidget::loadSecrets(const NetworkManager::Setting::Ptr &setting) { Q_D(OpenconnectSettingWidget); NetworkManager::VpnSetting::Ptr vpnSetting = setting.staticCast(); if (vpnSetting) { const NMStringMap secrets = vpnSetting->secrets(); d->tokenUi.leTokenSecret->setText(secrets.value(NM_OPENCONNECT_KEY_TOKEN_SECRET)); d->token.tokenSecret = secrets.value(NM_OPENCONNECT_KEY_TOKEN_SECRET); } } QVariantMap OpenconnectSettingWidget::setting() const { Q_D(const OpenconnectSettingWidget); NetworkManager::VpnSetting setting; setting.setServiceType(QLatin1String(NM_DBUS_SERVICE_OPENCONNECT)); NMStringMap data; NMStringMap secrets; QString protocol; switch (d->ui.cmbProtocol->currentIndex()) { case 0: protocol = QLatin1String("anyconnect"); break; case 1: protocol = QLatin1String("nc"); break; default: protocol = QLatin1String("gp"); } data.insert(NM_OPENCONNECT_KEY_PROTOCOL, protocol); data.insert(QLatin1String(NM_OPENCONNECT_KEY_GATEWAY), d->ui.leGateway->text()); if (d->ui.leCaCertificate->url().isValid()) { data.insert(QLatin1String(NM_OPENCONNECT_KEY_CACERT), d->ui.leCaCertificate->url().toLocalFile()); } if (!d->ui.leProxy->text().isEmpty()) { data.insert(QLatin1String(NM_OPENCONNECT_KEY_PROXY), d->ui.leProxy->text()); } data.insert(QLatin1String(NM_OPENCONNECT_KEY_CSD_ENABLE), d->ui.chkAllowTrojan->isChecked() ? "yes" : "no"); if (d->ui.leCsdWrapperScript->url().isValid()) { data.insert(QLatin1String(NM_OPENCONNECT_KEY_CSD_WRAPPER), d->ui.leCsdWrapperScript->url().toLocalFile()); } if (d->ui.leUserCert->url().isValid()) { data.insert(QLatin1String(NM_OPENCONNECT_KEY_USERCERT), d->ui.leUserCert->url().toLocalFile()); } if (d->ui.leUserPrivateKey->url().isValid()) { data.insert(QLatin1String(NM_OPENCONNECT_KEY_PRIVKEY), d->ui.leUserPrivateKey->url().toLocalFile()); } data.insert(QLatin1String(NM_OPENCONNECT_KEY_PEM_PASSPHRASE_FSID), d->ui.chkUseFsid->isChecked() ? "yes" : "no"); data.insert(QLatin1String(NM_OPENCONNECT_KEY_PREVENT_INVALID_CERT), d->ui.preventInvalidCert->isChecked() ? "yes" : "no"); int index = d->tokenUi.cmbTokenMode->currentIndex(); data.insert(QLatin1String(NM_OPENCONNECT_KEY_TOKEN_MODE), d->tokenUi.cmbTokenMode->itemData(index, Qt::UserRole).toString()); secrets.insert(QLatin1String(NM_OPENCONNECT_KEY_TOKEN_SECRET), d->tokenUi.leTokenSecret->text()); // Restore previous flags, this is necessary for keeping secrets stored in KWallet for (const QString &key : d->setting->data().keys()) { if (key.contains(QLatin1String("-flags"))) { data.insert(key, d->setting->data().value(key)); } } if (d->tokenUi.leTokenSecret->passwordOption() == PasswordField::StoreForAllUsers) { data.insert(NM_OPENCONNECT_KEY_TOKEN_SECRET"-flags", QString::number(NetworkManager::Setting::None)); } else if (d->tokenUi.leTokenSecret->passwordOption() == PasswordField::StoreForUser) { data.insert(NM_OPENCONNECT_KEY_TOKEN_SECRET"-flags", QString::number(NetworkManager::Setting::AgentOwned)); } else { data.insert(NM_OPENCONNECT_KEY_TOKEN_SECRET"-flags", QString::number(NetworkManager::Setting::NotSaved)); } /* These are different for every login session, and should not be stored */ data.insert(QLatin1String(NM_OPENCONNECT_KEY_COOKIE"-flags"), QString::number(NetworkManager::Setting::NotSaved)); data.insert(QLatin1String(NM_OPENCONNECT_KEY_GWCERT"-flags"), QString::number(NetworkManager::Setting::NotSaved)); data.insert(QLatin1String(NM_OPENCONNECT_KEY_GATEWAY"-flags"), QString::number(NetworkManager::Setting::NotSaved)); setting.setData(data); setting.setSecrets(secrets); return setting.toMap(); } void OpenconnectSettingWidget::restoreTokens() { Q_D(const OpenconnectSettingWidget); d->tokenUi.cmbTokenMode->setCurrentIndex(d->token.tokenIndex); d->tokenUi.leTokenSecret->setText(d->token.tokenSecret); } void OpenconnectSettingWidget::saveTokens() { Q_D(OpenconnectSettingWidget); d->token.tokenIndex = d->tokenUi.cmbTokenMode->currentIndex(); d->token.tokenSecret = d->tokenUi.leTokenSecret->text(); } void OpenconnectSettingWidget::showTokens() { Q_D(OpenconnectSettingWidget); d->tokenDlg->show(); } bool OpenconnectSettingWidget::isValid() const { Q_D(const OpenconnectSettingWidget); return !d->ui.leGateway->text().isEmpty(); } diff --git a/vpn/openswan/openswanauth.cpp b/vpn/openswan/openswanauth.cpp index f87fafe0..a50b64da 100644 --- a/vpn/openswan/openswanauth.cpp +++ b/vpn/openswan/openswanauth.cpp @@ -1,106 +1,108 @@ /* Copyright 2013 Jan Grulich This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) version 3, or any later version accepted by the membership of KDE e.V. (or its successor approved by the membership of KDE e.V.), which shall act as a proxy defined in Section 6 of version 3 of the license. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library. If not, see . */ #include "openswanauth.h" #include "ui_openswanauth.h" #include "nm-openswan-service.h" #include +#include + class OpenswanAuthDialogPrivate { public: Ui_OpenswanAuth ui; NetworkManager::VpnSetting::Ptr setting; }; OpenswanAuthDialog::OpenswanAuthDialog(const NetworkManager::VpnSetting::Ptr &setting, QWidget * parent) : SettingWidget(setting, parent) , d_ptr(new OpenswanAuthDialogPrivate) { Q_D(OpenswanAuthDialog); d->ui.setupUi(this); d->setting = setting; readSecrets(); KAcceleratorManager::manage(this); } OpenswanAuthDialog::~OpenswanAuthDialog() { delete d_ptr; } void OpenswanAuthDialog::readSecrets() { Q_D(OpenswanAuthDialog); const NMStringMap data = d->setting->data(); const NMStringMap secrets = d->setting->secrets(); const QString groupName = data.value(NM_OPENSWAN_LEFTID); if (!groupName.isEmpty()) { d->ui.leGroupName->setText(groupName); } bool haveUserPassword = true; if (data.value(NM_OPENSWAN_XAUTH_PASSWORD_INPUT_MODES) != NM_OPENSWAN_PW_TYPE_UNUSED) { d->ui.leUserPassword->setText(secrets.value(NM_OPENSWAN_XAUTH_PASSWORD)); } else { d->ui.leUserPassword->setVisible(false); d->ui.userPasswordLabel->setVisible(false); haveUserPassword = false; } bool haveGroupPassword = true; if (data.value(NM_OPENSWAN_PSK_INPUT_MODES) != NM_OPENSWAN_PW_TYPE_UNUSED) { d->ui.leGroupPassword->setText(secrets.value(NM_OPENSWAN_PSK_VALUE)); } else { d->ui.leGroupPassword->setVisible(false); d->ui.groupPasswordLabel->setVisible(false); haveGroupPassword = false; } if (haveUserPassword && d->ui.leUserPassword->text().isEmpty()) { d->ui.leUserPassword->setFocus(Qt::OtherFocusReason); } else if (haveGroupPassword && d->ui.leGroupPassword->text().isEmpty()) { d->ui.leGroupPassword->setFocus(Qt::OtherFocusReason); } } QVariantMap OpenswanAuthDialog::setting() const { Q_D(const OpenswanAuthDialog); NMStringMap secrets; QVariantMap result; if (!d->ui.leUserPassword->text().isEmpty()) { secrets.insert(NM_OPENSWAN_XAUTH_PASSWORD, d->ui.leUserPassword->text()); } if (!d->ui.leGroupPassword->text().isEmpty()) { secrets.insert(NM_OPENSWAN_PSK_VALUE, d->ui.leGroupPassword->text()); } result.insert("secrets", QVariant::fromValue(secrets)); return result; } diff --git a/vpn/openswan/openswanwidget.cpp b/vpn/openswan/openswanwidget.cpp index 979a4522..5827e44c 100644 --- a/vpn/openswan/openswanwidget.cpp +++ b/vpn/openswan/openswanwidget.cpp @@ -1,203 +1,205 @@ /* Copyright 2013 Jan Grulich This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) version 3, or any later version accepted by the membership of KDE e.V. (or its successor approved by the membership of KDE e.V.), which shall act as a proxy defined in Section 6 of version 3 of the license. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library. If not, see . */ #include "openswanwidget.h" #include "ui_openswan.h" #include "nm-openswan-service.h" #include #include +#include + OpenswanWidget::OpenswanWidget(const NetworkManager::VpnSetting::Ptr &setting, QWidget *parent, Qt::WindowFlags f) : SettingWidget(setting, parent, f) , m_ui(new Ui::OpenswanWidget) , m_setting(setting) { qDBusRegisterMetaType(); m_ui->setupUi(this); m_ui->groupPassword->setPasswordOptionsEnabled(true); m_ui->userPassword->setPasswordOptionsEnabled(true); // Connect for setting check watchChangedSetting(); // Connect for validity check connect(m_ui->gateway, &QLineEdit::textChanged, this, &OpenswanWidget::slotWidgetChanged); connect(m_ui->groupname, &QLineEdit::textChanged, this, &OpenswanWidget::slotWidgetChanged); KAcceleratorManager::manage(this); if (setting && !setting->isNull()) { loadConfig(setting); } } OpenswanWidget::~OpenswanWidget() { delete m_ui; } void OpenswanWidget::loadConfig(const NetworkManager::Setting::Ptr &setting) { Q_UNUSED(setting); const NMStringMap data = m_setting->data(); const QString gateway = data.value(NM_OPENSWAN_RIGHT); if (!gateway.isEmpty()) { m_ui->gateway->setText(gateway); } const QString groupName = data.value(NM_OPENSWAN_LEFTID); if (!groupName.isEmpty()) { m_ui->groupname->setText(groupName); } const NetworkManager::Setting::SecretFlags groupPasswordFlag = static_cast(data.value(NM_OPENSWAN_PSK_VALUE"-flags").toInt()); if (groupPasswordFlag == NetworkManager::Setting::None) { m_ui->groupPassword->setPasswordOption(PasswordField::StoreForAllUsers); } else if (groupPasswordFlag == NetworkManager::Setting::AgentOwned) { m_ui->groupPassword->setPasswordOption(PasswordField::StoreForUser); } else { m_ui->groupPassword->setPasswordOption(PasswordField::AlwaysAsk); } const NetworkManager::Setting::SecretFlags userPasswordFlag = static_cast(data.value(NM_OPENSWAN_XAUTH_PASSWORD"-flags").toInt()); if (userPasswordFlag == NetworkManager::Setting::None) { m_ui->userPassword->setPasswordOption(PasswordField::StoreForAllUsers); } else if (userPasswordFlag == NetworkManager::Setting::AgentOwned) { m_ui->userPassword->setPasswordOption(PasswordField::StoreForUser); } else { m_ui->userPassword->setPasswordOption(PasswordField::AlwaysAsk); } const QString username = data.value(NM_OPENSWAN_LEFTXAUTHUSER); if (!username.isEmpty()) { m_ui->username->setText(username); } const QString phase1 = data.value(NM_OPENSWAN_IKE); if (!phase1.isEmpty()) { m_ui->phase1->setText(phase1); } const QString phase2 = data.value(NM_OPENSWAN_ESP); if (!phase2.isEmpty()) { m_ui->phase2->setText(phase2); } const QString domain = data.value(NM_OPENSWAN_DOMAIN); if (!domain.isEmpty()) { m_ui->domain->setText(domain); } loadSecrets(setting); } void OpenswanWidget::loadSecrets(const NetworkManager::Setting::Ptr &setting) { NetworkManager::VpnSetting::Ptr vpnSetting = setting.staticCast(); if (vpnSetting) { const NMStringMap secrets = vpnSetting->secrets(); const QString userPassword = secrets.value(NM_OPENSWAN_XAUTH_PASSWORD); if (!userPassword.isEmpty()) { m_ui->userPassword->setText(userPassword); } const QString groupPassword = secrets.value(NM_OPENSWAN_PSK_VALUE); if (!groupPassword.isEmpty()) { m_ui->groupPassword->setText(groupPassword); } } } QVariantMap OpenswanWidget::setting() const { NetworkManager::VpnSetting setting; setting.setServiceType(QLatin1String(NM_DBUS_SERVICE_OPENSWAN)); NMStringMap data; NMStringMap secrets; if (!m_ui->gateway->text().isEmpty()) { data.insert(NM_OPENSWAN_RIGHT, m_ui->gateway->text()); } if (!m_ui->groupname->text().isEmpty()) { data.insert(NM_OPENSWAN_LEFTID, m_ui->groupname->text()); } if (!m_ui->userPassword->text().isEmpty()) { secrets.insert(NM_OPENSWAN_XAUTH_PASSWORD, m_ui->userPassword->text()); } if (m_ui->userPassword->passwordOption() == PasswordField::StoreForAllUsers) { data.insert(NM_OPENSWAN_XAUTH_PASSWORD_INPUT_MODES, NM_OPENSWAN_PW_TYPE_SAVE); data.insert(NM_OPENSWAN_XAUTH_PASSWORD"-flags", QString::number(NetworkManager::Setting::None)); } else if (m_ui->userPassword->passwordOption() == PasswordField::StoreForUser) { data.insert(NM_OPENSWAN_XAUTH_PASSWORD"-flags", QString::number(NetworkManager::Setting::AgentOwned)); } else { data.insert(NM_OPENSWAN_XAUTH_PASSWORD_INPUT_MODES, NM_OPENSWAN_PW_TYPE_ASK); data.insert(NM_OPENSWAN_XAUTH_PASSWORD"-flags", QString::number(NetworkManager::Setting::NotSaved)); } if (!m_ui->groupPassword->text().isEmpty()) { secrets.insert(NM_OPENSWAN_PSK_VALUE, m_ui->groupPassword->text()); } if (m_ui->groupPassword->passwordOption() == PasswordField::StoreForAllUsers) { data.insert(NM_OPENSWAN_PSK_INPUT_MODES, NM_OPENSWAN_PW_TYPE_SAVE); data.insert(NM_OPENSWAN_PSK_VALUE"-flags", QString::number(NetworkManager::Setting::None)); } else if (m_ui->groupPassword->passwordOption() == PasswordField::StoreForUser) { data.insert(NM_OPENSWAN_PSK_VALUE"-flags", QString::number(NetworkManager::Setting::AgentOwned)); } else { data.insert(NM_OPENSWAN_PSK_INPUT_MODES, NM_OPENSWAN_PW_TYPE_ASK); data.insert(NM_OPENSWAN_PSK_VALUE"-flags", QString::number(NetworkManager::Setting::NotSaved)); } if (!m_ui->username->text().isEmpty()) { data.insert(NM_OPENSWAN_LEFTXAUTHUSER, m_ui->username->text()); } if (!m_ui->phase1->text().isEmpty()) { data.insert(NM_OPENSWAN_IKE, m_ui->phase1->text()); } if (!m_ui->phase2->text().isEmpty()) { data.insert(NM_OPENSWAN_ESP, m_ui->phase2->text()); } if (!m_ui->domain->text().isEmpty()) { data.insert(NM_OPENSWAN_DOMAIN, m_ui->domain->text()); } setting.setData(data); setting.setSecrets(secrets); return setting.toMap(); } bool OpenswanWidget::isValid() const { return !m_ui->gateway->text().isEmpty() && !m_ui->groupname->text().isEmpty(); } diff --git a/vpn/openvpn/openvpnauth.cpp b/vpn/openvpn/openvpnauth.cpp index a6e0e571..734dd304 100644 --- a/vpn/openvpn/openvpnauth.cpp +++ b/vpn/openvpn/openvpnauth.cpp @@ -1,146 +1,147 @@ /* Copyright 2011 Ilia Kats Copyright 2013 Lukáš Tinkl This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License or (at your option) version 3 or any later version accepted by the membership of KDE e.V. (or its successor approved by the membership of KDE e.V.), which shall act as a proxy defined in Section 14 of version 3 of the license. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see . */ #include "openvpnauth.h" #include "passwordfield.h" #include #include #include #include +#include #include #include "nm-openvpn-service.h" #include "debug.h" class OpenVpnAuthWidgetPrivate { public: NetworkManager::VpnSetting::Ptr setting; QFormLayout *layout; }; OpenVpnAuthWidget::OpenVpnAuthWidget(const NetworkManager::VpnSetting::Ptr &setting, QWidget * parent) : SettingWidget(setting, parent) , d_ptr(new OpenVpnAuthWidgetPrivate) { Q_D(OpenVpnAuthWidget); d->setting = setting; d->layout = new QFormLayout(this); setLayout(d->layout); readSecrets(); KAcceleratorManager::manage(this); } OpenVpnAuthWidget::~OpenVpnAuthWidget() { delete d_ptr; } void OpenVpnAuthWidget::readSecrets() { Q_D(OpenVpnAuthWidget); const NMStringMap secrets = d->setting->secrets(); const NMStringMap dataMap = d->setting->data(); const QString cType = dataMap[NM_OPENVPN_KEY_CONNECTION_TYPE]; QLabel *label; PasswordField *lineEdit; NetworkManager::Setting::SecretFlags certType = (NetworkManager::Setting::SecretFlags)dataMap.value(NM_OPENVPN_KEY_CERTPASS"-flags").toInt(); NetworkManager::Setting::SecretFlags passType = (NetworkManager::Setting::SecretFlags)dataMap.value(NM_OPENVPN_KEY_PASSWORD"-flags").toInt(); NetworkManager::Setting::SecretFlags proxyType = (NetworkManager::Setting::SecretFlags)dataMap.value(NM_OPENVPN_KEY_HTTP_PROXY_PASSWORD"-flags").toInt(); if (cType == QLatin1String(NM_OPENVPN_CONTYPE_TLS) && !(certType.testFlag(NetworkManager::Setting::NotRequired))) { label = new QLabel(this); label->setText(i18n("Key Password:")); lineEdit = new PasswordField(this); lineEdit->setPasswordModeEnabled(true); lineEdit->setProperty("nm_secrets_key", QLatin1String(NM_OPENVPN_KEY_CERTPASS)); lineEdit->setText(secrets.value(QLatin1String(NM_OPENVPN_KEY_CERTPASS))); d->layout->addRow(label, lineEdit); } else if (cType == QLatin1String(NM_OPENVPN_CONTYPE_PASSWORD) && !(passType.testFlag(NetworkManager::Setting::NotRequired))) { label = new QLabel(this); label->setText(i18n("Password:")); lineEdit = new PasswordField(this); lineEdit->setPasswordModeEnabled(true); lineEdit->setProperty("nm_secrets_key", QLatin1String(NM_OPENVPN_KEY_PASSWORD)); lineEdit->setText(secrets.value(QLatin1String(NM_OPENVPN_KEY_PASSWORD))); d->layout->addRow(label, lineEdit); } else if (cType == QLatin1String(NM_OPENVPN_CONTYPE_PASSWORD_TLS)) { if (!(passType.testFlag(NetworkManager::Setting::NotRequired))) { label = new QLabel(this); label->setText(i18n("Password:")); lineEdit = new PasswordField(this); lineEdit->setPasswordModeEnabled(true); lineEdit->setProperty("nm_secrets_key", QLatin1String(NM_OPENVPN_KEY_PASSWORD)); lineEdit->setText(secrets.value(QLatin1String(NM_OPENVPN_KEY_PASSWORD))); d->layout->addRow(label, lineEdit); } if (!(certType.testFlag(NetworkManager::Setting::NotRequired))) { label = new QLabel(this); label->setText(i18n("Key Password:")); lineEdit = new PasswordField(this); lineEdit->setPasswordModeEnabled(true); lineEdit->setProperty("nm_secrets_key", QLatin1String(NM_OPENVPN_KEY_CERTPASS)); lineEdit->setText(secrets.value(QLatin1String(NM_OPENVPN_KEY_CERTPASS))); d->layout->addRow(label, lineEdit); } } if (dataMap.contains(NM_OPENVPN_KEY_HTTP_PROXY_PASSWORD"-flags") && !(proxyType.testFlag(NetworkManager::Setting::NotRequired))) { label = new QLabel(this); label->setText(i18n("Proxy Password:")); lineEdit = new PasswordField(this); lineEdit->setPasswordModeEnabled(true); lineEdit->setProperty("nm_secrets_key", QLatin1String(NM_OPENVPN_KEY_HTTP_PROXY_PASSWORD)); lineEdit->setText(secrets.value(QLatin1String(NM_OPENVPN_KEY_HTTP_PROXY_PASSWORD))); d->layout->addRow(label, lineEdit); } for (int i = 0; i < d->layout->rowCount(); i++) { PasswordField *le = qobject_cast(d->layout->itemAt(i, QFormLayout::FieldRole)->widget()); if (le && le->text().isEmpty()) { le->setFocus(Qt::OtherFocusReason); break; } } } QVariantMap OpenVpnAuthWidget::setting() const { Q_D(const OpenVpnAuthWidget); NMStringMap secrets; QVariantMap secretData; for (int i = 0; i < d->layout->rowCount(); i++) { PasswordField *le = qobject_cast(d->layout->itemAt(i, QFormLayout::FieldRole)->widget()); if (le && !le->text().isEmpty()) { const QString key = le->property("nm_secrets_key").toString(); secrets.insert(key, le->text()); } } secretData.insert("secrets", QVariant::fromValue(secrets)); return secretData; } diff --git a/vpn/openvpn/openvpnwidget.cpp b/vpn/openvpn/openvpnwidget.cpp index 4ecd1021..7bdcd7af 100644 --- a/vpn/openvpn/openvpnwidget.cpp +++ b/vpn/openvpn/openvpnwidget.cpp @@ -1,353 +1,354 @@ /* Copyright 2008 Will Stephenson Copyright 2013 Lukáš Tinkl This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License or (at your option) version 3 or any later version accepted by the membership of KDE e.V. (or its successor approved by the membership of KDE e.V.), which shall act as a proxy defined in Section 14 of version 3 of the license. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see . */ #include "debug.h" #include "openvpnwidget.h" #include "openvpnadvancedwidget.h" #include #include #include #include +#include #include #include #include "nm-openvpn-service.h" class OpenVpnSettingWidget::Private { public: Ui_OpenVPNProp ui; NetworkManager::VpnSetting::Ptr setting; class EnumConnectionType { public: enum ConnectionType {Certificates = 0, Psk, Password, CertsPassword}; }; class EnumKeyDirection { public: enum KeyDirection {None = 0, D0, D1}; }; }; OpenVpnSettingWidget::OpenVpnSettingWidget(const NetworkManager::VpnSetting::Ptr &setting, QWidget *parent) : SettingWidget(setting, parent) , d(new Private) { qDBusRegisterMetaType(); d->ui.setupUi(this); d->setting = setting; d->ui.x509KeyPassword->setPasswordOptionsEnabled(true); d->ui.x509KeyPassword->setPasswordNotRequiredEnabled(true); d->ui.passPassword->setPasswordOptionsEnabled(true); d->ui.passPassword->setPasswordNotRequiredEnabled(true); d->ui.x509PassKeyPassword->setPasswordOptionsEnabled(true); d->ui.x509PassKeyPassword->setPasswordNotRequiredEnabled(true); d->ui.x509PassPassword->setPasswordOptionsEnabled(true); d->ui.x509PassPassword->setPasswordNotRequiredEnabled(true); // use requesters' urlSelected signals to set other requester's startDirs to save clicking // around the filesystem QList requesters; requesters << d->ui.x509CaFile << d->ui.x509Cert << d->ui.x509Key << d->ui.pskSharedKey << d->ui.passCaFile << d->ui.x509PassCaFile << d->ui.x509PassCert << d->ui.x509PassKey; for (const KUrlRequester *requester : requesters) { connect(requester, &KUrlRequester::urlSelected, this, &OpenVpnSettingWidget::updateStartDir); } connect(d->ui.btnAdvanced, &QPushButton::clicked, this, &OpenVpnSettingWidget::showAdvanced); // Connect for setting check watchChangedSetting(); // Connect for validity check connect(d->ui.gateway, &QLineEdit::textChanged, this, &OpenVpnSettingWidget::slotWidgetChanged); KAcceleratorManager::manage(this); if (setting && !setting->isNull()) { loadConfig(d->setting); } } OpenVpnSettingWidget::~OpenVpnSettingWidget() { delete d; } void OpenVpnSettingWidget::loadConfig(const NetworkManager::Setting::Ptr &setting) { Q_UNUSED(setting) // General settings const NMStringMap dataMap = d->setting->data(); const QString cType = dataMap.value(NM_OPENVPN_KEY_CONNECTION_TYPE); if (cType == QLatin1String(NM_OPENVPN_CONTYPE_PASSWORD_TLS)) { d->ui.cmbConnectionType->setCurrentIndex(Private::EnumConnectionType::CertsPassword); d->ui.x509PassUsername->setText(dataMap[NM_OPENVPN_KEY_USERNAME]); d->ui.x509PassCaFile->setUrl(QUrl::fromLocalFile(dataMap[NM_OPENVPN_KEY_CA])); d->ui.x509PassCert->setUrl(QUrl::fromLocalFile(dataMap[NM_OPENVPN_KEY_CERT])); d->ui.x509PassKey->setUrl(QUrl::fromLocalFile(dataMap[NM_OPENVPN_KEY_KEY])); } else if (cType == QLatin1String( NM_OPENVPN_CONTYPE_STATIC_KEY)) { d->ui.cmbConnectionType->setCurrentIndex( Private::EnumConnectionType::Psk ); d->ui.pskSharedKey->setText( dataMap[NM_OPENVPN_KEY_STATIC_KEY]); if (dataMap.contains(NM_OPENVPN_KEY_STATIC_KEY_DIRECTION)) { switch (dataMap[NM_OPENVPN_KEY_STATIC_KEY_DIRECTION].toUInt()) { case 0: d->ui.cmbKeyDirection->setCurrentIndex(Private::EnumKeyDirection::D0); break; case 1: d->ui.cmbKeyDirection->setCurrentIndex(Private::EnumKeyDirection::D1); break; } } else { d->ui.cmbKeyDirection->setCurrentIndex(Private::EnumKeyDirection::None); } d->ui.pskRemoteIp->setText(dataMap[NM_OPENVPN_KEY_REMOTE_IP]); d->ui.pskLocalIp->setText(dataMap[NM_OPENVPN_KEY_LOCAL_IP]); } else if (cType == QLatin1String(NM_OPENVPN_CONTYPE_PASSWORD)) { d->ui.cmbConnectionType->setCurrentIndex(Private::EnumConnectionType::Password); d->ui.passUserName->setText(dataMap[NM_OPENVPN_KEY_USERNAME] ); d->ui.passCaFile->setUrl(QUrl::fromLocalFile(dataMap[NM_OPENVPN_KEY_CA])); } else if (cType == QLatin1String(NM_OPENVPN_CONTYPE_TLS)) { d->ui.cmbConnectionType->setCurrentIndex(Private::EnumConnectionType::Certificates); d->ui.x509CaFile->setUrl(QUrl::fromLocalFile(dataMap[NM_OPENVPN_KEY_CA])); d->ui.x509Cert->setUrl(QUrl::fromLocalFile(dataMap[NM_OPENVPN_KEY_CERT])); d->ui.x509Key->setUrl(QUrl::fromLocalFile(dataMap[NM_OPENVPN_KEY_KEY])); } d->ui.gateway->setText( dataMap[NM_OPENVPN_KEY_REMOTE] ); NetworkManager::Setting::SecretFlags type; if (cType == QLatin1String(NM_OPENVPN_CONTYPE_TLS)) { type = (NetworkManager::Setting::SecretFlags)dataMap[NM_OPENVPN_KEY_CERTPASS"-flags"].toInt(); fillOnePasswordCombo(d->ui.x509KeyPassword, type); } else if (cType == QLatin1String(NM_OPENVPN_CONTYPE_PASSWORD)) { type = (NetworkManager::Setting::SecretFlags)dataMap[NM_OPENVPN_KEY_PASSWORD"-flags"].toInt(); fillOnePasswordCombo(d->ui.passPassword, type); } else if (cType == QLatin1String(NM_OPENVPN_CONTYPE_PASSWORD_TLS)) { type = (NetworkManager::Setting::SecretFlags)dataMap[NM_OPENVPN_KEY_PASSWORD"-flags"].toInt(); fillOnePasswordCombo(d->ui.x509PassPassword, type); type = (NetworkManager::Setting::SecretFlags)dataMap[NM_OPENVPN_KEY_CERTPASS"-flags"].toInt(); fillOnePasswordCombo(d->ui.x509PassKeyPassword, type); } loadSecrets(setting); } void OpenVpnSettingWidget::loadSecrets(const NetworkManager::Setting::Ptr &setting) { NetworkManager::VpnSetting::Ptr vpnSetting = setting.staticCast(); if (vpnSetting) { const QString cType = d->setting->data().value(NM_OPENVPN_KEY_CONNECTION_TYPE); const NMStringMap secrets = vpnSetting->secrets(); if (cType == QLatin1String(NM_OPENVPN_CONTYPE_TLS)) { d->ui.x509KeyPassword->setText(secrets.value(NM_OPENVPN_KEY_CERTPASS)); } else if (cType == QLatin1String(NM_OPENVPN_CONTYPE_PASSWORD)) { d->ui.passPassword->setText(secrets.value(NM_OPENVPN_KEY_PASSWORD)); } else if (cType == QLatin1String(NM_OPENVPN_CONTYPE_PASSWORD_TLS)) { d->ui.x509PassPassword->setText(secrets.value(NM_OPENVPN_KEY_PASSWORD)); d->ui.x509PassKeyPassword->setText(secrets.value(NM_OPENVPN_KEY_CERTPASS)); } } } QVariantMap OpenVpnSettingWidget::setting() const { NMStringMap data = d->setting->data(); NMStringMap secretData = d->setting->secrets(); NetworkManager::VpnSetting setting; setting.setServiceType(QLatin1String(NM_DBUS_SERVICE_OPENVPN)); // required settings data.insert(QLatin1String(NM_OPENVPN_KEY_REMOTE), d->ui.gateway->text()); QString contype; switch ( d->ui.cmbConnectionType->currentIndex()) { case Private::EnumConnectionType::Certificates: contype = QLatin1String(NM_OPENVPN_CONTYPE_TLS); // qCDebug(PLASMA_NM) << "saving VPN TLS settings as urls:" << d->ui.x509CaFile->url() << d->ui.x509Cert->url() << d->ui.x509Key->url(); data.insert(QLatin1String(NM_OPENVPN_KEY_CA), d->ui.x509CaFile->url().toLocalFile()); data.insert(QLatin1String(NM_OPENVPN_KEY_CERT), d->ui.x509Cert->url().toLocalFile()); data.insert(QLatin1String(NM_OPENVPN_KEY_KEY), d->ui.x509Key->url().toLocalFile()); // key password if (!d->ui.x509KeyPassword->text().isEmpty()) { secretData.insert(QLatin1String(NM_OPENVPN_KEY_CERTPASS), d->ui.x509KeyPassword->text()); } else { secretData.remove(QLatin1String(NM_OPENVPN_KEY_CERTPASS)); } handleOnePasswordType(d->ui.x509KeyPassword, QLatin1String(NM_OPENVPN_KEY_CERTPASS"-flags"), data); break; case Private::EnumConnectionType::Psk: contype = QLatin1String(NM_OPENVPN_CONTYPE_STATIC_KEY); data.insert(QLatin1String(NM_OPENVPN_KEY_STATIC_KEY), d->ui.pskSharedKey->url().toLocalFile()); switch (d->ui.cmbKeyDirection->currentIndex()) { case Private::EnumKeyDirection::None: break; case Private::EnumKeyDirection::D0: data.insert(QLatin1String(NM_OPENVPN_KEY_STATIC_KEY_DIRECTION), QString::number(0)); break; case Private::EnumKeyDirection::D1: data.insert(QLatin1String(NM_OPENVPN_KEY_STATIC_KEY_DIRECTION), QString::number(1)); break; } // ip addresses data.insert(QLatin1String(NM_OPENVPN_KEY_REMOTE_IP), d->ui.pskRemoteIp->text()); data.insert(QLatin1String(NM_OPENVPN_KEY_LOCAL_IP), d->ui.pskLocalIp->text()); break; case Private::EnumConnectionType::Password: contype = QLatin1String(NM_OPENVPN_CONTYPE_PASSWORD); // username if (!d->ui.passUserName->text().isEmpty()) { data.insert(QLatin1String(NM_OPENVPN_KEY_USERNAME), d->ui.passUserName->text()); } else { data.remove(QLatin1String(NM_OPENVPN_KEY_USERNAME)); } // password if (!d->ui.passPassword->text().isEmpty()) { secretData.insert(QLatin1String(NM_OPENVPN_KEY_PASSWORD), d->ui.passPassword->text()); } else { secretData.remove(QLatin1String(NM_OPENVPN_KEY_PASSWORD)); } handleOnePasswordType(d->ui.passPassword, QLatin1String(NM_OPENVPN_KEY_PASSWORD"-flags"), data); // ca data.insert(QLatin1String(NM_OPENVPN_KEY_CA), d->ui.passCaFile->url().toLocalFile()); break; case Private::EnumConnectionType::CertsPassword: contype = QLatin1String(NM_OPENVPN_CONTYPE_PASSWORD_TLS); // username if (!d->ui.x509PassUsername->text().isEmpty()) { data.insert(QLatin1String(NM_OPENVPN_KEY_USERNAME), d->ui.x509PassUsername->text()); } else { data.remove(QLatin1String(NM_OPENVPN_KEY_USERNAME)); } // ca data.insert(QLatin1String(NM_OPENVPN_KEY_CA), d->ui.x509PassCaFile->url().toLocalFile()); // cert data.insert(QLatin1String(NM_OPENVPN_KEY_CERT), d->ui.x509PassCert->url().toLocalFile()); // key file data.insert(QLatin1String(NM_OPENVPN_KEY_KEY), d->ui.x509PassKey->url().toLocalFile()); // key password if (!d->ui.x509PassKeyPassword->text().isEmpty()) { secretData.insert(QLatin1String(NM_OPENVPN_KEY_CERTPASS), d->ui.x509PassKeyPassword->text()); } else { secretData.remove(QLatin1String(NM_OPENVPN_KEY_CERTPASS)); } handleOnePasswordType(d->ui.x509PassKeyPassword, QLatin1String(NM_OPENVPN_KEY_CERTPASS"-flags"), data); // password if (!d->ui.x509PassPassword->text().isEmpty()) { secretData.insert(QLatin1String(NM_OPENVPN_KEY_PASSWORD), d->ui.x509PassPassword->text()); } else { secretData.remove(QLatin1String(NM_OPENVPN_KEY_PASSWORD)); } handleOnePasswordType(d->ui.x509PassPassword, QLatin1String(NM_OPENVPN_KEY_PASSWORD"-flags"), data); break; } data.insert(QLatin1String(NM_OPENVPN_KEY_CONNECTION_TYPE), contype); setting.setData(data); setting.setSecrets(secretData); return setting.toMap(); } void OpenVpnSettingWidget::updateStartDir(const QUrl &url) { QList requesters; requesters << d->ui.x509CaFile << d->ui.x509Cert << d->ui.x509Key << d->ui.pskSharedKey << d->ui.passCaFile << d->ui.x509PassCaFile << d->ui.x509PassCert << d->ui.x509PassKey; for (KUrlRequester *requester : requesters) { requester->setStartDir(url.adjusted(QUrl::RemoveFilename | QUrl::StripTrailingSlash)); } } void OpenVpnSettingWidget::setPasswordType(QLineEdit *edit, int type) { edit->setEnabled(type == SettingWidget::EnumPasswordStorageType::Store); } void OpenVpnSettingWidget::fillOnePasswordCombo(PasswordField *passwordField, NetworkManager::Setting::SecretFlags type) { if (type.testFlag(NetworkManager::Setting::None)) { passwordField->setPasswordOption(PasswordField::StoreForAllUsers); } else if (type.testFlag(NetworkManager::Setting::AgentOwned)) { passwordField->setPasswordOption(PasswordField::StoreForUser); } else if (type.testFlag(NetworkManager::Setting::NotSaved)) { passwordField->setPasswordOption(PasswordField::AlwaysAsk); } else if (type.testFlag(NetworkManager::Setting::NotRequired)) { passwordField->setPasswordOption(PasswordField::NotRequired); } } void OpenVpnSettingWidget::handleOnePasswordType(const PasswordField *passwordField, const QString &key, NMStringMap &data) const { const PasswordField::PasswordOption option = passwordField->passwordOption(); switch (option) { case PasswordField::StoreForAllUsers: data.insert(key, QString::number(NetworkManager::Setting::None)); break; case PasswordField::StoreForUser: data.insert(key, QString::number(NetworkManager::Setting::AgentOwned)); break; case PasswordField::AlwaysAsk: data.insert(key, QString::number(NetworkManager::Setting::NotSaved)); break; case PasswordField::NotRequired: data.insert(key, QString::number(NetworkManager::Setting::NotRequired)); break; } } void OpenVpnSettingWidget::showAdvanced() { QPointer adv = new OpenVpnAdvancedWidget(d->setting, this); adv->init(); connect(adv.data(), &OpenVpnAdvancedWidget::accepted, [adv, this] () { NetworkManager::VpnSetting::Ptr advData = adv->setting(); if (!advData.isNull()) { d->setting->setData(advData->data()); d->setting->setSecrets(advData->secrets()); } }); connect(adv.data(), &OpenVpnAdvancedWidget::finished, [adv] () { if (adv) { adv->deleteLater(); } }); adv->setModal(true); adv->show(); } bool OpenVpnSettingWidget::isValid() const { return !d->ui.gateway->text().isEmpty(); } diff --git a/vpn/pptp/pptpauth.cpp b/vpn/pptp/pptpauth.cpp index 66ad578f..8802d9ba 100644 --- a/vpn/pptp/pptpauth.cpp +++ b/vpn/pptp/pptpauth.cpp @@ -1,63 +1,65 @@ /* Copyright 2011 Ilia Kats Copyright 2013 Lukáš Tinkl This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License or (at your option) version 3 or any later version accepted by the membership of KDE e.V. (or its successor approved by the membership of KDE e.V.), which shall act as a proxy defined in Section 14 of version 3 of the license. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see . */ #include "pptpauth.h" #include "ui_pptpauth.h" #include "nm-pptp-service.h" +#include + class PptpAuthWidgetPrivate { public: NetworkManager::VpnSetting::Ptr setting; Ui_PptpAuthenticationWidget ui; }; PptpAuthWidget::PptpAuthWidget(const NetworkManager::VpnSetting::Ptr &setting, QWidget * parent) : SettingWidget(setting, parent) , d_ptr(new PptpAuthWidgetPrivate) { Q_D(PptpAuthWidget); d->setting = setting; d->ui.setupUi(this); KAcceleratorManager::manage(this); } PptpAuthWidget::~PptpAuthWidget() { delete d_ptr; } QVariantMap PptpAuthWidget::setting() const { Q_D(const PptpAuthWidget); NMStringMap secrets; QVariantMap secretData; if (!d->ui.lePassword->text().isEmpty()) { secrets.insert(QLatin1String(NM_PPTP_KEY_PASSWORD), d->ui.lePassword->text()); } secretData.insert("secrets", QVariant::fromValue(secrets)); return secretData; } diff --git a/vpn/pptp/pptpwidget.cpp b/vpn/pptp/pptpwidget.cpp index c5bf4167..88ca8321 100644 --- a/vpn/pptp/pptpwidget.cpp +++ b/vpn/pptp/pptpwidget.cpp @@ -1,323 +1,325 @@ /* Copyright 2009 Will Stephenson Copyright 2009 Pavel Andreev Copyright 2013 Lukáš Tinkl This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License or (at your option) version 3 or any later version accepted by the membership of KDE e.V. (or its successor approved by the membership of KDE e.V.), which shall act as a proxy defined in Section 14 of version 3 of the license. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see . */ #include "pptpwidget.h" #include "ui_pptpprop.h" #include "ui_pptpadvanced.h" #include #include #include +#include + #include "nm-pptp-service.h" class PptpSettingWidgetPrivate { public: Ui_PptpProp ui; Ui_PptpAdvanced advUi; NetworkManager::VpnSetting::Ptr setting; QDialog *advancedDlg; QWidget *advancedWid; }; PptpSettingWidget::PptpSettingWidget(const NetworkManager::VpnSetting::Ptr &setting, QWidget *parent) : SettingWidget(setting, parent) , d_ptr(new PptpSettingWidgetPrivate) { Q_D(PptpSettingWidget); d->ui.setupUi(this); d->setting = setting; d->ui.edt_password->setPasswordOptionsEnabled(true); d->ui.edt_password->setPasswordNotRequiredEnabled(true); connect(d->ui.btnAdvanced, &QPushButton::clicked, this, &PptpSettingWidget::doAdvancedDialog); d->advancedDlg = new QDialog(this); d->advancedWid = new QWidget(this); d->advUi.setupUi(d->advancedWid); QVBoxLayout * layout = new QVBoxLayout(d->advancedDlg); layout->addWidget(d->advancedWid); d->advancedDlg->setLayout(layout); QDialogButtonBox* buttons = new QDialogButtonBox(QDialogButtonBox::Ok|QDialogButtonBox::Cancel, d->advancedDlg); connect(buttons, &QDialogButtonBox::accepted, d->advancedDlg, &QDialog::accept); connect(buttons, &QDialogButtonBox::rejected, d->advancedDlg, &QDialog::reject); layout->addWidget(buttons); // Connect for setting check watchChangedSetting(); // Connect for validity check connect(d->ui.edt_gateway, &QLineEdit::textChanged, this, &PptpSettingWidget::slotWidgetChanged); KAcceleratorManager::manage(this); if (d->setting && !d->setting->isNull()) { loadConfig(d->setting); } } PptpSettingWidget::~PptpSettingWidget() { delete d_ptr; } void PptpSettingWidget::doAdvancedDialog() { Q_D(PptpSettingWidget); d->advancedDlg->setModal(true); d->advancedDlg->show(); } void PptpSettingWidget::loadConfig(const NetworkManager::Setting::Ptr &setting) { Q_D(PptpSettingWidget); Q_UNUSED(setting) // General settings const NMStringMap dataMap = d->setting->data(); // Authentication const QString sGateway = dataMap[NM_PPTP_KEY_GATEWAY]; if (!sGateway.isEmpty()) { d->ui.edt_gateway->setText(sGateway); } const QString sLogin = dataMap[NM_PPTP_KEY_USER]; if (!sLogin.isEmpty()) { d->ui.edt_login->setText(sLogin); } const QString sDomain = dataMap[NM_PPTP_KEY_DOMAIN]; if (!sDomain.isEmpty()) { d->ui.edt_ntDomain->setText(sDomain); } // Options below is belongs to "Advanced" dialog // Authentication options const QString yesString = QLatin1String("yes"); bool refuse_pap = (dataMap[NM_PPTP_KEY_REFUSE_PAP] == yesString); bool refuse_chap = (dataMap[NM_PPTP_KEY_REFUSE_CHAP] == yesString); bool refuse_mschap = (dataMap[NM_PPTP_KEY_REFUSE_MSCHAP] == yesString); bool refuse_mschapv2 = (dataMap[NM_PPTP_KEY_REFUSE_MSCHAPV2] == yesString); bool refuse_eap = (dataMap[NM_PPTP_KEY_REFUSE_EAP] == yesString); QListWidgetItem * item = nullptr; item = d->advUi.listWidget->item(0); // PAP item->setCheckState(refuse_pap ? Qt::Unchecked : Qt::Checked); item = d->advUi.listWidget->item(1); // CHAP item->setCheckState(refuse_chap ? Qt::Unchecked : Qt::Checked); item = d->advUi.listWidget->item(2); // MSCHAP item->setCheckState(refuse_mschap ? Qt::Unchecked : Qt::Checked); item = d->advUi.listWidget->item(3); // MSCHAPv2 item->setCheckState(refuse_mschapv2 ? Qt::Unchecked : Qt::Checked); item = d->advUi.listWidget->item(4); // EAP item->setCheckState(refuse_eap ? Qt::Unchecked : Qt::Checked); // Cryptography and compression const bool mppe = (dataMap[NM_PPTP_KEY_REQUIRE_MPPE] == yesString); const bool mppe40 = (dataMap[NM_PPTP_KEY_REQUIRE_MPPE_40] == yesString); const bool mppe128 = (dataMap[NM_PPTP_KEY_REQUIRE_MPPE_128] == yesString); const bool mppe_stateful = (dataMap[NM_PPTP_KEY_MPPE_STATEFUL] == yesString); if (mppe || mppe40 || mppe128) { // If MPPE is use d->advUi.gb_MPPE->setChecked(mppe || mppe40 || mppe128); if (mppe128) { d->advUi.cb_MPPECrypto->setCurrentIndex(1); // 128 bit } else if (mppe40) { d->advUi.cb_MPPECrypto->setCurrentIndex(2); // 40 bit } else { d->advUi.cb_MPPECrypto->setCurrentIndex(0); // Any } d->advUi.cb_statefulEncryption->setChecked(mppe_stateful); } const bool nobsd = (dataMap[NM_PPTP_KEY_NOBSDCOMP] == yesString); d->advUi.cb_BSD->setChecked(!nobsd); const bool nodeflate = (dataMap[NM_PPTP_KEY_NODEFLATE] == yesString); d->advUi.cb_deflate->setChecked(!nodeflate); const bool novjcomp = (dataMap[NM_PPTP_KEY_NO_VJ_COMP] == yesString); d->advUi.cb_TCPheaders->setChecked(!novjcomp); // Echo const int lcp_echo_interval = QString(dataMap[NM_PPTP_KEY_LCP_ECHO_INTERVAL]).toInt(); d->advUi.cb_sendEcho->setChecked(lcp_echo_interval > 0); // secrets const NetworkManager::Setting::SecretFlags type = (NetworkManager::Setting::SecretFlags)dataMap[NM_PPTP_KEY_PASSWORD"-flags"].toInt(); fillOnePasswordCombo(d->ui.edt_password, type); loadSecrets(setting); } void PptpSettingWidget::loadSecrets(const NetworkManager::Setting::Ptr &setting) { Q_D(PptpSettingWidget); NetworkManager::VpnSetting::Ptr vpnSetting = setting.staticCast(); if (vpnSetting) { const NMStringMap secrets = vpnSetting->secrets(); const QString keyPassword = secrets.value(QLatin1String(NM_PPTP_KEY_PASSWORD)); if (!keyPassword.isEmpty()) { d->ui.edt_password->setText(keyPassword); } } } QVariantMap PptpSettingWidget::setting() const { Q_D(const PptpSettingWidget); NetworkManager::VpnSetting setting; setting.setServiceType(QLatin1String(NM_DBUS_SERVICE_PPTP)); // save the main dialog's data in the setting // if the advanced dialog is dirty, save its data in the vpn setting too // NMStringMap data; NMStringMap secretData; data.insert(NM_PPTP_KEY_GATEWAY, d->ui.edt_gateway->text()); data.insert(NM_PPTP_KEY_USER, d->ui.edt_login->text()); if (!d->ui.edt_password->text().isEmpty()) { secretData.insert(QLatin1String(NM_PPTP_KEY_PASSWORD), d->ui.edt_password->text()); } handleOnePasswordType(d->ui.edt_password, NM_PPTP_KEY_PASSWORD"-flags", data); if (!d->ui.edt_ntDomain->text().isEmpty()) { data.insert(NM_PPTP_KEY_DOMAIN, d->ui.edt_ntDomain->text()); } // Advanced dialog settings // Authentication options QListWidgetItem * item = nullptr; item = d->advUi.listWidget->item(0); // PAP const QString yesString = QLatin1String("yes"); if (item->checkState() == Qt::Unchecked) { data.insert(NM_PPTP_KEY_REFUSE_PAP, yesString); } item = d->advUi.listWidget->item(1); // CHAP if (item->checkState() == Qt::Unchecked) { data.insert(NM_PPTP_KEY_REFUSE_CHAP, yesString); } item = d->advUi.listWidget->item(2); // MSCHAP if (item->checkState() == Qt::Unchecked) { data.insert(NM_PPTP_KEY_REFUSE_MSCHAP, yesString); } item = d->advUi.listWidget->item(3); // MSCHAPv2 if (item->checkState() == Qt::Unchecked) { data.insert(NM_PPTP_KEY_REFUSE_MSCHAPV2, yesString); } item = d->advUi.listWidget->item(4); // EAP if (item->checkState() == Qt::Unchecked) { data.insert(NM_PPTP_KEY_REFUSE_EAP, yesString); } // Cryptography and compression if (d->advUi.gb_MPPE->isChecked()) { int index = d->advUi.cb_MPPECrypto->currentIndex(); switch (index) { case 0: data.insert(NM_PPTP_KEY_REQUIRE_MPPE, yesString); break; case 1: data.insert(NM_PPTP_KEY_REQUIRE_MPPE_128, yesString); break; case 2: data.insert(NM_PPTP_KEY_REQUIRE_MPPE_40, yesString); break; } if (d->advUi.cb_statefulEncryption->isChecked()) { data.insert(NM_PPTP_KEY_MPPE_STATEFUL, yesString); } } if (!d->advUi.cb_BSD->isChecked()) { data.insert(NM_PPTP_KEY_NOBSDCOMP, yesString); } if (!d->advUi.cb_deflate->isChecked()) { data.insert(NM_PPTP_KEY_NODEFLATE, yesString); } if (!d->advUi.cb_TCPheaders->isChecked()) { data.insert(NM_PPTP_KEY_NO_VJ_COMP, yesString); } // Echo if (d->advUi.cb_sendEcho->isChecked()) { data.insert(NM_PPTP_KEY_LCP_ECHO_FAILURE, "5"); data.insert(NM_PPTP_KEY_LCP_ECHO_INTERVAL, "30"); } // save it all setting.setData(data); setting.setSecrets(secretData); return setting.toMap(); } void PptpSettingWidget::fillOnePasswordCombo(PasswordField *passwordField, NetworkManager::Setting::SecretFlags type) { if (type.testFlag(NetworkManager::Setting::None)) { passwordField->setPasswordOption(PasswordField::StoreForAllUsers); } else if (type.testFlag(NetworkManager::Setting::AgentOwned)) { passwordField->setPasswordOption(PasswordField::StoreForUser); } else if (type.testFlag(NetworkManager::Setting::NotSaved)) { passwordField->setPasswordOption(PasswordField::AlwaysAsk); } else { passwordField->setPasswordOption(PasswordField::PasswordField::NotRequired); } } void PptpSettingWidget::handleOnePasswordType(const PasswordField *passwordField, const QString &key, NMStringMap &data) const { const PasswordField::PasswordOption option = passwordField->passwordOption(); switch (option) { case PasswordField::StoreForAllUsers: data.insert(key, QString::number(NetworkManager::Setting::None)); break; case PasswordField::StoreForUser: data.insert(key, QString::number(NetworkManager::Setting::AgentOwned)); break; case PasswordField::AlwaysAsk: data.insert(key, QString::number(NetworkManager::Setting::NotSaved)); break; case PasswordField::NotRequired: data.insert(key, QString::number(NetworkManager::Setting::NotRequired)); break; } } bool PptpSettingWidget::isValid() const { Q_D(const PptpSettingWidget); return !d->ui.edt_gateway->text().isEmpty(); } diff --git a/vpn/ssh/sshauth.cpp b/vpn/ssh/sshauth.cpp index f27fe7e0..c6c0e6e0 100644 --- a/vpn/ssh/sshauth.cpp +++ b/vpn/ssh/sshauth.cpp @@ -1,63 +1,65 @@ /* Copyright 2015 Jan Grulich This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License or (at your option) version 3 or any later version accepted by the membership of KDE e.V. (or its successor approved by the membership of KDE e.V.), which shall act as a proxy defined in Section 14 of version 3 of the license. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see . */ #include "sshauth.h" #include "ui_sshauth.h" #include "nm-ssh-service.h" +#include + class SshAuthWidgetPrivate { public: NetworkManager::VpnSetting::Ptr setting; Ui_SshAuth ui; }; SshAuthWidget::SshAuthWidget(const NetworkManager::VpnSetting::Ptr &setting, QWidget *parent) : SettingWidget(setting, parent) , d_ptr(new SshAuthWidgetPrivate) { Q_D(SshAuthWidget); d->setting = setting; d->ui.setupUi(this); KAcceleratorManager::manage(this); } SshAuthWidget::~SshAuthWidget() { delete d_ptr; } QVariantMap SshAuthWidget::setting() const { Q_D(const SshAuthWidget); NMStringMap secrets; QVariantMap secretData; if (!d->ui.le_password->text().isEmpty()) { secrets.insert(QLatin1String(NM_SSH_KEY_PASSWORD), d->ui.le_password->text()); } secretData.insert("secrets", QVariant::fromValue(secrets)); return secretData; } diff --git a/vpn/ssh/sshwidget.cpp b/vpn/ssh/sshwidget.cpp index 9399a038..28c95615 100644 --- a/vpn/ssh/sshwidget.cpp +++ b/vpn/ssh/sshwidget.cpp @@ -1,394 +1,396 @@ /* Copyright 2015 Jan Grulich This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License or (at your option) version 3 or any later version accepted by the membership of KDE e.V. (or its successor approved by the membership of KDE e.V.), which shall act as a proxy defined in Section 14 of version 3 of the license. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see . */ #include "sshwidget.h" #include "ui_sshwidget.h" #include "ui_sshadvanced.h" #include "simpleipv4addressvalidator.h" #include "simpleipv6addressvalidator.h" #include #include #include +#include + #include "nm-ssh-service.h" class SshSettingWidgetPrivate { public: Ui_SshWidget ui; Ui_SshAdvanced advUi; NetworkManager::VpnSetting::Ptr setting; QDialog *advancedDlg; QWidget *advancedWid; }; SshSettingWidget::SshSettingWidget(const NetworkManager::VpnSetting::Ptr &setting, QWidget *parent) : SettingWidget(setting, parent) , d_ptr(new SshSettingWidgetPrivate) { Q_D(SshSettingWidget); d->ui.setupUi(this); d->setting = setting; d->ui.le_password->setPasswordOptionsEnabled(true); connect(d->ui.cmb_authType, QOverload::of(&QComboBox::currentIndexChanged), this, &SshSettingWidget::authTypeChanged); connect(d->ui.btn_advancedOption, &QPushButton::clicked, this, &SshSettingWidget::doAdvancedDialog); d->advancedDlg = new QDialog(this); d->advancedDlg->setModal(true); d->advancedWid = new QWidget(this); d->advUi.setupUi(d->advancedWid); QVBoxLayout *layout = new QVBoxLayout(d->advancedDlg); layout->addWidget(d->advancedWid); d->advancedDlg->setLayout(layout); QDialogButtonBox *buttons = new QDialogButtonBox(QDialogButtonBox::Ok|QDialogButtonBox::Cancel, d->advancedDlg); connect(buttons, &QDialogButtonBox::accepted, d->advancedDlg, &QDialog::accept); connect(buttons, &QDialogButtonBox::rejected, d->advancedDlg, &QDialog::reject); layout->addWidget(buttons); // Connect for setting check watchChangedSetting(); // Connect for validity check connect(d->ui.le_gateway, &QLineEdit::textChanged, this, &SshSettingWidget::slotWidgetChanged); connect(d->ui.le_localIp, &QLineEdit::textChanged, this, &SshSettingWidget::slotWidgetChanged); connect(d->ui.le_netmask, &QLineEdit::textChanged, this, &SshSettingWidget::slotWidgetChanged); connect(d->ui.le_remoteIp, &QLineEdit::textChanged, this, &SshSettingWidget::slotWidgetChanged); SimpleIpV4AddressValidator *ipv4Validator = new SimpleIpV4AddressValidator(SimpleIpV4AddressValidator::Base, this); d->ui.le_localIp->setValidator(ipv4Validator); d->ui.le_remoteIp->setValidator(ipv4Validator); d->ui.le_netmask->setValidator(ipv4Validator); SimpleIpV6AddressValidator *ipv6Validator = new SimpleIpV6AddressValidator(SimpleIpV6AddressValidator::Base, this); d->ui.le_localIpv6->setValidator(ipv6Validator); d->ui.le_remoteIpv6->setValidator(ipv6Validator); d->ui.passwordWidget->setVisible(false); d->advUi.sb_useCustomGatewayPort->setValue(NM_SSH_DEFAULT_PORT); d->advUi.sb_useCustomTunnelMtu->setValue(NM_SSH_DEFAULT_MTU); d->advUi.le_extraSshOptions->setText(QLatin1String(NM_SSH_DEFAULT_EXTRA_OPTS)); d->advUi.sb_remoteDeviceNumber->setValue(NM_SSH_DEFAULT_REMOTE_DEV); d->advUi.le_remoteUsername->setText(QLatin1String(NM_SSH_DEFAULT_REMOTE_USERNAME)); KAcceleratorManager::manage(this); if (d->setting && !d->setting->isNull()) { loadConfig(d->setting); } } SshSettingWidget::~SshSettingWidget() { delete d_ptr; } void SshSettingWidget::loadConfig(const NetworkManager::Setting::Ptr &setting) { Q_D(SshSettingWidget); Q_UNUSED(setting) const NMStringMap dataMap = d->setting->data(); // General const QString gateway = dataMap[QLatin1String(NM_SSH_KEY_REMOTE)]; if (!gateway.isEmpty()) { d->ui.le_gateway->setText(gateway); } // Network settings const QString remoteIp = dataMap[QLatin1String(NM_SSH_KEY_REMOTE_IP)]; if (!remoteIp.isEmpty()) { d->ui.le_remoteIp->setText(remoteIp); } const QString localIp = dataMap[QLatin1String(NM_SSH_KEY_LOCAL_IP)]; if (!localIp.isEmpty()) { d->ui.le_localIp->setText(localIp); } const QString netmask = dataMap[QLatin1String(NM_SSH_KEY_NETMASK)]; if (!netmask.isEmpty()) { d->ui.le_netmask->setText(netmask); } // IPv6 network settings const bool ipv6Enabled = dataMap[QLatin1String(NM_SSH_KEY_IP_6)] == QLatin1String("yes"); d->ui.chk_useIpv6->setChecked(ipv6Enabled); if (ipv6Enabled) { const QString remoteIpv6 = dataMap[QLatin1String(NM_SSH_KEY_REMOTE_IP_6)]; if (!remoteIpv6.isEmpty()) { d->ui.le_remoteIpv6->setText(remoteIpv6); } const QString localIpv6 = dataMap[QLatin1String(NM_SSH_KEY_LOCAL_IP_6)]; if (!localIpv6.isEmpty()) { d->ui.le_localIpv6->setText(localIpv6); } const QString netmaskIpv6 = dataMap[QLatin1String(NM_SSH_KEY_NETMASK_6)]; if (!netmaskIpv6.isEmpty()) { d->ui.le_netmaskIpv6->setText(netmaskIpv6); } } // Authentication const QString sshAuthType = dataMap[QLatin1String(NM_SSH_KEY_AUTH_TYPE)]; if (sshAuthType == QLatin1String(NM_SSH_AUTH_TYPE_SSH_AGENT)) { d->ui.cmb_authType->setCurrentIndex(0); } else if (sshAuthType == QLatin1String(NM_SSH_AUTH_TYPE_PASSWORD)) { d->ui.cmb_authType->setCurrentIndex(1); const NetworkManager::Setting::SecretFlags type = (NetworkManager::Setting::SecretFlags)dataMap[NM_SSH_KEY_PASSWORD"-flags"].toInt(); fillOnePasswordCombo(d->ui.le_password, type); } else if (sshAuthType == QLatin1String(NM_SSH_AUTH_TYPE_KEY)) { d->ui.cmb_authType->setCurrentIndex(2); d->ui.kurl_sshKeyFile->setUrl(QUrl::fromLocalFile(dataMap[QLatin1String(NM_SSH_KEY_KEY_FILE)])); } // Options below is belongs to "Advanced" dialog const QString customGatewayPort = dataMap[QLatin1String(NM_SSH_KEY_PORT)]; if (!customGatewayPort.isEmpty()) { d->advUi.chk_useCustomGatewayPort->setChecked(true); d->advUi.sb_useCustomGatewayPort->setValue(customGatewayPort.toInt()); } const QString customMtu = dataMap[QLatin1String(NM_SSH_KEY_TUNNEL_MTU)]; if (!customMtu.isEmpty()) { d->advUi.chk_useCustomTunnelMtu->setChecked(true); d->advUi.sb_useCustomTunnelMtu->setValue(customMtu.toInt()); } const QString extraSshOptions = dataMap[QLatin1String(NM_SSH_KEY_EXTRA_OPTS)]; if (!extraSshOptions.isEmpty()) { d->advUi.chk_extraSshOptions->setChecked(true); d->advUi.le_extraSshOptions->setText(extraSshOptions); } const QString remoteDeviceNumber = dataMap[QLatin1String(NM_SSH_KEY_REMOTE_DEV)]; if (!remoteDeviceNumber.isEmpty()) { d->advUi.chk_remoteDeviceNumber->setChecked(true); d->advUi.sb_remoteDeviceNumber->setValue(remoteDeviceNumber.toInt()); } const QString useTapDevice = dataMap[QLatin1String(NM_SSH_KEY_TAP_DEV)]; if (!useTapDevice.isEmpty()) { if (useTapDevice == QLatin1String("yes")) { d->advUi.chk_useTapDevice->setChecked(true); } } const QString remoteUsername = dataMap[QLatin1String(NM_SSH_KEY_REMOTE_USERNAME)]; if (!remoteUsername.isEmpty()) { d->advUi.chk_remoteUsername->setChecked(true); d->advUi.le_remoteUsername->setText(remoteUsername); } const QString doNotReplaceDefaultRoute = dataMap[QLatin1String(NM_SSH_KEY_NO_DEFAULT_ROUTE)]; if (!doNotReplaceDefaultRoute.isEmpty()) { if (doNotReplaceDefaultRoute == QLatin1String("yes")) { d->advUi.chk_doNotReplaceDefaultRoute->setChecked(true); } } loadSecrets(setting); } void SshSettingWidget::loadSecrets(const NetworkManager::Setting::Ptr &setting) { Q_D(SshSettingWidget); NetworkManager::VpnSetting::Ptr vpnSetting = setting.staticCast(); if (vpnSetting) { const NMStringMap secrets = vpnSetting->secrets(); const QString keyPassword = secrets.value(NM_SSH_KEY_PASSWORD); if (!keyPassword.isEmpty()) { d->ui.le_password->setText(keyPassword); } } } QVariantMap SshSettingWidget::setting() const { Q_D(const SshSettingWidget); NetworkManager::VpnSetting setting; setting.setServiceType(QLatin1String(NM_DBUS_SERVICE_SSH)); NMStringMap data; NMStringMap secretData; data.insert(QLatin1String(NM_SSH_KEY_REMOTE), d->ui.le_gateway->text()); if (!d->ui.le_remoteIp->text().isEmpty()) { data.insert(QLatin1String(NM_SSH_KEY_REMOTE_IP), d->ui.le_remoteIp->text()); } if (!d->ui.le_localIp->text().isEmpty()) { data.insert(QLatin1String(NM_SSH_KEY_LOCAL_IP), d->ui.le_localIp->text()); } if (!d->ui.le_netmask->text().isEmpty()) { data.insert(QLatin1String(NM_SSH_KEY_NETMASK), d->ui.le_netmask->text()); } if (d->ui.chk_useIpv6->isChecked()) { data.insert(QLatin1String(NM_SSH_KEY_IP_6), QLatin1String("yes")); if (!d->ui.le_remoteIpv6->text().isEmpty()) { data.insert(QLatin1String(NM_SSH_KEY_REMOTE_IP_6), d->ui.le_remoteIpv6->text()); } if (!d->ui.le_localIpv6->text().isEmpty()) { data.insert(QLatin1String(NM_SSH_KEY_LOCAL_IP_6), d->ui.le_localIpv6->text()); } if (!d->ui.le_netmaskIpv6->text().isEmpty()) { data.insert(QLatin1String(NM_SSH_KEY_NETMASK_6), d->ui.le_netmaskIpv6->text()); } } switch (d->ui.cmb_authType->currentIndex()) { case 0: data.insert(QLatin1String(NM_SSH_KEY_AUTH_TYPE), QLatin1String(NM_SSH_AUTH_TYPE_SSH_AGENT)); break; case 1: data.insert(QLatin1String(NM_SSH_KEY_AUTH_TYPE), QLatin1String(NM_SSH_AUTH_TYPE_PASSWORD)); if (!d->ui.le_password->text().isEmpty()) { secretData.insert(QLatin1String(NM_SSH_KEY_PASSWORD), d->ui.le_password->text()); } handleOnePasswordType(d->ui.le_password, NM_SSH_KEY_PASSWORD"-flags", data); break; case 2: data.insert(QLatin1String(NM_SSH_KEY_AUTH_TYPE), QLatin1String(NM_SSH_AUTH_TYPE_KEY)); if (!d->ui.kurl_sshKeyFile->url().isEmpty()) { data.insert(QLatin1String(NM_SSH_KEY_KEY_FILE), d->ui.kurl_sshKeyFile->url().toLocalFile()); } break; } if (d->advUi.chk_useCustomGatewayPort->isChecked()) { data.insert(QLatin1String(NM_SSH_KEY_PORT), QString::number(d->advUi.sb_useCustomGatewayPort->value())); } if (d->advUi.chk_useCustomTunnelMtu->isChecked()) { data.insert(QLatin1String(NM_SSH_KEY_TUNNEL_MTU), QString::number(d->advUi.sb_useCustomTunnelMtu->value())); } if (d->advUi.chk_extraSshOptions->isChecked()) { data.insert(QLatin1String(NM_SSH_KEY_EXTRA_OPTS), d->advUi.le_extraSshOptions->text()); } if (d->advUi.chk_remoteDeviceNumber->isChecked()) { data.insert(QLatin1String(NM_SSH_KEY_REMOTE_DEV), QString::number(d->advUi.sb_remoteDeviceNumber->value())); } if (d->advUi.chk_useTapDevice->isChecked()) { data.insert(QLatin1String(NM_SSH_KEY_TAP_DEV), QLatin1String("yes")); } if (d->advUi.chk_remoteUsername->isChecked()) { data.insert(QLatin1String(NM_SSH_KEY_REMOTE_USERNAME), d->advUi.le_remoteUsername->text()); } if (d->advUi.chk_doNotReplaceDefaultRoute->isChecked()) { data.insert(QLatin1String(NM_SSH_KEY_NO_DEFAULT_ROUTE), QLatin1String("yes")); } // save it all setting.setData(data); setting.setSecrets(secretData); return setting.toMap(); } void SshSettingWidget::authTypeChanged(int index) { Q_D(SshSettingWidget); if (index == 0) { d->ui.stackedWidget->setCurrentIndex(0); d->ui.passwordWidget->setVisible(false); } else if (index == 1) { d->ui.stackedWidget->setCurrentIndex(0); d->ui.passwordWidget->setVisible(true); } else { d->ui.stackedWidget->setCurrentIndex(1); } } void SshSettingWidget::doAdvancedDialog() { Q_D(SshSettingWidget); d->advancedDlg->show(); } void SshSettingWidget::passwordTypeChanged(int index) { Q_D(SshSettingWidget); d->ui.le_password->setEnabled(index == SettingWidget::EnumPasswordStorageType::Store); } void SshSettingWidget::fillOnePasswordCombo(PasswordField *passwordField, NetworkManager::Setting::SecretFlags type) { if (type.testFlag(NetworkManager::Setting::None)) { passwordField->setPasswordOption(PasswordField::StoreForAllUsers); } else if (type.testFlag(NetworkManager::Setting::AgentOwned)) { passwordField->setPasswordOption(PasswordField::StoreForUser); } else if (type.testFlag(NetworkManager::Setting::NotSaved)) { passwordField->setPasswordOption(PasswordField::AlwaysAsk); } else { passwordField->setPasswordOption(PasswordField::PasswordField::NotRequired); } } void SshSettingWidget::handleOnePasswordType(const PasswordField *passwordField, const QString &key, NMStringMap &data) const { const PasswordField::PasswordOption option = passwordField->passwordOption(); switch (option) { case PasswordField::StoreForAllUsers: data.insert(key, QString::number(NetworkManager::Setting::None)); break; case PasswordField::StoreForUser: data.insert(key, QString::number(NetworkManager::Setting::AgentOwned)); break; case PasswordField::AlwaysAsk: data.insert(key, QString::number(NetworkManager::Setting::NotSaved)); break; case PasswordField::NotRequired: data.insert(key, QString::number(NetworkManager::Setting::NotRequired)); break; } } bool SshSettingWidget::isValid() const { Q_D(const SshSettingWidget); return !d->ui.le_gateway->text().isEmpty() && !d->ui.le_localIp->text().isEmpty() && !d->ui.le_remoteIp->text().isEmpty() && !d->ui.le_netmask->text().isEmpty(); } diff --git a/vpn/sstp/sstpauth.cpp b/vpn/sstp/sstpauth.cpp index a5938547..e54690fb 100644 --- a/vpn/sstp/sstpauth.cpp +++ b/vpn/sstp/sstpauth.cpp @@ -1,63 +1,65 @@ /* Copyright 2015 Jan Grulich This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License or (at your option) version 3 or any later version accepted by the membership of KDE e.V. (or its successor approved by the membership of KDE e.V.), which shall act as a proxy defined in Section 14 of version 3 of the license. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see . */ #include "sstpauth.h" #include "ui_sstpauth.h" #include "nm-sstp-service.h" +#include + class SstpAuthWidgetPrivate { public: NetworkManager::VpnSetting::Ptr setting; Ui_SstpAuth ui; }; SstpAuthWidget::SstpAuthWidget(const NetworkManager::VpnSetting::Ptr &setting, QWidget *parent) : SettingWidget(setting, parent) , d_ptr(new SstpAuthWidgetPrivate) { Q_D(SstpAuthWidget); d->setting = setting; d->ui.setupUi(this); KAcceleratorManager::manage(this); } SstpAuthWidget::~SstpAuthWidget() { delete d_ptr; } QVariantMap SstpAuthWidget::setting() const { Q_D(const SstpAuthWidget); NMStringMap secrets; QVariantMap secretData; if (!d->ui.le_password->text().isEmpty()) { secrets.insert(QLatin1String(NM_SSTP_KEY_PASSWORD), d->ui.le_password->text()); } secretData.insert("secrets", QVariant::fromValue(secrets)); return secretData; } diff --git a/vpn/sstp/sstpwidget.cpp b/vpn/sstp/sstpwidget.cpp index 208dca6d..3e14cd7a 100644 --- a/vpn/sstp/sstpwidget.cpp +++ b/vpn/sstp/sstpwidget.cpp @@ -1,388 +1,390 @@ /* Copyright 2015 Jan Grulich This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License or (at your option) version 3 or any later version accepted by the membership of KDE e.V. (or its successor approved by the membership of KDE e.V.), which shall act as a proxy defined in Section 14 of version 3 of the license. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see . */ #include "sstpwidget.h" #include "ui_sstpwidget.h" #include "ui_sstpadvanced.h" #include #include #include +#include + #include "nm-sstp-service.h" class SstpSettingWidgetPrivate { public: Ui_SstpWidget ui; Ui_SstpAdvanced advUi; NetworkManager::VpnSetting::Ptr setting; QDialog *advancedDlg; QWidget *advancedWid; }; SstpSettingWidget::SstpSettingWidget(const NetworkManager::VpnSetting::Ptr &setting, QWidget *parent) : SettingWidget(setting, parent) , d_ptr(new SstpSettingWidgetPrivate) { Q_D(SstpSettingWidget); d->ui.setupUi(this); d->setting = setting; d->ui.le_password->setPasswordOptionsEnabled(true); connect(d->ui.btn_advancedOption, &QPushButton::clicked, this, &SstpSettingWidget::doAdvancedDialog); d->advancedDlg = new QDialog(this); d->advancedDlg->setModal(true); d->advancedWid = new QWidget(this); d->advUi.setupUi(d->advancedWid); QVBoxLayout *layout = new QVBoxLayout(d->advancedDlg); layout->addWidget(d->advancedWid); d->advancedDlg->setLayout(layout); QDialogButtonBox *buttons = new QDialogButtonBox(QDialogButtonBox::Ok|QDialogButtonBox::Cancel, d->advancedDlg); connect(buttons, &QDialogButtonBox::accepted, d->advancedDlg, &QDialog::accept); connect(buttons, &QDialogButtonBox::rejected, d->advancedDlg, &QDialog::reject); layout->addWidget(buttons); // Connect for setting check watchChangedSetting(); // Connect for validity check connect(d->ui.le_gateway, &QLineEdit::textChanged, this, &SstpSettingWidget::slotWidgetChanged); connect(d->ui.le_username, &QLineEdit::textChanged, this, &SstpSettingWidget::slotWidgetChanged); connect(d->ui.le_password, &PasswordField::textChanged, this, &SstpSettingWidget::slotWidgetChanged); KAcceleratorManager::manage(this); if (d->setting && !d->setting->isNull()) { loadConfig(d->setting); } } SstpSettingWidget::~SstpSettingWidget() { delete d_ptr; } void SstpSettingWidget::loadConfig(const NetworkManager::Setting::Ptr &setting) { Q_D(SstpSettingWidget); Q_UNUSED(setting) const QString yesString = QLatin1String("yes"); const NMStringMap dataMap = d->setting->data(); // General const QString gateway = dataMap[QLatin1String(NM_SSTP_KEY_GATEWAY)]; if (!gateway.isEmpty()) { d->ui.le_gateway->setText(gateway); } // Optional setting const QString username = dataMap[QLatin1String(NM_SSTP_KEY_USER)]; if (!username.isEmpty()) { d->ui.le_username->setText(username); } // Authentication const NetworkManager::Setting::SecretFlags type = (NetworkManager::Setting::SecretFlags)dataMap[NM_SSTP_KEY_PASSWORD_FLAGS].toInt(); fillOnePasswordCombo(d->ui.le_password, type); const QString ntDomain = dataMap[QLatin1String(NM_SSTP_KEY_DOMAIN)]; if (!ntDomain.isEmpty()) { d->ui.le_ntDomain->setText(ntDomain); } const QString caCert = dataMap[QLatin1String(NM_SSTP_KEY_CA_CERT)]; if (!caCert.isEmpty()) { d->ui.kurl_caCert->setUrl(QUrl::fromLocalFile(caCert)); } const bool ignoreCertWarnings = (dataMap[QLatin1String(NM_SSTP_KEY_IGN_CERT_WARN)] == yesString); d->ui.chk_ignoreCertWarnings->setChecked(ignoreCertWarnings); // Advanced options - Point-to-Point bool refuse_pap = (dataMap[QLatin1String(NM_SSTP_KEY_REFUSE_PAP)] == yesString); bool refuse_chap = (dataMap[QLatin1String(NM_SSTP_KEY_REFUSE_CHAP)] == yesString); bool refuse_mschap = (dataMap[QLatin1String(NM_SSTP_KEY_REFUSE_MSCHAP)] == yesString); bool refuse_mschapv2 = (dataMap[QLatin1String(NM_SSTP_KEY_REFUSE_MSCHAPV2)] == yesString); bool refuse_eap = (dataMap[QLatin1String(NM_SSTP_KEY_REFUSE_EAP)] == yesString); QListWidgetItem *item = nullptr; item = d->advUi.listWidget->item(0); // PAP item->setCheckState(refuse_pap ? Qt::Unchecked : Qt::Checked); item = d->advUi.listWidget->item(1); // CHAP item->setCheckState(refuse_chap ? Qt::Unchecked : Qt::Checked); item = d->advUi.listWidget->item(2); // MSCHAP item->setCheckState(refuse_mschap ? Qt::Unchecked : Qt::Checked); item = d->advUi.listWidget->item(3); // MSCHAPv2 item->setCheckState(refuse_mschapv2 ? Qt::Unchecked : Qt::Checked); item = d->advUi.listWidget->item(4); // EAP item->setCheckState(refuse_eap ? Qt::Unchecked : Qt::Checked); // Cryptography and compression const bool mppe = (dataMap[QLatin1String(NM_SSTP_KEY_REQUIRE_MPPE)] == yesString); const bool mppe40 = (dataMap[QLatin1String(NM_SSTP_KEY_REQUIRE_MPPE_40)] == yesString); const bool mppe128 = (dataMap[QLatin1String(NM_SSTP_KEY_REQUIRE_MPPE_128)] == yesString); const bool mppe_stateful = (dataMap[QLatin1String(NM_SSTP_KEY_MPPE_STATEFUL)] == yesString); if (mppe || mppe40 || mppe128) { // If MPPE is use d->advUi.gb_MPPE->setChecked(mppe || mppe40 || mppe128); if (mppe128) { d->advUi.cb_MPPECrypto->setCurrentIndex(1); // 128 bit } else if (mppe40) { d->advUi.cb_MPPECrypto->setCurrentIndex(2); // 40 bit } else { d->advUi.cb_MPPECrypto->setCurrentIndex(0); // Any } d->advUi.cb_statefulEncryption->setChecked(mppe_stateful); } const bool nobsd = (dataMap[QLatin1String(NM_SSTP_KEY_NOBSDCOMP)] == yesString); d->advUi.cb_BSD->setChecked(!nobsd); const bool nodeflate = (dataMap[QLatin1String(NM_SSTP_KEY_NODEFLATE)] == yesString); d->advUi.cb_deflate->setChecked(!nodeflate); const bool novjcomp = (dataMap[QLatin1String(NM_SSTP_KEY_NO_VJ_COMP)] == yesString); d->advUi.cb_TCPheaders->setChecked(!novjcomp); // Echo const int lcp_echo_interval = QString(dataMap[QLatin1String(NM_SSTP_KEY_LCP_ECHO_INTERVAL)]).toInt(); d->advUi.cb_sendEcho->setChecked(lcp_echo_interval > 0); if (dataMap.contains(QLatin1String(NM_SSTP_KEY_UNIT_NUM))) { d->advUi.chk_useCustomUnitNumber->setChecked(true); d->advUi.sb_customUnitNumber->setValue(dataMap[QLatin1String(NM_SSTP_KEY_UNIT_NUM)].toInt()); } // Advanced options - Proxy const QString address = dataMap[QLatin1String(NM_SSTP_KEY_PROXY_SERVER)]; if (!address.isEmpty()) { d->advUi.le_address->setText(address); } const int port = dataMap[QLatin1String(NM_SSTP_KEY_PROXY_PORT)].toInt(); if (port >= 0) { d->advUi.sb_port->setValue(port); } const QString proxyUsername = dataMap[QLatin1String(NM_SSTP_KEY_PROXY_USER)]; if (!proxyUsername.isEmpty()) { d->advUi.le_username->setText(proxyUsername); } const QString proxyPassword = dataMap[QLatin1String(NM_SSTP_KEY_PROXY_PASSWORD)]; if (!proxyPassword.isEmpty()) { d->advUi.le_password->setText(proxyPassword); } loadSecrets(setting); } void SstpSettingWidget::loadSecrets(const NetworkManager::Setting::Ptr &setting) { Q_D(SstpSettingWidget); NetworkManager::VpnSetting::Ptr vpnSetting = setting.staticCast(); if (vpnSetting) { const NMStringMap secrets = vpnSetting->secrets(); const QString keyPassword = secrets.value(NM_SSTP_KEY_PASSWORD); if (!keyPassword.isEmpty()) { d->ui.le_password->setText(keyPassword); } } } QVariantMap SstpSettingWidget::setting() const { Q_D(const SstpSettingWidget); NetworkManager::VpnSetting setting; setting.setServiceType(QLatin1String(NM_DBUS_SERVICE_SSTP)); const QString yesString = QLatin1String("yes"); NMStringMap data; NMStringMap secretData; data.insert(QLatin1String(NM_SSTP_KEY_GATEWAY), d->ui.le_gateway->text()); if (!d->ui.le_username->text().isEmpty()) { data.insert(QLatin1String(NM_SSTP_KEY_USER), d->ui.le_username->text()); } if (!d->ui.le_password->text().isEmpty()) { secretData.insert(QLatin1String(NM_SSTP_KEY_PASSWORD), d->ui.le_password->text()); } handleOnePasswordType(d->ui.le_password, NM_SSTP_KEY_PASSWORD_FLAGS, data); if (!d->ui.le_ntDomain->text().isEmpty()) { data.insert(QLatin1String(NM_SSTP_KEY_DOMAIN), d->ui.le_ntDomain->text()); } if (!d->ui.kurl_caCert->url().isEmpty()) { data.insert(QLatin1String(NM_SSTP_KEY_CA_CERT), d->ui.kurl_caCert->url().toLocalFile()); } if (d->ui.chk_ignoreCertWarnings->isChecked()) { data.insert(QLatin1String(NM_SSTP_KEY_IGN_CERT_WARN), yesString); } // Advanced configuration QListWidgetItem *item = nullptr; item = d->advUi.listWidget->item(0); // PAP if (item->checkState() == Qt::Unchecked) { data.insert(QLatin1String(NM_SSTP_KEY_REFUSE_PAP), yesString); } item = d->advUi.listWidget->item(1); // CHAP if (item->checkState() == Qt::Unchecked) { data.insert(QLatin1String(NM_SSTP_KEY_REFUSE_CHAP), yesString); } item = d->advUi.listWidget->item(2); // MSCHAP if (item->checkState() == Qt::Unchecked) { data.insert(QLatin1String(NM_SSTP_KEY_REFUSE_MSCHAP), yesString); } item = d->advUi.listWidget->item(3); // MSCHAPv2 if (item->checkState() == Qt::Unchecked) { data.insert(QLatin1String(NM_SSTP_KEY_REFUSE_MSCHAPV2), yesString); } item = d->advUi.listWidget->item(4); // EAP if (item->checkState() == Qt::Unchecked) { data.insert(QLatin1String(NM_SSTP_KEY_REFUSE_EAP), yesString); } // Cryptography and compression if (d->advUi.gb_MPPE->isChecked()) { int index = d->advUi.cb_MPPECrypto->currentIndex(); switch (index) { case 0: data.insert(QLatin1String(NM_SSTP_KEY_REQUIRE_MPPE), yesString); break; case 1: data.insert(QLatin1String(NM_SSTP_KEY_REQUIRE_MPPE_128), yesString); break; case 2: data.insert(QLatin1String(NM_SSTP_KEY_REQUIRE_MPPE_40), yesString); break; } if (d->advUi.cb_statefulEncryption->isChecked()) { data.insert(NM_SSTP_KEY_MPPE_STATEFUL, yesString); } } if (!d->advUi.cb_BSD->isChecked()) { data.insert(QLatin1String(NM_SSTP_KEY_NOBSDCOMP), yesString); } if (!d->advUi.cb_deflate->isChecked()) { data.insert(QLatin1String(NM_SSTP_KEY_NODEFLATE), yesString); } if (!d->advUi.cb_TCPheaders->isChecked()) { data.insert(QLatin1String(NM_SSTP_KEY_NO_VJ_COMP), yesString); } // Echo if (d->advUi.cb_sendEcho->isChecked()) { data.insert(QLatin1String(NM_SSTP_KEY_LCP_ECHO_FAILURE), "5"); data.insert(QLatin1String(NM_SSTP_KEY_LCP_ECHO_INTERVAL), "30"); } if (d->advUi.chk_useCustomUnitNumber->isChecked()) { data.insert(QLatin1String(NM_SSTP_KEY_UNIT_NUM), QString::number(d->advUi.sb_customUnitNumber->value())); } if (!d->advUi.le_address->text().isEmpty()) { data.insert(QLatin1String(NM_SSTP_KEY_PROXY_SERVER), d->advUi.le_address->text()); } if (d->advUi.sb_port->value() >= 0) { data.insert(QLatin1String(NM_SSTP_KEY_PROXY_PORT), QString::number(d->advUi.sb_port->value())); } if (!d->advUi.le_username->text().isEmpty()) { data.insert(QLatin1String(NM_SSTP_KEY_PROXY_USER), d->advUi.le_username->text()); } if (!d->advUi.le_password->text().isEmpty()) { data.insert(QLatin1String(NM_SSTP_KEY_PROXY_PASSWORD), d->advUi.le_password->text()); } handleOnePasswordType(d->advUi.le_password, NM_SSTP_KEY_PROXY_PASSWORD_FLAGS, data); // save it all setting.setData(data); setting.setSecrets(secretData); return setting.toMap(); } void SstpSettingWidget::doAdvancedDialog() { Q_D(SstpSettingWidget); d->advancedDlg->show(); } void SstpSettingWidget::fillOnePasswordCombo(PasswordField *passwordField, NetworkManager::Setting::SecretFlags type) { if (type.testFlag(NetworkManager::Setting::None)) { passwordField->setPasswordOption(PasswordField::StoreForAllUsers); } else if (type.testFlag(NetworkManager::Setting::AgentOwned)) { passwordField->setPasswordOption(PasswordField::StoreForUser); } else if (type.testFlag(NetworkManager::Setting::NotSaved)) { passwordField->setPasswordOption(PasswordField::AlwaysAsk); } else { passwordField->setPasswordOption(PasswordField::PasswordField::NotRequired); } } void SstpSettingWidget::handleOnePasswordType(const PasswordField *passwordField, const QString &key, NMStringMap &data) const { const PasswordField::PasswordOption option = passwordField->passwordOption(); switch (option) { case PasswordField::StoreForAllUsers: data.insert(key, QString::number(NetworkManager::Setting::None)); break; case PasswordField::StoreForUser: data.insert(key, QString::number(NetworkManager::Setting::AgentOwned)); break; case PasswordField::AlwaysAsk: data.insert(key, QString::number(NetworkManager::Setting::NotSaved)); break; case PasswordField::NotRequired: data.insert(key, QString::number(NetworkManager::Setting::NotRequired)); break; } } bool SstpSettingWidget::isValid() const { Q_D(const SstpSettingWidget); return !d->ui.le_gateway->text().isEmpty(); } diff --git a/vpn/strongswan/strongswanauth.cpp b/vpn/strongswan/strongswanauth.cpp index a064351e..8f4bd95e 100644 --- a/vpn/strongswan/strongswanauth.cpp +++ b/vpn/strongswan/strongswanauth.cpp @@ -1,126 +1,127 @@ /* Copyright 2011 Ilia Kats Copyright 2013 Lukas Tinkl This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License or (at your option) version 3 or any later version accepted by the membership of KDE e.V. (or its successor approved by the membership of KDE e.V.), which shall act as a proxy defined in Section 14 of version 3 of the license. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see . */ #include "strongswanauth.h" #include "ui_strongswanauth.h" #include "nm-strongswan-service.h" #include #include #include #include +#include #include class StrongswanAuthWidgetPrivate { public: Ui_StrongswanAuth ui; bool acceptOnShow; NetworkManager::VpnSetting::Ptr setting; }; StrongswanAuthWidget::StrongswanAuthWidget(const NetworkManager::VpnSetting::Ptr &setting, QWidget * parent) : SettingWidget(setting, parent) , d_ptr(new StrongswanAuthWidgetPrivate) { Q_D(StrongswanAuthWidget); d->setting = setting; d->ui.setupUi(this); d->acceptOnShow = false; readSecrets(); KAcceleratorManager::manage(this); } StrongswanAuthWidget::~StrongswanAuthWidget() { delete d_ptr; } void StrongswanAuthWidget::readSecrets() { Q_D(StrongswanAuthWidget); const NMStringMap dataMap = d->setting->data(); const QString method = dataMap[NM_STRONGSWAN_METHOD]; if (method == QLatin1String(NM_STRONGSWAN_AUTH_AGENT) || dataMap[NM_STRONGSWAN_SECRET_TYPE] == QLatin1String(NM_STRONGSWAN_PW_TYPE_UNUSED)) { if (isVisible()) { acceptDialog(); } else { d->acceptOnShow = true; } } else if (method == QLatin1String(NM_STRONGSWAN_AUTH_KEY)) { d->ui.passwordLabel->setText(i18nc("@label:textbox password label for private key password", "Private Key Password:")); } else if (method == QLatin1String(NM_STRONGSWAN_AUTH_SMARTCARD)) { d->ui.passwordLabel->setText(i18nc("@label:textbox password label for smartcard pin", "PIN:")); } else if (method == QLatin1String(NM_STRONGSWAN_AUTH_EAP)) { d->ui.passwordLabel->setText(i18nc("@label:textbox password label for EAP password", "Password:")); } } void StrongswanAuthWidget::setVisible(bool visible) { Q_D(StrongswanAuthWidget); SettingWidget::setVisible(visible); if (visible) { if (d->acceptOnShow) { acceptDialog(); } else { SettingWidget::setVisible(visible); } } else { SettingWidget::setVisible(visible); } } void StrongswanAuthWidget::acceptDialog() { QDialog *dialog = qobject_cast(parentWidget()); if (dialog) { dialog->accept(); } } QVariantMap StrongswanAuthWidget::setting() const { Q_D(const StrongswanAuthWidget); NMStringMap secrets; QVariantMap secretData; if (d->setting->data()[NM_STRONGSWAN_METHOD] == QLatin1String(NM_STRONGSWAN_AUTH_AGENT)) { const QString agent = QProcessEnvironment::systemEnvironment().value(QLatin1String("SSH_AUTH_SOCK")); if (!agent.isEmpty()) { secrets.insert(NM_STRONGSWAN_AUTH_AGENT, agent); } else { KMessageBox::error(nullptr, i18nc("@label:textbox error message while saving configuration", "Configuration uses ssh-agent for authentication, but no ssh-agent found running.")); } } else { secrets.insert(NM_STRONGSWAN_SECRET, d->ui.password->text()); } secretData.insert("secrets", QVariant::fromValue(secrets)); return secretData; } diff --git a/vpn/strongswan/strongswanwidget.cpp b/vpn/strongswan/strongswanwidget.cpp index f42a491e..cb4596e2 100644 --- a/vpn/strongswan/strongswanwidget.cpp +++ b/vpn/strongswan/strongswanwidget.cpp @@ -1,173 +1,175 @@ /* Copyright 2008 Will Stephenson Copyright 2010 Maurus Rohrer Copyright 2013 Lukas Tinkl This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License or (at your option) version 3 or any later version accepted by the membership of KDE e.V. (or its successor approved by the membership of KDE e.V.), which shall act as a proxy defined in Section 14 of version 3 of the license. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see . */ #include "strongswanwidget.h" #include "nm-strongswan-service.h" #include "ui_strongswanprop.h" #include #include +#include + class StrongswanSettingWidgetPrivate { public: Ui_StrongswanProp ui; NetworkManager::VpnSetting::Ptr setting; enum AuthType {PrivateKey = 0, SshAgent, Smartcard, Eap}; }; StrongswanSettingWidget::StrongswanSettingWidget(const NetworkManager::VpnSetting::Ptr &setting, QWidget *parent) : SettingWidget(setting, parent) , d_ptr(new StrongswanSettingWidgetPrivate) { Q_D(StrongswanSettingWidget); d->ui.setupUi(this); d->setting = setting; // Connect for setting check watchChangedSetting(); // Connect for validity check connect(d->ui.leGateway, &QLineEdit::textChanged, this, &StrongswanSettingWidget::slotWidgetChanged); connect(d->ui.proposal, &QGroupBox::toggled, this, &SettingWidget::settingChanged); KAcceleratorManager::manage(this); if (d->setting && !d->setting->isNull()) { loadConfig(d->setting); } } StrongswanSettingWidget::~StrongswanSettingWidget() { delete d_ptr; } void StrongswanSettingWidget::loadConfig(const NetworkManager::Setting::Ptr &setting) { Q_UNUSED(setting) Q_D(StrongswanSettingWidget); // General settings const NMStringMap dataMap = d->setting->data(); // Gateway Address const QString gateway = dataMap[NM_STRONGSWAN_GATEWAY]; if (!gateway.isEmpty()) { d->ui.leGateway->setText(gateway); } // Certificate d->ui.leGatewayCertificate->setUrl(QUrl::fromLocalFile(dataMap[NM_STRONGSWAN_CERTIFICATE]) ); // Authentication const QString method = dataMap[NM_STRONGSWAN_METHOD]; if (method == QLatin1String(NM_STRONGSWAN_AUTH_KEY)) { d->ui.cmbMethod->setCurrentIndex(StrongswanSettingWidgetPrivate::PrivateKey); d->ui.leAuthPrivatekeyCertificate->setUrl(QUrl::fromLocalFile(dataMap[NM_STRONGSWAN_USERCERT])); d->ui.leAuthPrivatekeyKey->setUrl(QUrl::fromLocalFile(dataMap[NM_STRONGSWAN_USERKEY])); } else if (method == QLatin1String(NM_STRONGSWAN_AUTH_AGENT)) { d->ui.cmbMethod->setCurrentIndex(StrongswanSettingWidgetPrivate::SshAgent); d->ui.leAuthSshCertificate->setUrl(QUrl::fromLocalFile(dataMap[NM_STRONGSWAN_USERCERT])); } else if (method == QLatin1String(NM_STRONGSWAN_AUTH_SMARTCARD)) { d->ui.cmbMethod->setCurrentIndex(StrongswanSettingWidgetPrivate::Smartcard); } else if (method == QLatin1String(NM_STRONGSWAN_AUTH_EAP)) { d->ui.cmbMethod->setCurrentIndex(StrongswanSettingWidgetPrivate::Eap); d->ui.leUserName->setText(dataMap[NM_STRONGSWAN_USER]); } // Settings d->ui.innerIP->setChecked(dataMap[NM_STRONGSWAN_INNERIP] == "yes"); d->ui.udpEncap->setChecked(dataMap[NM_STRONGSWAN_ENCAP] == "yes"); d->ui.ipComp->setChecked(dataMap[NM_STRONGSWAN_IPCOMP] == "yes"); d->ui.proposal->setChecked(dataMap[NM_STRONGSWAN_PROPOSAL] == "yes"); d->ui.ike->setText(dataMap[NM_STRONGSWAN_IKE]); d->ui.esp->setText(dataMap[NM_STRONGSWAN_ESP]); } void StrongswanSettingWidget::loadSecrets(const NetworkManager::Setting::Ptr &setting) { Q_D(StrongswanSettingWidget); Q_UNUSED(setting); } QVariantMap StrongswanSettingWidget::setting() const { Q_D(const StrongswanSettingWidget); NetworkManager::VpnSetting setting; setting.setServiceType(QLatin1String(NM_DBUS_SERVICE_STRONGSWAN)); NMStringMap data; NMStringMap secretData; // General settings // Gateway if (!d->ui.leGateway->text().isEmpty()) { data.insert(NM_STRONGSWAN_GATEWAY, d->ui.leGateway->text()); } data.insert( NM_STRONGSWAN_CERTIFICATE, d->ui.leGatewayCertificate->url().toLocalFile()); // Authentication switch (d->ui.cmbMethod->currentIndex()) { case StrongswanSettingWidgetPrivate::PrivateKey: data.insert(NM_STRONGSWAN_METHOD, NM_STRONGSWAN_AUTH_KEY); data.insert(NM_STRONGSWAN_USERCERT, d->ui.leAuthPrivatekeyCertificate->url().toLocalFile()); data.insert(NM_STRONGSWAN_USERKEY, d->ui.leAuthPrivatekeyKey->url().toLocalFile()); break; case StrongswanSettingWidgetPrivate::SshAgent: data.insert(NM_STRONGSWAN_METHOD, NM_STRONGSWAN_AUTH_AGENT); data.insert(NM_STRONGSWAN_USERCERT, d->ui.leAuthSshCertificate->url().toLocalFile()); break; case StrongswanSettingWidgetPrivate::Smartcard: data.insert(NM_STRONGSWAN_METHOD, NM_STRONGSWAN_AUTH_SMARTCARD); break; case StrongswanSettingWidgetPrivate::Eap: data.insert(NM_STRONGSWAN_METHOD, NM_STRONGSWAN_AUTH_EAP); if (!d->ui.leUserName->text().isEmpty()) { data.insert(NM_STRONGSWAN_USER, d->ui.leUserName->text()); } //StrongSwan-nm 1.2 does not appear to be able to save secrets, the must be entered through the auth dialog } //Options data.insert(NM_STRONGSWAN_INNERIP, d->ui.innerIP->isChecked() ? "yes" : "no"); data.insert(NM_STRONGSWAN_ENCAP, d->ui.udpEncap->isChecked() ? "yes" : "no"); data.insert(NM_STRONGSWAN_IPCOMP, d->ui.ipComp->isChecked() ? "yes" : "no"); if (d->ui.proposal->isChecked()) { data.insert(NM_STRONGSWAN_PROPOSAL, "yes"); data.insert(NM_STRONGSWAN_IKE, d->ui.ike->text()); data.insert(NM_STRONGSWAN_ESP, d->ui.esp->text()); } else data.insert(NM_STRONGSWAN_PROPOSAL, "no"); // save it all setting.setData(data); setting.setSecrets(secretData); return setting.toMap(); } bool StrongswanSettingWidget::isValid() const { Q_D(const StrongswanSettingWidget); return !d->ui.leGateway->text().isEmpty(); } diff --git a/vpn/vpnc/vpncauth.cpp b/vpn/vpnc/vpncauth.cpp index 159f3399..7277178c 100644 --- a/vpn/vpnc/vpncauth.cpp +++ b/vpn/vpnc/vpncauth.cpp @@ -1,116 +1,118 @@ /* Copyright 2010 Andrey Borzenkov Copyright 2013 Lukas Tinkl This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License or (at your option) version 3 or any later version accepted by the membership of KDE e.V. (or its successor approved by the membership of KDE e.V.), which shall act as a proxy defined in Section 14 of version 3 of the license. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see . */ #include "vpncauth.h" #include "ui_vpncauth.h" #include "nm-vpnc-service.h" #include +#include + class VpncAuthDialogPrivate { public: Ui_VpncAuth ui; NetworkManager::VpnSetting::Ptr setting; }; VpncAuthDialog::VpncAuthDialog(const NetworkManager::VpnSetting::Ptr &setting, QWidget * parent) : SettingWidget(setting, parent) , d_ptr(new VpncAuthDialogPrivate) { Q_D(VpncAuthDialog); d->ui.setupUi(this); d->setting = setting; readSecrets(); KAcceleratorManager::manage(this); } VpncAuthDialog::~VpncAuthDialog() { delete d_ptr; } void VpncAuthDialog::readSecrets() { Q_D(VpncAuthDialog); const NMStringMap data = d->setting->data(); const NMStringMap secrets = d->setting->secrets(); // username const QString user = data.value(NM_VPNC_KEY_XAUTH_USER); if (!user.isEmpty()) { d->ui.leUserName->setText(user); } // group name const QString group = data.value(NM_VPNC_KEY_ID); if (!group.isEmpty()) { d->ui.leGroupName->setText(group); } bool haveUserPassword = true; if (!((NetworkManager::Setting::SecretFlags)data.value(NM_VPNC_KEY_XAUTH_PASSWORD"-flags").toInt()).testFlag(NetworkManager::Setting::NotRequired)) { d->ui.leUserPassword->setText(secrets.value(QLatin1String(NM_VPNC_KEY_XAUTH_PASSWORD))); } else { d->ui.userNameLabel->setVisible(false); d->ui.leUserName->setVisible(false); d->ui.userPasswordLabel->setVisible(false); d->ui.leUserPassword->setVisible(false); haveUserPassword = false; } if (!((NetworkManager::Setting::SecretFlags)data.value(NM_VPNC_KEY_SECRET"-flags").toInt()).testFlag(NetworkManager::Setting::NotRequired)) { d->ui.leGroupPassword->setText(secrets.value(QLatin1String(NM_VPNC_KEY_SECRET))); } else { d->ui.groupNameLabel->setVisible(false); d->ui.leGroupName->setVisible(false); d->ui.groupPasswordLabel->setVisible(false); d->ui.leGroupPassword->setVisible(false); } if (haveUserPassword && d->ui.leUserPassword->text().isEmpty()) { d->ui.leUserPassword->setFocus(Qt::OtherFocusReason); } else if (d->ui.leGroupPassword->text().isEmpty()) { d->ui.leGroupPassword->setFocus(Qt::OtherFocusReason); } } QVariantMap VpncAuthDialog::setting() const { Q_D(const VpncAuthDialog); NMStringMap secrets; QVariantMap result; // user password if (!d->ui.leUserPassword->text().isEmpty()) { secrets.insert(NM_VPNC_KEY_XAUTH_PASSWORD, d->ui.leUserPassword->text()); } // group password if (!d->ui.leGroupPassword->text().isEmpty()) { secrets.insert(NM_VPNC_KEY_SECRET, d->ui.leGroupPassword->text()); } result.insert("secrets", QVariant::fromValue(secrets)); return result; } diff --git a/vpn/vpnc/vpncwidget.cpp b/vpn/vpnc/vpncwidget.cpp index d993e60d..433e1912 100644 --- a/vpn/vpnc/vpncwidget.cpp +++ b/vpn/vpnc/vpncwidget.cpp @@ -1,236 +1,237 @@ /* Copyright 2013 Lukas Tinkl This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) version 3, or any later version accepted by the membership of KDE e.V. (or its successor approved by the membership of KDE e.V.), which shall act as a proxy defined in Section 6 of version 3 of the license. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library. If not, see . */ #include "vpncwidget.h" #include "vpncadvancedwidget.h" #include "ui_vpnc.h" #include "nm-vpnc-service.h" +#include #include -#include +#include VpncWidget::VpncWidget(const NetworkManager::VpnSetting::Ptr &setting, QWidget* parent, Qt::WindowFlags f) : SettingWidget(setting, parent, f) , m_ui(new Ui::VpncWidget) , m_setting(setting) { qDBusRegisterMetaType(); m_ui->setupUi(this); m_ui->groupPassword->setPasswordOptionsEnabled(true); m_ui->groupPassword->setPasswordNotRequiredEnabled(true); m_ui->userPassword->setPasswordOptionsEnabled(true); m_ui->userPassword->setPasswordNotRequiredEnabled(true); connect(m_ui->btnAdvanced, &QPushButton::clicked, this, &VpncWidget::showAdvanced); // Connect for setting check watchChangedSetting(); // Connect for validity check connect(m_ui->gateway, &QLineEdit::textChanged, this, &VpncWidget::slotWidgetChanged); KAcceleratorManager::manage(this); m_advancedWidget = new VpncAdvancedWidget(m_setting, this); NMStringMap advData = m_advancedWidget->setting(); if (!advData.isEmpty()) { if (m_tmpSetting.isNull()) { m_tmpSetting = NetworkManager::VpnSetting::Ptr(new NetworkManager::VpnSetting); } m_tmpSetting->setData(advData); } if (setting && !setting->isNull()) { loadConfig(setting); } } VpncWidget::~VpncWidget() { m_tmpSetting.clear(); m_advancedWidget->deleteLater(); delete m_ui; } void VpncWidget::loadConfig(const NetworkManager::Setting::Ptr &setting) { Q_UNUSED(setting); const NMStringMap data = m_setting->data(); const QString gateway = data.value(NM_VPNC_KEY_GATEWAY); if (!gateway.isEmpty()) { m_ui->gateway->setText(gateway); } const QString user = data.value(NM_VPNC_KEY_XAUTH_USER); if (!user.isEmpty()) { m_ui->user->setText(user); } const NetworkManager::Setting::SecretFlags userPassType = static_cast(data.value(NM_VPNC_KEY_XAUTH_PASSWORD"-flags").toInt()); if (userPassType.testFlag(NetworkManager::Setting::None)) { m_ui->userPassword->setPasswordOption(PasswordField::StoreForAllUsers); } else if (userPassType.testFlag(NetworkManager::Setting::AgentOwned)) { m_ui->userPassword->setPasswordOption(PasswordField::StoreForUser); } else if (userPassType.testFlag(NetworkManager::Setting::NotSaved)) { m_ui->userPassword->setPasswordOption(PasswordField::AlwaysAsk); } else { m_ui->userPassword->setPasswordOption(PasswordField::NotRequired); } const QString groupName = data.value(NM_VPNC_KEY_ID); if (!groupName.isEmpty()) { m_ui->group->setText(groupName); } const NetworkManager::Setting::SecretFlags groupPassType = static_cast(data.value(NM_VPNC_KEY_SECRET"-flags").toInt()); if (groupPassType.testFlag(NetworkManager::Setting::None)) { m_ui->groupPassword->setPasswordOption(PasswordField::StoreForAllUsers); } else if (groupPassType.testFlag(NetworkManager::Setting::AgentOwned)) { m_ui->groupPassword->setPasswordOption(PasswordField::StoreForUser); } else if (groupPassType.testFlag(NetworkManager::Setting::NotSaved)) { m_ui->groupPassword->setPasswordOption(PasswordField::AlwaysAsk); } else { m_ui->groupPassword->setPasswordOption(PasswordField::NotRequired); } if (data.value(NM_VPNC_KEY_AUTHMODE) == QLatin1String("hybrid")) { m_ui->useHybridAuth->setChecked(true); m_ui->caFile->setUrl(QUrl::fromLocalFile(data.value(NM_VPNC_KEY_CA_FILE))); } loadSecrets(setting); } void VpncWidget::loadSecrets(const NetworkManager::Setting::Ptr &setting) { NetworkManager::VpnSetting::Ptr vpnSetting = setting.staticCast(); if (vpnSetting) { const NMStringMap secrets = vpnSetting->secrets(); const QString userPassword = secrets.value(NM_VPNC_KEY_XAUTH_PASSWORD); if (!userPassword.isEmpty()) { m_ui->userPassword->setText(userPassword); } const QString groupPassword = secrets.value(NM_VPNC_KEY_SECRET); if (!groupPassword.isEmpty()) { m_ui->groupPassword->setText(groupPassword); } } } QVariantMap VpncWidget::setting() const { NetworkManager::VpnSetting setting; setting.setServiceType(QLatin1String(NM_DBUS_SERVICE_VPNC)); NMStringMap data; NMStringMap secrets; if (!m_tmpSetting.isNull()) { data = m_tmpSetting->data(); } if (!m_ui->gateway->text().isEmpty()) { data.insert(NM_VPNC_KEY_GATEWAY, m_ui->gateway->text()); } if (!m_ui->user->text().isEmpty()) { data.insert(NM_VPNC_KEY_XAUTH_USER, m_ui->user->text()); } if (m_ui->userPassword->isEnabled() && !m_ui->userPassword->text().isEmpty()) { secrets.insert(NM_VPNC_KEY_XAUTH_PASSWORD, m_ui->userPassword->text()); } if (m_ui->userPassword->passwordOption() == PasswordField::StoreForAllUsers) { data.insert(NM_VPNC_KEY_XAUTH_PASSWORD"-flags", QString::number(NetworkManager::Setting::None)); } else if (m_ui->userPassword->passwordOption() == PasswordField::StoreForUser) { data.insert(NM_VPNC_KEY_XAUTH_PASSWORD"-flags", QString::number(NetworkManager::Setting::AgentOwned)); } else if (m_ui->userPassword->passwordOption() == PasswordField::AlwaysAsk) { // SettingWidget::EnumPasswordStorageType::Store data.insert(NM_VPNC_KEY_XAUTH_PASSWORD"-flags", QString::number(NetworkManager::Setting::NotSaved)); } else { data.insert(NM_VPNC_KEY_XAUTH_PASSWORD"-flags", QString::number(NetworkManager::Setting::NotRequired)); } if (!m_ui->group->text().isEmpty()) { data.insert(NM_VPNC_KEY_ID, m_ui->group->text()); } if (m_ui->groupPassword->isEnabled() && !m_ui->groupPassword->text().isEmpty()) { secrets.insert(NM_VPNC_KEY_SECRET, m_ui->groupPassword->text()); } if (m_ui->groupPassword->passwordOption() == PasswordField::StoreForAllUsers) { data.insert(NM_VPNC_KEY_SECRET"-flags", QString::number(NetworkManager::Setting::None)); } else if (m_ui->groupPassword->passwordOption() == PasswordField::StoreForUser) { data.insert(NM_VPNC_KEY_SECRET"-flags", QString::number(NetworkManager::Setting::AgentOwned)); } else if (m_ui->groupPassword->passwordOption() == PasswordField::AlwaysAsk) { // SettingWidget::EnumPasswordStorageType::Store data.insert(NM_VPNC_KEY_SECRET"-flags", QString::number(NetworkManager::Setting::NotSaved)); } else { data.insert(NM_VPNC_KEY_SECRET"-flags", QString::number(NetworkManager::Setting::NotRequired)); } if (m_ui->useHybridAuth->isChecked() && m_ui->caFile->url().isValid()) { data.insert(NM_VPNC_KEY_AUTHMODE, "hybrid"); data.insert(NM_VPNC_KEY_CA_FILE, m_ui->caFile->url().toLocalFile()); } setting.setData(data); setting.setSecrets(secrets); return setting.toMap(); } void VpncWidget::userPasswordTypeChanged(int index) { m_ui->userPassword->setEnabled(index == SettingWidget::EnumPasswordStorageType::Store); } void VpncWidget::groupPasswordTypeChanged(int index) { m_ui->groupPassword->setEnabled(index == SettingWidget::EnumPasswordStorageType::Store); } void VpncWidget::showAdvanced() { m_advancedWidget->loadConfig(m_tmpSetting); connect(m_advancedWidget.data(), &VpncAdvancedWidget::accepted, [this] () { NMStringMap advData = m_advancedWidget->setting(); if (!advData.isEmpty()) { m_tmpSetting->setData(advData); } }); m_advancedWidget->setModal(true); m_advancedWidget->show(); } bool VpncWidget::isValid() const { return !m_ui->gateway->text().isEmpty(); }