From c144c3562cd786f24b8d25444a823eb8ca09995a Mon Sep 17 00:00:00 2001 From: Thomas Geymayer Date: Wed, 18 Jun 2014 18:07:42 +0200 Subject: [PATCH] Keep md5 inside simgear and use single encodeHex implementation. --- simgear/misc/strutils.cxx | 45 +++++++++++++++++++++++++--------- simgear/misc/strutils.hxx | 7 ++++++ simgear/package/CMakeLists.txt | 3 +-- simgear/package/Install.cxx | 16 +++++------- 4 files changed, 47 insertions(+), 24 deletions(-) diff --git a/simgear/misc/strutils.cxx b/simgear/misc/strutils.cxx index bc56100a..c72d0058 100644 --- a/simgear/misc/strutils.cxx +++ b/simgear/misc/strutils.cxx @@ -27,6 +27,7 @@ #include "strutils.hxx" #include +#include using std::string; using std::vector; @@ -401,8 +402,32 @@ std::string convertWindowsLocal8BitToUtf8(const std::string& a) #endif } +//------------------------------------------------------------------------------ +std::string md5(const unsigned char* data, size_t num) +{ + SG_MD5_CTX md5_ctx; + SG_MD5Init(&md5_ctx); + SG_MD5Update(&md5_ctx, data, num); + unsigned char digest[MD5_DIGEST_LENGTH]; + SG_MD5Final(digest, &md5_ctx); + return encodeHex(digest, MD5_DIGEST_LENGTH); +} + +//------------------------------------------------------------------------------ +std::string md5(const char* data, size_t num) +{ + return md5(reinterpret_cast(data), num); +} + +//------------------------------------------------------------------------------ +std::string md5(const std::string& str) +{ + return md5(reinterpret_cast(str.c_str()), str.size()); +} + +//------------------------------------------------------------------------------ static const std::string base64_chars = "ABCDEFGHIJKLMNOPQRSTUVWXYZ" "abcdefghijklmnopqrstuvwxyz" @@ -482,28 +507,24 @@ void decodeBase64(const std::string& encoded_string, std::vector& } } +//------------------------------------------------------------------------------ const char hexChar[] = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f'}; std::string encodeHex(const std::string& bytes) { - std::string hex; - size_t count = bytes.size(); - for (unsigned int i=0; i> 4]); - hex.push_back(hexChar[c & 0x0f]); - } - - return hex; + return encodeHex( + reinterpret_cast(bytes.c_str()), + bytes.size() + ); } std::string encodeHex(const unsigned char* rawBytes, unsigned int length) { - std::string hex; + std::string hex(length * 2, '\0'); for (unsigned int i=0; i> 4]); - hex.push_back(hexChar[c & 0x0f]); + hex[i * 2] = hexChar[c >> 4]; + hex[i * 2 + 1] = hexChar[c & 0x0f]; } return hex; diff --git a/simgear/misc/strutils.hxx b/simgear/misc/strutils.hxx index 9070b246..2b02909e 100644 --- a/simgear/misc/strutils.hxx +++ b/simgear/misc/strutils.hxx @@ -176,6 +176,13 @@ namespace simgear { WCharVec convertUtf8ToWString(const std::string& a); #endif + /** + * Get md5 hash of raw data. + */ + std::string md5(const unsigned char* data, size_t num); + std::string md5(const char* data, size_t num); + std::string md5(const std::string& str); + /** * convert base-64 encoded data to raw bytes (possibly with embedded * NULs). Throws an exception if input data is not base64, or is diff --git a/simgear/package/CMakeLists.txt b/simgear/package/CMakeLists.txt index cc660385..33672680 100644 --- a/simgear/package/CMakeLists.txt +++ b/simgear/package/CMakeLists.txt @@ -7,7 +7,6 @@ set(HEADERS Install.hxx Root.hxx Delegate.hxx - md5.h # TODO expose somehow more elegant (eg. a function accepting a string) ) set(SOURCES @@ -16,7 +15,7 @@ set(SOURCES Install.cxx Root.cxx # internal helpers - md5.c + md5.h md5.c ioapi.c ioapi_mem.c ioapi.h unzip.h unzip.c ) diff --git a/simgear/package/Install.cxx b/simgear/package/Install.cxx index 7d7b2fa9..b5c9487d 100644 --- a/simgear/package/Install.cxx +++ b/simgear/package/Install.cxx @@ -30,6 +30,7 @@ #include #include #include +#include extern "C" { void fill_memory_filefunc (zlib_filefunc_def*); @@ -91,17 +92,12 @@ protected: unsigned char digest[MD5_DIGEST_LENGTH]; SG_MD5Final(digest, &m_md5); - // convert final sum to hex - const char hexChar[] = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f'}; - std::stringstream hexMd5; - for (int i=0; i> 4]; - hexMd5 << hexChar[digest[i] & 0x0f]; - } - - if (hexMd5.str() != m_owner->package()->md5()) { + std::string const hex_md5 = + strutils::encodeHex(digest, MD5_DIGEST_LENGTH); + + if (hex_md5 != m_owner->package()->md5()) { SG_LOG(SG_GENERAL, SG_ALERT, "md5 verification failed:\n" - << "\t" << hexMd5.str() << "\n\t" + << "\t" << hex_md5 << "\n\t" << m_owner->package()->md5() << "\n\t" << "downloading from:" << url()); doFailure(Delegate::FAIL_CHECKSUM); -- 2.39.5