From e6a61b8da788efbbbb0eb690c49434b6b5fc9741 Mon Sep 17 00:00:00 2001 From: Eelco Dolstra Date: Thu, 8 Dec 2016 15:31:27 +0100 Subject: [PATCH] Fix S3BinaryCacheStore MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit It failed with AWS error uploading ā€˜6gaxphsyhg66mz0a00qghf9nqf7majs2.ls.xzā€™: Unable to parse ExceptionName: MissingContentLength Message: You must provide the Content-Length HTTP header. possibly because the istringstream_nocopy introduced in 0d2ebb4373e509521f27a6e8f16bfd39d05b2188 doesn't supply the seek method that the AWS library expects. So bring back the old version, but only for S3BinaryCacheStore. --- src/libstore/derivations.cc | 2 +- src/libstore/s3-binary-cache-store.cc | 9 +++++ src/libutil/hash.cc | 2 +- src/libutil/util.hh | 51 --------------------------- 4 files changed, 11 insertions(+), 53 deletions(-) diff --git a/src/libstore/derivations.cc b/src/libstore/derivations.cc index 5562d4689..d934bda38 100644 --- a/src/libstore/derivations.cc +++ b/src/libstore/derivations.cc @@ -155,7 +155,7 @@ static StringSet parseStrings(std::istream & str, bool arePaths) static Derivation parseDerivation(const string & s) { Derivation drv; - istringstream_nocopy str(s); + std::istringstream str(s); expect(str, "Derive(["); /* Parse the list of outputs. */ diff --git a/src/libstore/s3-binary-cache-store.cc b/src/libstore/s3-binary-cache-store.cc index 1bc8576a8..3c5101f00 100644 --- a/src/libstore/s3-binary-cache-store.cc +++ b/src/libstore/s3-binary-cache-store.cc @@ -18,6 +18,15 @@ namespace nix { +struct istringstream_nocopy : public std::stringstream +{ + istringstream_nocopy(const std::string & s) + { + rdbuf()->pubsetbuf( + (char *) s.data(), s.size()); + } +}; + struct S3Error : public Error { Aws::S3::S3Errors err; diff --git a/src/libutil/hash.cc b/src/libutil/hash.cc index 49e781980..81aced0fd 100644 --- a/src/libutil/hash.cc +++ b/src/libutil/hash.cc @@ -106,7 +106,7 @@ Hash parseHash(HashType ht, const string & s) string s2(s, i * 2, 2); if (!isxdigit(s2[0]) || !isxdigit(s2[1])) throw BadHash(format("invalid hash ā€˜%1%ā€™") % s); - istringstream_nocopy str(s2); + std::istringstream str(s2); int n; str >> std::hex >> n; hash.hash[i] = n; diff --git a/src/libutil/util.hh b/src/libutil/util.hh index 1ede48a65..50b96f7ed 100644 --- a/src/libutil/util.hh +++ b/src/libutil/util.hh @@ -431,55 +431,4 @@ void callSuccess( } -/* A variant of std::istringstream that doesn't copy its string - argument. This is useful for large strings. The caller must ensure - that the string object is not destroyed while it's referenced by - this object. */ -class istringbuf_nocopy : public std::streambuf -{ - const std::string & s; - decltype(s.size()) off; - decltype(s.size()) size; -public: - istringbuf_nocopy(const std::string & s) : s{s}, off{0}, size{s.size()} - { - } - -private: - int_type underflow() - { - if (off == size) - return traits_type::eof(); - return traits_type::to_int_type(s[off]); - } - - int_type uflow() - { - if (off == size) - return traits_type::eof(); - return traits_type::to_int_type(s[off++]); - } - - int_type pbackfail(int_type ch) - { - if (off == 0 || (ch != traits_type::eof() && ch != s[off - 1])) - return traits_type::eof(); - - return traits_type::to_int_type(s[--off]); - } - - std::streamsize showmanyc() - { - return size - off; - } -}; - - -struct istringstream_nocopy : public std::iostream -{ - istringbuf_nocopy buf; - istringstream_nocopy(const std::string & s) : std::iostream(&buf), buf(s) {}; -}; - - }