From 7da68ff72d5b0cb0cdd969bd7b44d62da38f6b0e Mon Sep 17 00:00:00 2001 From: csoler Date: Sun, 22 Jan 2017 21:44:26 +0100 Subject: [PATCH] improved certificate parsing in Home so that corrupted certs never get accepted --- libretroshare/src/pgp/rscertificate.cc | 17 ++++++++++-- libretroshare/src/pgp/rscertificate.h | 2 +- libretroshare/src/rsserver/p3peers.cc | 2 +- .../src/gui/connect/ConnectFriendWizard.cpp | 27 +++++++++++-------- 4 files changed, 33 insertions(+), 15 deletions(-) diff --git a/libretroshare/src/pgp/rscertificate.cc b/libretroshare/src/pgp/rscertificate.cc index 9f78a78de..b29952c91 100644 --- a/libretroshare/src/pgp/rscertificate.cc +++ b/libretroshare/src/pgp/rscertificate.cc @@ -431,12 +431,25 @@ unsigned short RsCertificate::loc_port_us() const return (int)ipv4_internal_ip_and_port[4]*256 + (int)ipv4_internal_ip_and_port[5] ; } -bool RsCertificate::cleanCertificate(const std::string& input,std::string& output,Format& format,int& error_code) +bool RsCertificate::cleanCertificate(const std::string& input,std::string& output,Format& format,int& error_code,bool check_content) { if(cleanCertificate(input,output,error_code)) { format = RS_CERTIFICATE_RADIX ; - return true ; + + if(!check_content) + return true ; + + try + { + RsCertificate c(input) ; + return true ; + } + catch(uint32_t err_code) + { + error_code = err_code ; + return false; + } } return false ; diff --git a/libretroshare/src/pgp/rscertificate.h b/libretroshare/src/pgp/rscertificate.h index 1c25cf6b4..7f206d904 100644 --- a/libretroshare/src/pgp/rscertificate.h +++ b/libretroshare/src/pgp/rscertificate.h @@ -41,7 +41,7 @@ class RsCertificate const unsigned char *pgp_key() const { return binary_pgp_key ; } size_t pgp_key_size() const { return binary_pgp_key_size ; } - static bool cleanCertificate(const std::string& input,std::string& output,RsCertificate::Format& format,int& error_code) ; + static bool cleanCertificate(const std::string& input, std::string& output, RsCertificate::Format& format, int& error_code, bool check_content) ; private: static bool cleanCertificate(const std::string& input,std::string& output,int&) ; // new radix format diff --git a/libretroshare/src/rsserver/p3peers.cc b/libretroshare/src/rsserver/p3peers.cc index d4b5fe332..c46f4398b 100644 --- a/libretroshare/src/rsserver/p3peers.cc +++ b/libretroshare/src/rsserver/p3peers.cc @@ -1214,7 +1214,7 @@ bool p3Peers::cleanCertificate(const std::string &certstr, std::string &cleanCer { RsCertificate::Format format ; - return RsCertificate::cleanCertificate(certstr,cleanCert,format,error_code) ; + return RsCertificate::cleanCertificate(certstr,cleanCert,format,error_code,true) ; } bool p3Peers::saveCertificateToFile(const RsPeerId &id, const std::string &/*fname*/) diff --git a/retroshare-gui/src/gui/connect/ConnectFriendWizard.cpp b/retroshare-gui/src/gui/connect/ConnectFriendWizard.cpp index e69b46278..03f54329c 100755 --- a/retroshare-gui/src/gui/connect/ConnectFriendWizard.cpp +++ b/retroshare-gui/src/gui/connect/ConnectFriendWizard.cpp @@ -962,13 +962,14 @@ void ConnectFriendWizard::friendCertChanged() void ConnectFriendWizard::cleanFriendCert() { bool certValid = false; - QString errorMsg; + QString errorMsg ; std::string cert = ui->friendCertEdit->toPlainText().toUtf8().constData(); if (cert.empty()) { ui->friendCertCleanLabel->setPixmap(QPixmap(":/images/delete.png")); ui->friendCertCleanLabel->setToolTip(""); ui->friendCertCleanLabel->setStyleSheet(""); + errorMsg = tr(""); } else { std::string cleanCert; @@ -984,23 +985,27 @@ void ConnectFriendWizard::cleanFriendCert() ui->friendCertCleanLabel->setStyleSheet(""); connect(ui->friendCertEdit, SIGNAL(textChanged()), this, SLOT(friendCertChanged())); } + errorMsg = tr("Certificate appears to be valid"); + ui->friendCertCleanLabel->setPixmap(QPixmap(":/images/accepted16.png")); } else { if (error_code > 0) { switch (error_code) { - case RS_PEER_CERT_CLEANING_CODE_NO_BEGIN_TAG: - errorMsg = tr("No or misspelled BEGIN tag found") ; - break ; - case RS_PEER_CERT_CLEANING_CODE_NO_END_TAG: - errorMsg = tr("No or misspelled END tag found") ; - break ; - case RS_PEER_CERT_CLEANING_CODE_NO_CHECKSUM: - errorMsg = tr("No checksum found (the last 5 chars should be separated by a '=' char), or no newline after tag line (e.g. line beginning with Version:)") ; - break ; + case CERTIFICATE_PARSING_ERROR_CHECKSUM_ERROR : + case CERTIFICATE_PARSING_ERROR_WRONG_VERSION : + case CERTIFICATE_PARSING_ERROR_SIZE_ERROR : + case CERTIFICATE_PARSING_ERROR_INVALID_LOCATION_ID : + case CERTIFICATE_PARSING_ERROR_INVALID_EXTERNAL_IP : + case CERTIFICATE_PARSING_ERROR_INVALID_LOCAL_IP : + case CERTIFICATE_PARSING_ERROR_INVALID_CHECKSUM_SECTION : + case CERTIFICATE_PARSING_ERROR_UNKNOWN_SECTION_PTAG : + case CERTIFICATE_PARSING_ERROR_MISSING_CHECKSUM : + default: - errorMsg = tr("Fake certificate: take any real certificate, and replace some of the letters randomly") ; + errorMsg = tr("Not a valid Retroshare certificate!") ; ui->friendCertCleanLabel->setStyleSheet("QLabel#friendCertCleanLabel {border: 2px solid red; border-radius: 6px;}"); } } + ui->friendCertCleanLabel->setPixmap(QPixmap(":/images/delete.png")); } }