diff --git a/domain-server/src/DomainServer.cpp b/domain-server/src/DomainServer.cpp index c164c9bc00..706307dd70 100644 --- a/domain-server/src/DomainServer.cpp +++ b/domain-server/src/DomainServer.cpp @@ -651,14 +651,14 @@ void DomainServer::processConnectRequestPacket(QSharedPointer packet) // if username is empty, don't attempt to unpack username signature if(isRestrictingAccess) { if (!username.isEmpty()) { - qDebug() << "Reading username signature."; + packetStream >> usernameSignature; if(usernameSignature.isEmpty()) { // if user didn't include username and usernameSignature in connect request, send a connectionToken packet QUuid& connectionToken = _connectionTokenHash[username.toLower()]; - if(connectionToken.isNull()) { + if (connectionToken.isNull()) { connectionToken = QUuid::createUuid(); } @@ -667,14 +667,12 @@ void DomainServer::processConnectRequestPacket(QSharedPointer packet) connectionTokenPacket->write(connectionToken.toRfc4122()); limitedNodeList->sendUnreliablePacket(*connectionTokenPacket, packet->getSenderSockAddr()); - qDebug() << "Sending connection token. " << _connectionTokenHash[username.toLower()]; + qDebug() << "Sending connectionToken packet with connectionUUID " << _connectionTokenHash[username.toLower()]; return; } - } - } QString reason; @@ -820,7 +818,6 @@ bool DomainServer::verifyUserSignature(const QString& username, QByteArray publicKeyArray = _userPublicKeys.value(username); QUuid connectionToken = _connectionTokenHash.value(username.toLower()); - qDebug() << "Pulling out connection token. " << connectionToken; if (!publicKeyArray.isEmpty() && !connectionToken.isNull()) { // if we do have a public key for the user, check for a signature match @@ -830,46 +827,37 @@ bool DomainServer::verifyUserSignature(const QString& username, // first load up the public key into an RSA struct RSA* rsaPublicKey = d2i_RSA_PUBKEY(NULL, &publicKeyData, publicKeyArray.size()); - qDebug() << "Signature: " << usernameSignature.toHex(); + //qDebug() << "Verifying signature: " << usernameSignature.toHex(); + + QByteArray lowercaseUsername = username.toLower().toUtf8(); + QByteArray usernameWithToken = QCryptographicHash::hash(lowercaseUsername.append(connectionToken.toRfc4122()), QCryptographicHash::Sha256); if (rsaPublicKey) { QByteArray decryptedArray(RSA_size(rsaPublicKey), 0); int decryptResult = - RSA_public_decrypt(usernameSignature.size(), - reinterpret_cast(usernameSignature.constData()), - reinterpret_cast(decryptedArray.data()), - rsaPublicKey, RSA_PKCS1_PADDING); + RSA_verify(NID_sha256, reinterpret_cast(usernameWithToken.constData()), usernameWithToken.size(), reinterpret_cast(usernameSignature.constData()), usernameSignature.size(), rsaPublicKey); - QByteArray lowercaseUsername = username.toLower().toUtf8(); - QByteArray usernameWithToken = QCryptographicHash::hash(lowercaseUsername.append(connectionToken.toRfc4122()), QCryptographicHash::Sha256); int err = ERR_get_error(); - qDebug() << "Error: " << err; + qDebug() << "Decrypt result: " << decryptResult << " Error: " << err; - if (decryptResult != -1) { - if (usernameWithToken == decryptedArray) { - qDebug() << "Username signature matches for" << username << "- allowing connection."; + if (decryptResult == 1) { + qDebug() << "Username signature matches for" << username << "- allowing connection."; - // free up the public key before we return - RSA_free(rsaPublicKey); + // free up the public key before we return + RSA_free(rsaPublicKey); - // remove the username's connection token from the hash - _connectionTokenHash.remove(username); + // remove the username's connection token from the hash + _connectionTokenHash.remove(username); - return true; - } else { - qDebug() << "Username signature did not match for" << username << "- denying connection."; - reasonReturn = "Username signature did not match."; - } + return true; } else { - qDebug() << "Couldn't decrypt user signature for" << username << "- denying connection."; - reasonReturn = "Couldn't decrypt user signature."; - + qDebug() << "Error decrypting username signature for " << username << "- denying connection."; + reasonReturn = "Error decrypting username signature."; + // free up the public key, we don't need it anymore + RSA_free(rsaPublicKey); } - // free up the public key, we don't need it anymore - RSA_free(rsaPublicKey); - } else { // we can't let this user in since we couldn't convert their public key to an RSA key we could use diff --git a/libraries/networking/src/DataServerAccountInfo.cpp b/libraries/networking/src/DataServerAccountInfo.cpp index de647d09c4..0d38de7cf0 100644 --- a/libraries/networking/src/DataServerAccountInfo.cpp +++ b/libraries/networking/src/DataServerAccountInfo.cpp @@ -10,6 +10,7 @@ // #include +#include #include #include @@ -30,8 +31,7 @@ DataServerAccountInfo::DataServerAccountInfo() : _walletID(), _balance(0), _hasBalance(false), - _privateKey(), - _usernameSignature() + _privateKey() { } @@ -73,9 +73,6 @@ void DataServerAccountInfo::setAccessTokenFromJSON(const QJsonObject& jsonObject void DataServerAccountInfo::setUsername(const QString& username) { if (_username != username) { _username = username; - - // clear our username signature so it has to be re-created - _usernameSignature = QByteArray(); qCDebug(networking) << "Username changed to" << username; } @@ -138,13 +135,10 @@ QByteArray DataServerAccountInfo::getUsernameSignature(const QUuid& connectionTo if (rsaPrivateKey) { QByteArray lowercaseUsername = _username.toLower().toUtf8(); QByteArray usernameWithToken = QCryptographicHash::hash(lowercaseUsername.append(connectionToken.toRfc4122()), QCryptographicHash::Sha256); - QByteArray usernameSignature(RSA_size(rsaPrivateKey), 0); - - int encryptReturn = RSA_private_encrypt(usernameWithToken.size(), - reinterpret_cast(usernameWithToken.constData()), - reinterpret_cast(usernameSignature.data()), - rsaPrivateKey, RSA_PKCS1_PADDING); + QByteArray usernameSignature(RSA_size(rsaPrivateKey), 0); + unsigned int usernameSignatureSize = 0; + int encryptReturn = RSA_sign(NID_sha256, reinterpret_cast(usernameWithToken.constData()), usernameWithToken.size(), reinterpret_cast(usernameSignature.data()), &usernameSignatureSize, rsaPrivateKey); // free the private key RSA struct now that we are done with it RSA_free(rsaPrivateKey); @@ -154,7 +148,6 @@ QByteArray DataServerAccountInfo::getUsernameSignature(const QUuid& connectionTo qCDebug(networking) << "Will re-attempt on next domain-server check in."; } else { qDebug(networking) << "Signing username with connectionUUID " << connectionToken; - qDebug() << "Signature: " << usernameSignature.toHex(); return usernameSignature; } @@ -169,8 +162,6 @@ QByteArray DataServerAccountInfo::getUsernameSignature(const QUuid& connectionTo void DataServerAccountInfo::setPrivateKey(const QByteArray& privateKey) { _privateKey = privateKey; - // clear our username signature so it has to be re-created - _usernameSignature = QByteArray(); } QDataStream& operator<<(QDataStream &out, const DataServerAccountInfo& info) { diff --git a/libraries/networking/src/DataServerAccountInfo.h b/libraries/networking/src/DataServerAccountInfo.h index 0d8157ccf3..9b80de5422 100644 --- a/libraries/networking/src/DataServerAccountInfo.h +++ b/libraries/networking/src/DataServerAccountInfo.h @@ -73,7 +73,7 @@ private: qint64 _balance; bool _hasBalance; QByteArray _privateKey; - QByteArray _usernameSignature; + }; #endif // hifi_DataServerAccountInfo_h diff --git a/libraries/networking/src/NodeList.cpp b/libraries/networking/src/NodeList.cpp index 13224ca5bc..e8c92e37e3 100644 --- a/libraries/networking/src/NodeList.cpp +++ b/libraries/networking/src/NodeList.cpp @@ -289,6 +289,7 @@ void NodeList::sendDomainServerCheckIn() { QByteArray usernameSignature = AccountManager::getInstance().getAccountInfo().getUsernameSignature(connectionToken); if (!usernameSignature.isEmpty()) { + qDebug() << "Sending signature to packet stream " << usernameSignature.toHex(); packetStream << usernameSignature; } } @@ -463,6 +464,7 @@ void NodeList::processDomainServerConnectionTokenPacket(QSharedPointer // refuse to process this packet if we aren't currently connected to the DS return; } + qDebug() << "Setting connection token and sending domain server checkin"; // read in the connection token from the packet, then send domain-server checkin _domainHandler.setConnectionToken(QUuid::fromRfc4122(packet->read(NUM_BYTES_RFC4122_UUID))); sendDomainServerCheckIn();