#6669 Added TLS config options to select key length and certificate path

Signed-off-by: Jamie Newbon <jamie@symless.com>
This commit is contained in:
Jamie Newbon 2020-07-27 17:21:46 +01:00
parent e08423b0c6
commit 32bd271edf
8 changed files with 244 additions and 58 deletions

View File

@ -73,6 +73,8 @@ const char* AppConfig::m_SynergySettingsName[] = {
"useInternalConfig",
"groupClientChecked",
"serverHostname",
"tlsCertPath",
"tlsKeyLength",
};
static const char* logLevelNames[] =
@ -249,6 +251,13 @@ void AppConfig::loadSettings()
m_ClientGroupChecked = loadSetting(kGroupClientCheck, true).toBool();
m_ServerHostname = loadSetting(kServerHostname).toString();
//Set the default path of the TLS certificate file in the users DIR
QString certificateFilename = QString("%1/%2/%3").arg(m_CoreInterface.getProfileDir(),
"SSL",
"Synergy.pem");
m_TLSCertificatePath = loadSetting(kTLSCertPath, certificateFilename).toString();
m_TLSKeyLength = loadSetting(kTLSKeyLength, 2048).toInt();
}
@ -527,3 +536,19 @@ void AppConfig::setSettingModified(T &variable, const T& newValue) {
}
}
void AppConfig::setTLSCertPath(const QString& path) {
m_TLSCertificatePath = path;
}
QString AppConfig::getTLSCertPath() const {
return m_TLSCertificatePath;
}
QString AppConfig::getTLSKeyLength() const {
return m_TLSKeyLength;
}
void AppConfig::setTLSKeyLength(const QString& length) {
m_TLSKeyLength = length;
}

View File

@ -27,6 +27,7 @@
#include <shared/EditionType.h>
#include <mutex>
#include "ConfigBase.h"
#include "CoreInterface.h"
// this should be incremented each time a new page is added. this is
// saved to settings when the user finishes running the wizard. if
@ -126,6 +127,14 @@ class AppConfig: public QObject, public GUI::Config::ConfigBase
bool getClientGroupChecked() const;
QString getServerHostname() const;
/// @brief Gets the current TLS certificate path
/// @return QString The path to the cert
QString getTLSCertPath() const;
/// @brief Get the key length to be used for the private key of a TLS cert
/// @return QString The key length in bits
QString getTLSKeyLength() const;
void setServerGroupChecked(bool);
void setUseExternalConfig(bool) ;
void setConfigFile(const QString&);
@ -133,6 +142,15 @@ class AppConfig: public QObject, public GUI::Config::ConfigBase
void setClientGroupChecked(bool) ;
void setServerHostname(const QString&);
/// @brief Set the path to the TLS/SSL certificate file that will be used
/// @param [in] path The path to the Certificate
void setTLSCertPath(const QString& path);
/// @brief Sets the key length of the private key to use in a TLS connection
/// @param [in] QString length The key length eg: 1024, 2048, 4096
void setTLSKeyLength(const QString& length);
QString lastVersion() const;
void setMinimizeToTray(bool b);
@ -174,6 +192,8 @@ protected:
kUseInternalConfig,
kGroupClientCheck,
kServerHostname,
kTLSCertPath,
kTLSKeyLength,
};
void setScreenName(const QString& s);
@ -224,10 +244,15 @@ protected:
bool m_ClientGroupChecked;
QString m_ServerHostname;
QString m_TLSCertificatePath; /// @brief The path to the TLS certificate file
QString m_TLSKeyLength; /// @brief The key length of the TLS cert to make
bool m_LoadFromSystemScope; /// @brief should the setting be loaded from SystemScope
/// If the user has settings but this is true then
/// system settings will be loaded instead of the users
CoreInterface m_CoreInterface;
static const char m_SynergysName[];
static const char m_SynergycName[];
static const char m_SynergyLogDir[];

View File

@ -744,10 +744,6 @@ void MainWindow::retryStart()
void
MainWindow::sslToggled (bool enabled)
{
if (enabled) {
m_pSslCertificate = new SslCertificate(this);
m_pSslCertificate->generateCertificate();
}
updateLocalFingerprint();
}

View File

@ -65,9 +65,22 @@ void SettingsDialog::accept()
appConfig().setAutoHide(m_pCheckBoxAutoHide->isChecked());
appConfig().setAutoConfig(m_pCheckBoxAutoConfig->isChecked());
appConfig().setMinimizeToTray(m_pCheckBoxMinimizeToTray->isChecked());
appConfig().setTLSCertPath(m_pLineEditCertificatePath->text());
bool keyLengthChanged = appConfig().getTLSKeyLength() != m_pComboBoxKeyLength->currentText();
appConfig().setTLSKeyLength(m_pComboBoxKeyLength->currentText());
//We only need to test the System scoped Radio as they are connected
appConfig().setLoadFromSystemScope(m_pRadioSystemScope->isChecked());
if(m_pCheckBoxEnableCrypto->isChecked()) {
SslCertificate sslCertificate;
sslCertificate.generateCertificate(appConfig().getTLSCertPath(),
m_pComboBoxKeyLength->currentText(),
keyLengthChanged);
}
m_appConfig.setCryptoEnabled(m_pCheckBoxEnableCrypto->isChecked());
QDialog::accept();
}
@ -116,6 +129,8 @@ void SettingsDialog::loadFromConfig() {
m_pCheckBoxAutoHide->setChecked(appConfig().getAutoHide());
m_pCheckBoxMinimizeToTray->setChecked(appConfig().getMinimizeToTray());
m_pCheckBoxEnableCrypto->setChecked(m_appConfig.getCryptoEnabled());
m_pLineEditCertificatePath->setText(appConfig().getTLSCertPath());
m_pComboBoxKeyLength->setCurrentIndex(m_pComboBoxKeyLength->findText(appConfig().getTLSKeyLength()));
if (m_appConfig.isSystemScoped()) {
m_pRadioSystemScope->setChecked(true);
@ -204,7 +219,11 @@ void SettingsDialog::on_m_pCheckBoxEnableCrypto_toggled(bool checked)
SslCertificate sslCertificate;
sslCertificate.generateCertificate();
m_pMainWindow->updateLocalFingerprint();
verticalSpacer_4->changeSize(10, 10, QSizePolicy::Minimum);
} else {
verticalSpacer_4->changeSize(10, 0, QSizePolicy::Ignored);
}
adjustSize();
}
void SettingsDialog::on_m_pLabelInstallBonjour_linkActivated(const QString&)
@ -219,3 +238,16 @@ void SettingsDialog::on_m_pRadioSystemScope_toggled(bool checked)
appConfig().setLoadFromSystemScope(checked);
loadFromConfig();
}
void SettingsDialog::on_m_pPushButtonBrowseCert_clicked() {
QString fileName = QFileDialog::getSaveFileName(
this, tr("Select a TLS certificate to use..."),
m_pLineEditCertificatePath->text(),
"Cert (*.pem)",
nullptr,
QFileDialog::DontConfirmOverwrite);
if (!fileName.isEmpty()) {
m_pLineEditCertificatePath->setText(fileName);
}
}

View File

@ -65,6 +65,10 @@ class SettingsDialog : public QDialog, public Ui::SettingsDialogBase
/// @brief Handles the toggling of the system scoped radio button
/// As the user scope radio is connected this will fire for either radio button
void on_m_pRadioSystemScope_toggled(bool checked);
/// @brief Handles the click event of the Cert Path browse button
/// displaying a file browser
void on_m_pPushButtonBrowseCert_clicked();
};
#endif

View File

@ -6,16 +6,15 @@
<rect>
<x>0</x>
<y>0</y>
<width>357</width>
<height>496</height>
<width>378</width>
<height>756</height>
</rect>
</property>
<property name="windowTitle">
<string>Settings</string>
</property>
<layout class="QVBoxLayout" name="verticalLayout">
<item>
<layout class="QGridLayout" name="gridLayout_5">
<item row="0" column="0">
<widget class="QGroupBox" name="m_pGroupScope">
<property name="title">
<string>&amp;Settings Scope</string>
@ -41,7 +40,7 @@
</layout>
</widget>
</item>
<item>
<item row="1" column="0">
<widget class="QGroupBox" name="m_pGroupAdvanced">
<property name="title">
<string>&amp;Miscellaneous</string>
@ -190,7 +189,7 @@
</layout>
</widget>
</item>
<item>
<item row="2" column="0">
<spacer name="verticalSpacer_2">
<property name="orientation">
<enum>Qt::Vertical</enum>
@ -206,7 +205,7 @@
</property>
</spacer>
</item>
<item>
<item row="3" column="0">
<widget class="QGroupBox" name="m_pGroupNetwork">
<property name="enabled">
<bool>true</bool>
@ -220,10 +219,7 @@
<property name="title">
<string>&amp;Network</string>
</property>
<layout class="QFormLayout" name="formLayout">
<property name="fieldGrowthPolicy">
<enum>QFormLayout::AllNonFixedFieldsGrow</enum>
</property>
<layout class="QGridLayout" name="gridLayout_6">
<property name="leftMargin">
<number>2</number>
</property>
@ -236,7 +232,7 @@
<property name="bottomMargin">
<number>12</number>
</property>
<item row="0" column="1">
<item row="0" column="0">
<layout class="QGridLayout" name="m_pGridLayoutNetwork">
<property name="leftMargin">
<number>0</number>
@ -244,36 +240,6 @@
<property name="verticalSpacing">
<number>12</number>
</property>
<item row="1" column="0">
<widget class="QCheckBox" name="m_pCheckBoxEnableCrypto">
<property name="enabled">
<bool>false</bool>
</property>
<property name="text">
<string>Enable &amp;TLS Encryption</string>
</property>
</widget>
</item>
<item row="0" column="0">
<widget class="QCheckBox" name="m_pCheckBoxAutoConfig">
<property name="enabled">
<bool>false</bool>
</property>
<property name="text">
<string>Enable Auto Config</string>
</property>
</widget>
</item>
<item row="0" column="1">
<widget class="QLabel" name="m_pLabelInstallBonjour">
<property name="text">
<string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;&lt;a href=&quot;#&quot;&gt;&lt;span style=&quot; text-decoration: underline; color:#007af4;&quot;&gt;Install Bonjour&lt;/span&gt;&lt;/a&gt;&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
</property>
<property name="textFormat">
<enum>Qt::RichText</enum>
</property>
</widget>
</item>
<item row="1" column="1">
<widget class="QLabel" name="m_pLabelProUpgrade">
<property name="text">
@ -287,12 +253,42 @@
</property>
</widget>
</item>
<item row="0" column="1">
<widget class="QLabel" name="m_pLabelInstallBonjour">
<property name="text">
<string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;&lt;a href=&quot;#&quot;&gt;&lt;span style=&quot; text-decoration: underline; color:#007af4;&quot;&gt;Install Bonjour&lt;/span&gt;&lt;/a&gt;&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
</property>
<property name="textFormat">
<enum>Qt::RichText</enum>
</property>
</widget>
</item>
<item row="0" column="0">
<widget class="QCheckBox" name="m_pCheckBoxAutoConfig">
<property name="enabled">
<bool>false</bool>
</property>
<property name="text">
<string>Enable Auto Config</string>
</property>
</widget>
</item>
<item row="1" column="0">
<widget class="QCheckBox" name="m_pCheckBoxEnableCrypto">
<property name="enabled">
<bool>false</bool>
</property>
<property name="text">
<string>Enable &amp;TLS Encryption</string>
</property>
</widget>
</item>
</layout>
</item>
</layout>
</widget>
</item>
<item>
<item row="4" column="0">
<spacer name="verticalSpacer_3">
<property name="orientation">
<enum>Qt::Vertical</enum>
@ -308,7 +304,85 @@
</property>
</spacer>
</item>
<item>
<item row="5" column="0">
<widget class="QGroupBox" name="m_pGroupBoxTLS">
<property name="title">
<string>TLS/SSL Settings</string>
</property>
<layout class="QGridLayout" name="gridLayout">
<item row="1" column="1">
<widget class="QLineEdit" name="m_pLineEditCertificatePath"/>
</item>
<item row="0" column="0">
<widget class="QLabel" name="m_pLabel_29">
<property name="text">
<string>Key length</string>
</property>
</widget>
</item>
<item row="1" column="0">
<widget class="QLabel" name="m_pLabel_30">
<property name="text">
<string>Certificate Path</string>
</property>
</widget>
</item>
<item row="1" column="2">
<widget class="QPushButton" name="m_pPushButtonBrowseCert">
<property name="text">
<string>Browse</string>
</property>
</widget>
</item>
<item row="0" column="1" colspan="2">
<widget class="QComboBox" name="m_pComboBoxKeyLength">
<property name="currentText">
<string>2048</string>
</property>
<item>
<property name="text">
<string>1024</string>
</property>
</item>
<item>
<property name="text">
<string>2048</string>
</property>
</item>
<item>
<property name="text">
<string>4096</string>
</property>
</item>
</widget>
</item>
<item row="2" column="1">
<widget class="QPushButton" name="pushButton">
<property name="text">
<string>Regenerate Cert</string>
</property>
</widget>
</item>
</layout>
</widget>
</item>
<item row="6" column="0">
<spacer name="verticalSpacer_4">
<property name="orientation">
<enum>Qt::Vertical</enum>
</property>
<property name="sizeType">
<enum>QSizePolicy::Minimum</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>20</width>
<height>10</height>
</size>
</property>
</spacer>
</item>
<item row="7" column="0">
<widget class="QGroupBox" name="m_pGroupLog">
<property name="sizePolicy">
<sizepolicy hsizetype="Preferred" vsizetype="Preferred">
@ -393,7 +467,7 @@
</layout>
</widget>
</item>
<item>
<item row="8" column="0">
<spacer name="verticalSpacer">
<property name="orientation">
<enum>Qt::Vertical</enum>
@ -409,7 +483,7 @@
</property>
</spacer>
</item>
<item>
<item row="9" column="0">
<widget class="QDialogButtonBox" name="buttonBox">
<property name="orientation">
<enum>Qt::Horizontal</enum>
@ -422,13 +496,20 @@
</layout>
</widget>
<tabstops>
<tabstop>m_pRadioSystemScope</tabstop>
<tabstop>m_pRadioUserScope</tabstop>
<tabstop>m_pComboLanguage</tabstop>
<tabstop>m_pLineEditScreenName</tabstop>
<tabstop>m_pSpinBoxPort</tabstop>
<tabstop>m_pLineEditInterface</tabstop>
<tabstop>m_pCheckBoxMinimizeToTray</tabstop>
<tabstop>m_pComboElevate</tabstop>
<tabstop>m_pCheckBoxAutoHide</tabstop>
<tabstop>m_pCheckBoxMinimizeToTray</tabstop>
<tabstop>m_pCheckBoxAutoConfig</tabstop>
<tabstop>m_pCheckBoxEnableCrypto</tabstop>
<tabstop>m_pComboBoxKeyLength</tabstop>
<tabstop>m_pLineEditCertificatePath</tabstop>
<tabstop>m_pPushButtonBrowseCert</tabstop>
<tabstop>m_pComboLogLevel</tabstop>
<tabstop>m_pCheckBoxLogToFile</tabstop>
<tabstop>m_pLineEditLogFilename</tabstop>
@ -468,5 +549,21 @@
</hint>
</hints>
</connection>
<connection>
<sender>m_pCheckBoxEnableCrypto</sender>
<signal>toggled(bool)</signal>
<receiver>m_pGroupBoxTLS</receiver>
<slot>setVisible(bool)</slot>
<hints>
<hint type="sourcelabel">
<x>100</x>
<y>413</y>
</hint>
<hint type="destinationlabel">
<x>188</x>
<y>508</y>
</hint>
</hints>
</connection>
</connections>
</ui>

View File

@ -25,7 +25,7 @@
static const char kCertificateKeyLength[] = "rsa:2048"; //RSA Bit length (e.g. 1024/2048/4096)
static const char kCertificateKeyLength[] = "rsa:"; //RSA Bit length (e.g. 1024/2048/4096)
static const char kCertificateHashAlgorithm[] = "-sha256"; //fingerprint hashing algorithm
static const char kCertificateLifetime[] = "365";
static const char kCertificateSubjectInfo[] = "/CN=Synergy";
@ -93,7 +93,7 @@ bool SslCertificate::runTool(const QStringList& args)
return true;
}
void SslCertificate::generateCertificate()
void SslCertificate::generateCertificate(const QString& path, const QString& keyLength, bool forceGen)
{
QString sslDirPath = QString("%1%2%3")
.arg(m_ProfileDir)
@ -105,8 +105,11 @@ void SslCertificate::generateCertificate()
.arg(QDir::separator())
.arg(kCertificateFilename);
QFile file(filename);
if (!file.exists()) {
QString keySize = kCertificateKeyLength + keyLength;
//If path is empty use filename
QFile file(path.isEmpty() ? filename : path);
if (!file.exists() || forceGen) {
QStringList arguments;
// self signed certificate
@ -126,7 +129,7 @@ void SslCertificate::generateCertificate()
// private key
arguments.append("-newkey");
arguments.append(kCertificateKeyLength);
arguments.append(keySize);
QDir sslDir(sslDirPath);
if (!sslDir.exists()) {

View File

@ -29,7 +29,11 @@ public:
explicit SslCertificate(QObject *parent = 0);
public slots:
void generateCertificate();
/// @brief Generates a TLS cert and private key
/// @param [in] QString path The path of the file to be generated
/// @param [in] QString keyLength The size of the private key. default: 2048
/// @param [in] bool Should the file be created regardless of if the file already exists
void generateCertificate(const QString& path = QString(), const QString& keyLength = "2048", bool forceGen = false);
signals:
void error(QString e);