forked from qt-creator/qt-creator
SSH: Print more helpful error message on key decoding error.
The botan exception string doesn't help anybody. Change-Id: I81b8b837b0cf3406a8293cbf85b8fd1bff9bfa74 Reviewed-by: hjk <qthjk@ovi.com>
This commit is contained in:
@@ -640,11 +640,6 @@ void SshConnectionPrivate::connectToHost()
|
||||
m_errorString = ex.errorString;
|
||||
emit error(m_error);
|
||||
return;
|
||||
} catch (const Botan::Exception &ex) {
|
||||
m_error = SshKeyFileError;
|
||||
m_errorString = QString::fromAscii(ex.what());
|
||||
emit error(m_error);
|
||||
return;
|
||||
}
|
||||
|
||||
connect(m_socket, SIGNAL(connected()), this, SLOT(handleSocketConnected()));
|
||||
|
||||
@@ -200,18 +200,22 @@ void SshEncryptionFacility::createAuthenticationKey(const QByteArray &privKeyFil
|
||||
#endif
|
||||
QList<BigInt> pubKeyParams;
|
||||
QList<BigInt> allKeyParams;
|
||||
try {
|
||||
createAuthenticationKeyFromPKCS8(privKeyFileContents, pubKeyParams,
|
||||
allKeyParams);
|
||||
} catch (Botan::Exception &) {
|
||||
createAuthenticationKeyFromOpenSSL(privKeyFileContents, pubKeyParams,
|
||||
allKeyParams);
|
||||
QString error1;
|
||||
QString error2;
|
||||
if (!createAuthenticationKeyFromPKCS8(privKeyFileContents, pubKeyParams, allKeyParams, error1)
|
||||
&& !createAuthenticationKeyFromOpenSSL(privKeyFileContents, pubKeyParams, allKeyParams,
|
||||
error2)) {
|
||||
#ifdef CREATOR_SSH_DEBUG
|
||||
qDebug("%s: %s\n\t%s\n", Q_FUNC_INFO, qPrintable(error1), qPrintable(error2));
|
||||
#endif
|
||||
throw SshClientException(SshKeyFileError, SSH_TR("Decoding of private key file failed: "
|
||||
"Format not understood."));
|
||||
}
|
||||
|
||||
foreach (const BigInt &b, allKeyParams) {
|
||||
if (b.is_zero()) {
|
||||
throw SshClientException(SshKeyFileError,
|
||||
SSH_TR("Decoding of private key file failed."));
|
||||
SSH_TR("Decoding of private key file failed: Invalid zero parameter."));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -221,12 +225,12 @@ void SshEncryptionFacility::createAuthenticationKey(const QByteArray &privKeyFil
|
||||
m_cachedPrivKeyContents = privKeyFileContents;
|
||||
}
|
||||
|
||||
void SshEncryptionFacility::createAuthenticationKeyFromPKCS8(const QByteArray &privKeyFileContents,
|
||||
QList<BigInt> &pubKeyParams, QList<BigInt> &allKeyParams)
|
||||
bool SshEncryptionFacility::createAuthenticationKeyFromPKCS8(const QByteArray &privKeyFileContents,
|
||||
QList<BigInt> &pubKeyParams, QList<BigInt> &allKeyParams, QString &error)
|
||||
{
|
||||
try {
|
||||
Pipe pipe;
|
||||
pipe.process_msg(convertByteArray(privKeyFileContents),
|
||||
privKeyFileContents.size());
|
||||
pipe.process_msg(convertByteArray(privKeyFileContents), privKeyFileContents.size());
|
||||
Private_Key * const key = PKCS8::load_key(pipe, m_rng, SshKeyPasswordRetriever());
|
||||
if (DSA_PrivateKey * const dsaKey = dynamic_cast<DSA_PrivateKey *>(key)) {
|
||||
m_authKeyAlgoName = SshCapabilities::PubKeyDss;
|
||||
@@ -241,13 +245,20 @@ void SshEncryptionFacility::createAuthenticationKeyFromPKCS8(const QByteArray &p
|
||||
allKeyParams << pubKeyParams << rsaKey->get_p() << rsaKey->get_q()
|
||||
<< rsaKey->get_d();
|
||||
} else {
|
||||
throw Botan::Exception();
|
||||
qWarning("%s: Unexpected code flow, expected success or exception.", Q_FUNC_INFO);
|
||||
return false;
|
||||
}
|
||||
} catch (const Botan::Exception &ex) {
|
||||
error = QLatin1String(ex.what());
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void SshEncryptionFacility::createAuthenticationKeyFromOpenSSL(const QByteArray &privKeyFileContents,
|
||||
QList<BigInt> &pubKeyParams, QList<BigInt> &allKeyParams)
|
||||
bool SshEncryptionFacility::createAuthenticationKeyFromOpenSSL(const QByteArray &privKeyFileContents,
|
||||
QList<BigInt> &pubKeyParams, QList<BigInt> &allKeyParams, QString &error)
|
||||
{
|
||||
try {
|
||||
bool syntaxOk = true;
|
||||
QList<QByteArray> lines = privKeyFileContents.split('\n');
|
||||
while (lines.last().isEmpty())
|
||||
@@ -268,8 +279,8 @@ void SshEncryptionFacility::createAuthenticationKeyFromOpenSSL(const QByteArray
|
||||
syntaxOk = false;
|
||||
}
|
||||
if (!syntaxOk) {
|
||||
throw SshClientException(SshKeyFileError,
|
||||
SSH_TR("Private key file has unexpected format."));
|
||||
error = SSH_TR("Unexpected format.");
|
||||
return false;
|
||||
}
|
||||
|
||||
QByteArray privateKeyBlob;
|
||||
@@ -277,30 +288,26 @@ void SshEncryptionFacility::createAuthenticationKeyFromOpenSSL(const QByteArray
|
||||
privateKeyBlob += lines.at(i);
|
||||
privateKeyBlob = QByteArray::fromBase64(privateKeyBlob);
|
||||
|
||||
BER_Decoder decoder(convertByteArray(privateKeyBlob),
|
||||
privateKeyBlob.size());
|
||||
BER_Decoder decoder(convertByteArray(privateKeyBlob), privateKeyBlob.size());
|
||||
BER_Decoder sequence = decoder.start_cons(SEQUENCE);
|
||||
quint32 version;
|
||||
sequence.decode (version);
|
||||
if (version != 0) {
|
||||
throw SshClientException(SshKeyFileError,
|
||||
SSH_TR("Private key encoding has version %1, expected 0.")
|
||||
.arg(version));
|
||||
error = SSH_TR("Key encoding has version %1, expected 0.").arg(version);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (m_authKeyAlgoName == SshCapabilities::PubKeyDss) {
|
||||
BigInt p, q, g, y, x;
|
||||
sequence.decode (p).decode (q).decode (g).decode (y).decode (x);
|
||||
DSA_PrivateKey * const dsaKey
|
||||
= new DSA_PrivateKey(m_rng, DL_Group(p, q, g), x);
|
||||
DSA_PrivateKey * const dsaKey = new DSA_PrivateKey(m_rng, DL_Group(p, q, g), x);
|
||||
m_authKey.reset(dsaKey);
|
||||
pubKeyParams << p << q << g << y;
|
||||
allKeyParams << pubKeyParams << x;
|
||||
} else {
|
||||
BigInt p, q, e, d, n;
|
||||
sequence.decode(n).decode(e).decode(d).decode(p).decode(q);
|
||||
RSA_PrivateKey * const rsaKey
|
||||
= new RSA_PrivateKey (m_rng, p, q, e, d, n);
|
||||
RSA_PrivateKey * const rsaKey = new RSA_PrivateKey(m_rng, p, q, e, d, n);
|
||||
m_authKey.reset(rsaKey);
|
||||
pubKeyParams << e << n;
|
||||
allKeyParams << pubKeyParams << p << q << d;
|
||||
@@ -308,6 +315,11 @@ void SshEncryptionFacility::createAuthenticationKeyFromOpenSSL(const QByteArray
|
||||
|
||||
sequence.discard_remaining();
|
||||
sequence.verify_end();
|
||||
} catch (const Botan::Exception &ex) {
|
||||
error = QLatin1String(ex.what());
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
QByteArray SshEncryptionFacility::authenticationAlgorithmName() const
|
||||
|
||||
@@ -118,10 +118,10 @@ private:
|
||||
virtual char keyChar() const { return 'C'; }
|
||||
virtual char macChar() const { return 'E'; }
|
||||
|
||||
void createAuthenticationKeyFromPKCS8(const QByteArray &privKeyFileContents,
|
||||
QList<Botan::BigInt> &pubKeyParams, QList<Botan::BigInt> &allKeyParams);
|
||||
void createAuthenticationKeyFromOpenSSL(const QByteArray &privKeyFileContents,
|
||||
QList<Botan::BigInt> &pubKeyParams, QList<Botan::BigInt> &allKeyParams);
|
||||
bool createAuthenticationKeyFromPKCS8(const QByteArray &privKeyFileContents,
|
||||
QList<Botan::BigInt> &pubKeyParams, QList<Botan::BigInt> &allKeyParams, QString &error);
|
||||
bool createAuthenticationKeyFromOpenSSL(const QByteArray &privKeyFileContents,
|
||||
QList<Botan::BigInt> &pubKeyParams, QList<Botan::BigInt> &allKeyParams, QString &error);
|
||||
|
||||
static const QByteArray PrivKeyFileStartLineRsa;
|
||||
static const QByteArray PrivKeyFileStartLineDsa;
|
||||
|
||||
Reference in New Issue
Block a user