diff options
author | moneromooo-monero <moneromooo-monero@users.noreply.github.com> | 2017-11-25 14:50:15 +0000 |
---|---|---|
committer | moneromooo-monero <moneromooo-monero@users.noreply.github.com> | 2017-11-27 22:25:57 +0000 |
commit | 3dffe71b72c3b5dd1246ed74ee4cd1ad89aaccfa (patch) | |
tree | 5559bcf502288a62f34e17902de92fcc2c60f110 /contrib | |
parent | utils: initialize easylogging++ in on_startup (diff) | |
download | monero-3dffe71b72c3b5dd1246ed74ee4cd1ad89aaccfa.tar.xz |
new wipeable_string class to replace std::string passphrases
Diffstat (limited to 'contrib')
-rw-r--r-- | contrib/epee/include/net/http_auth.h | 6 | ||||
-rw-r--r-- | contrib/epee/include/wipeable_string.h | 70 | ||||
-rw-r--r-- | contrib/epee/src/CMakeLists.txt | 2 | ||||
-rw-r--r-- | contrib/epee/src/http_auth.cpp | 8 | ||||
-rw-r--r-- | contrib/epee/src/wipeable_string.cpp | 146 |
5 files changed, 228 insertions, 4 deletions
diff --git a/contrib/epee/include/net/http_auth.h b/contrib/epee/include/net/http_auth.h index bf368e6f4..841cebc17 100644 --- a/contrib/epee/include/net/http_auth.h +++ b/contrib/epee/include/net/http_auth.h @@ -33,7 +33,7 @@ #include <functional> #include <string> #include <utility> - +#include "wipeable_string.h" #include "http_base.h" #undef MONERO_DEFAULT_LOG_CATEGORY @@ -48,12 +48,12 @@ namespace net_utils struct login { login() : username(), password() {} - login(std::string username_, std::string password_) + login(std::string username_, wipeable_string password_) : username(std::move(username_)), password(std::move(password_)) {} std::string username; - std::string password; + wipeable_string password; }; //! Implements RFC 2617 digest auth. Digests from RFC 7616 can be added. diff --git a/contrib/epee/include/wipeable_string.h b/contrib/epee/include/wipeable_string.h new file mode 100644 index 000000000..66d3e8e2b --- /dev/null +++ b/contrib/epee/include/wipeable_string.h @@ -0,0 +1,70 @@ +// Copyright (c) 2017, The Monero Project +// +// All rights reserved. +// +// Redistribution and use in source and binary forms, with or without modification, are +// permitted provided that the following conditions are met: +// +// 1. Redistributions of source code must retain the above copyright notice, this list of +// conditions and the following disclaimer. +// +// 2. Redistributions in binary form must reproduce the above copyright notice, this list +// of conditions and the following disclaimer in the documentation and/or other +// materials provided with the distribution. +// +// 3. Neither the name of the copyright holder nor the names of its contributors may be +// used to endorse or promote products derived from this software without specific +// prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY +// EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF +// MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL +// THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, +// PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS +// INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, +// STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF +// THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +#pragma once + +#include <stddef.h> +#include <vector> +#include <string> + +namespace epee +{ + class wipeable_string + { + public: + wipeable_string() {} + wipeable_string(const wipeable_string &other); + wipeable_string(wipeable_string &&other); + wipeable_string(const std::string &other); + wipeable_string(std::string &&other); + wipeable_string(const char *s); + ~wipeable_string(); + void wipe(); + void push_back(char c); + void pop_back(); + const char *data() const noexcept { return buffer.data(); } + size_t size() const noexcept { return buffer.size(); } + bool empty() const noexcept { return buffer.empty(); } + void resize(size_t sz); + void reserve(size_t sz); + void clear(); + bool operator==(const wipeable_string &other) const noexcept { return buffer == other.buffer; } + bool operator!=(const wipeable_string &other) const noexcept { return buffer != other.buffer; } + wipeable_string &operator=(wipeable_string &&other); + wipeable_string &operator=(const wipeable_string &other); + + static void set_wipe(void *(*f)(void*, size_t)) { wipefunc = f; } + + private: + void grow(size_t sz, size_t reserved = 0); + + private: + std::vector<char> buffer; + static void *(*wipefunc)(void*, size_t); + }; +} diff --git a/contrib/epee/src/CMakeLists.txt b/contrib/epee/src/CMakeLists.txt index bd6714791..5cd6d7813 100644 --- a/contrib/epee/src/CMakeLists.txt +++ b/contrib/epee/src/CMakeLists.txt @@ -26,7 +26,7 @@ # STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF # THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -add_library(epee STATIC hex.cpp http_auth.cpp mlog.cpp net_utils_base.cpp string_tools.cpp) +add_library(epee STATIC hex.cpp http_auth.cpp mlog.cpp net_utils_base.cpp string_tools.cpp wipeable_string.cpp) if (USE_READLINE AND GNU_READLINE_FOUND) add_library(epee_readline STATIC readline_buffer.cpp) endif() diff --git a/contrib/epee/src/http_auth.cpp b/contrib/epee/src/http_auth.cpp index 30e562700..f06f05528 100644 --- a/contrib/epee/src/http_auth.cpp +++ b/contrib/epee/src/http_auth.cpp @@ -125,6 +125,14 @@ namespace { (*this)(boost::string_ref(arg)); } + void operator()(const epee::wipeable_string& arg) const + { + md5::MD5Update( + std::addressof(ctx), + reinterpret_cast<const std::uint8_t*>(arg.data()), + arg.size() + ); + } md5::MD5_CTX& ctx; }; diff --git a/contrib/epee/src/wipeable_string.cpp b/contrib/epee/src/wipeable_string.cpp new file mode 100644 index 000000000..75191df71 --- /dev/null +++ b/contrib/epee/src/wipeable_string.cpp @@ -0,0 +1,146 @@ +// Copyright (c) 2017, The Monero Project +// +// All rights reserved. +// +// Redistribution and use in source and binary forms, with or without modification, are +// permitted provided that the following conditions are met: +// +// 1. Redistributions of source code must retain the above copyright notice, this list of +// conditions and the following disclaimer. +// +// 2. Redistributions in binary form must reproduce the above copyright notice, this list +// of conditions and the following disclaimer in the documentation and/or other +// materials provided with the distribution. +// +// 3. Neither the name of the copyright holder nor the names of its contributors may be +// used to endorse or promote products derived from this software without specific +// prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY +// EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF +// MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL +// THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, +// PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS +// INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, +// STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF +// THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +#include <string.h> +#include "misc_log_ex.h" +#include "wipeable_string.h" + +namespace epee +{ + +void *(*wipeable_string::wipefunc)(void*, size_t) = NULL; + +wipeable_string::wipeable_string(const wipeable_string &other): + buffer(other.buffer) +{ +} + +wipeable_string::wipeable_string(wipeable_string &&other) +{ + if (&other == this) + return; + buffer = std::move(other.buffer); +} + +wipeable_string::wipeable_string(const std::string &other) +{ + grow(other.size()); + memcpy(buffer.data(), other.c_str(), size()); +} + +wipeable_string::wipeable_string(std::string &&other) +{ + CHECK_AND_ASSERT_THROW_MES(wipefunc, "wipefunc is not set"); + grow(other.size()); + memcpy(buffer.data(), other.c_str(), size()); + if (!other.empty()) + { + wipefunc(&other[0], other.size()); // we're kinda left with this again aren't we + other = std::string(); + } +} + +wipeable_string::wipeable_string(const char *s) +{ + grow(strlen(s)); + memcpy(buffer.data(), s, size()); +} + +wipeable_string::~wipeable_string() +{ + wipe(); +} + +void wipeable_string::wipe() +{ + CHECK_AND_ASSERT_THROW_MES(wipefunc, "wipefunc is not set"); + wipefunc(buffer.data(), buffer.size() * sizeof(char)); +} + +void wipeable_string::grow(size_t sz, size_t reserved) +{ + CHECK_AND_ASSERT_THROW_MES(wipefunc, "wipefunc is not set"); + if (reserved == 0) + reserved = sz; + CHECK_AND_ASSERT_THROW_MES(reserved >= sz, "reserved < sz"); + if (reserved <= buffer.capacity()) + return; + size_t old_sz = buffer.size(); + std::unique_ptr<char[]> tmp{new char[old_sz]}; + memcpy(tmp.get(), buffer.data(), old_sz * sizeof(char)); + wipefunc(buffer.data(), old_sz * sizeof(char)); + buffer.reserve(reserved); + buffer.resize(sz); + memcpy(buffer.data(), tmp.get(), sz * sizeof(char)); + wipefunc(tmp.get(), old_sz * sizeof(char)); +} + +void wipeable_string::push_back(char c) +{ + grow(size() + 1); + buffer.push_back(c); +} + +void wipeable_string::pop_back() +{ + resize(size() - 1); +} + +void wipeable_string::resize(size_t sz) +{ + CHECK_AND_ASSERT_THROW_MES(wipefunc, "wipefunc is not set"); + if (sz < buffer.size()) + wipefunc(buffer.data() + sz, buffer.size() - sz); + grow(sz); +} + +void wipeable_string::reserve(size_t sz) +{ + grow(size(), sz); +} + +void wipeable_string::clear() +{ + resize(0); +} + +wipeable_string &wipeable_string::operator=(wipeable_string &&other) +{ + if (&other != this) + buffer = std::move(other.buffer); + return *this; +} + +wipeable_string &wipeable_string::operator=(const wipeable_string &other) +{ + if (&other != this) + buffer = other.buffer; + return *this; +} + +} |