[C++] Refactor StatusOr and StringPiece (#8406)
* [C++] Refactor StatusOr and StringPiece This change makes `StatusOr` and `StringPiece` more like `absl::StatusOr` and `{absl,std}::string_view`. Note that there is more work required before the Abseil types can be used as drop-in replacement. Progress on #3688 * Fix more errors * Fix test * Remove some asserts * Delete outdate example
This commit is contained in:
parent
5941bd1198
commit
4b770cabd7
@ -173,12 +173,8 @@ size_t LimitByteSource::Available() const {
|
||||
}
|
||||
|
||||
StringPiece LimitByteSource::Peek() {
|
||||
StringPiece piece(source_->Peek());
|
||||
if (piece.size() > limit_) {
|
||||
piece.set(piece.data(), limit_);
|
||||
}
|
||||
|
||||
return piece;
|
||||
StringPiece piece = source_->Peek();
|
||||
return StringPiece(piece.data(), std::min(piece.size(), limit_));
|
||||
}
|
||||
|
||||
void LimitByteSource::Skip(size_t n) {
|
||||
|
@ -116,8 +116,7 @@ inline To down_cast(From& f) {
|
||||
|
||||
template<typename To, typename From>
|
||||
inline To bit_cast(const From& from) {
|
||||
GOOGLE_COMPILE_ASSERT(sizeof(From) == sizeof(To),
|
||||
bit_cast_with_different_sizes);
|
||||
static_assert(sizeof(From) == sizeof(To), "bit_cast_with_different_sizes");
|
||||
To dest;
|
||||
memcpy(&dest, &from, sizeof(dest));
|
||||
return dest;
|
||||
|
@ -123,7 +123,6 @@ std::string PROTOBUF_EXPORT VersionString(int version);
|
||||
// ===================================================================
|
||||
// from google3/util/utf8/public/unilib.h
|
||||
|
||||
class StringPiece;
|
||||
namespace internal {
|
||||
|
||||
// Checks if the buffer contains structurally-valid UTF-8. Implemented in
|
||||
|
@ -34,6 +34,7 @@
|
||||
#include <google/protobuf/stubs/macros.h>
|
||||
#include <google/protobuf/stubs/port.h>
|
||||
#include <google/protobuf/stubs/status.h>
|
||||
#include <google/protobuf/stubs/stringpiece.h>
|
||||
|
||||
#include <google/protobuf/port_def.inc>
|
||||
|
||||
@ -64,7 +65,6 @@ enum LogLevel {
|
||||
#endif
|
||||
};
|
||||
|
||||
class StringPiece;
|
||||
class uint128;
|
||||
namespace internal {
|
||||
|
||||
|
@ -31,21 +31,19 @@
|
||||
#ifndef GOOGLE_PROTOBUF_MACROS_H__
|
||||
#define GOOGLE_PROTOBUF_MACROS_H__
|
||||
|
||||
#include <google/protobuf/stubs/port.h>
|
||||
|
||||
namespace google {
|
||||
namespace protobuf {
|
||||
|
||||
#undef GOOGLE_DISALLOW_EVIL_CONSTRUCTORS
|
||||
#define GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(TypeName) \
|
||||
TypeName(const TypeName&); \
|
||||
void operator=(const TypeName&)
|
||||
TypeName(const TypeName&) = delete; \
|
||||
void operator=(const TypeName&) = delete
|
||||
|
||||
#undef GOOGLE_DISALLOW_IMPLICIT_CONSTRUCTORS
|
||||
#define GOOGLE_DISALLOW_IMPLICIT_CONSTRUCTORS(TypeName) \
|
||||
TypeName(); \
|
||||
TypeName(const TypeName&); \
|
||||
void operator=(const TypeName&)
|
||||
TypeName() = delete; \
|
||||
TypeName(const TypeName&) = delete; \
|
||||
void operator=(const TypeName&) = delete
|
||||
|
||||
// ===================================================================
|
||||
// from google3/base/basictypes.h
|
||||
@ -89,31 +87,6 @@ namespace protobuf {
|
||||
((sizeof(a) / sizeof(*(a))) / \
|
||||
static_cast<size_t>(!(sizeof(a) % sizeof(*(a)))))
|
||||
|
||||
// The COMPILE_ASSERT macro can be used to verify that a compile time
|
||||
// expression is true. For example, you could use it to verify the
|
||||
// size of a static array:
|
||||
//
|
||||
// COMPILE_ASSERT(ARRAYSIZE(content_type_names) == CONTENT_NUM_TYPES,
|
||||
// content_type_names_incorrect_size);
|
||||
//
|
||||
// or to make sure a struct is smaller than a certain size:
|
||||
//
|
||||
// COMPILE_ASSERT(sizeof(foo) < 128, foo_too_large);
|
||||
//
|
||||
// The second argument to the macro is the name of the variable. If
|
||||
// the expression is false, most compilers will issue a warning/error
|
||||
// containing the name of the variable.
|
||||
|
||||
namespace internal {
|
||||
|
||||
template <bool>
|
||||
struct CompileAssert {
|
||||
};
|
||||
|
||||
} // namespace internal
|
||||
|
||||
#define GOOGLE_COMPILE_ASSERT(expr, msg) static_assert(expr, #msg)
|
||||
|
||||
} // namespace protobuf
|
||||
} // namespace google
|
||||
|
||||
|
@ -60,7 +60,7 @@ namespace util {
|
||||
template<typename T>
|
||||
Status DoAssignOrReturn(T& lhs, StatusOr<T> result) {
|
||||
if (result.ok()) {
|
||||
lhs = result.ValueOrDie();
|
||||
lhs = result.value();
|
||||
}
|
||||
return result.status();
|
||||
}
|
||||
|
@ -35,14 +35,14 @@
|
||||
namespace google {
|
||||
namespace protobuf {
|
||||
namespace util {
|
||||
namespace internal {
|
||||
namespace statusor_internal {
|
||||
|
||||
void StatusOrHelper::Crash(const Status& status) {
|
||||
GOOGLE_LOG(FATAL) << "Attempting to fetch value instead of handling error "
|
||||
<< status.ToString();
|
||||
}
|
||||
|
||||
} // namespace internal
|
||||
} // namespace statusor_internal
|
||||
} // namespace util
|
||||
} // namespace protobuf
|
||||
} // namespace google
|
||||
|
@ -42,7 +42,7 @@
|
||||
//
|
||||
// StatusOr<float> result = DoBigCalculationThatCouldFail();
|
||||
// if (result.ok()) {
|
||||
// float answer = result.ValueOrDie();
|
||||
// float answer = result.value();
|
||||
// printf("Big calculation yielded: %f", answer);
|
||||
// } else {
|
||||
// LOG(ERROR) << result.status();
|
||||
@ -52,17 +52,7 @@
|
||||
//
|
||||
// StatusOr<Foo*> result = FooFactory::MakeNewFoo(arg);
|
||||
// if (result.ok()) {
|
||||
// std::unique_ptr<Foo> foo(result.ValueOrDie());
|
||||
// foo->DoSomethingCool();
|
||||
// } else {
|
||||
// LOG(ERROR) << result.status();
|
||||
// }
|
||||
//
|
||||
// Example client usage for a StatusOr<std::unique_ptr<T>>:
|
||||
//
|
||||
// StatusOr<std::unique_ptr<Foo>> result = FooFactory::MakeNewFoo(arg);
|
||||
// if (result.ok()) {
|
||||
// std::unique_ptr<Foo> foo = result.ConsumeValueOrDie();
|
||||
// std::unique_ptr<Foo> foo(result.value());
|
||||
// foo->DoSomethingCool();
|
||||
// } else {
|
||||
// LOG(ERROR) << result.status();
|
||||
@ -93,17 +83,21 @@
|
||||
namespace google {
|
||||
namespace protobuf {
|
||||
namespace util {
|
||||
namespace statusor_internal {
|
||||
|
||||
template<typename T>
|
||||
class StatusOr {
|
||||
template<typename U> friend class StatusOr;
|
||||
|
||||
public:
|
||||
using value_type = T;
|
||||
|
||||
// Construct a new StatusOr with Status::UNKNOWN status.
|
||||
// Construct a new StatusOr with UnknownError() status.
|
||||
StatusOr();
|
||||
explicit StatusOr();
|
||||
|
||||
// Construct a new StatusOr with the given non-ok status. After calling
|
||||
// this constructor, calls to ValueOrDie() will CHECK-fail.
|
||||
// this constructor, calls to value() will CHECK-fail.
|
||||
//
|
||||
// NOTE: Not explicit - we want to use StatusOr<T> as a return
|
||||
// value, so it is convenient and sensible to be able to do 'return
|
||||
@ -116,7 +110,7 @@ class StatusOr {
|
||||
|
||||
// Construct a new StatusOr with the given value. If T is a plain pointer,
|
||||
// value must not be nullptr. After calling this constructor, calls to
|
||||
// ValueOrDie() will succeed, and calls to status() will return OK.
|
||||
// value() will succeed, and calls to status() will return OK.
|
||||
//
|
||||
// NOTE: Not explicit - we want to use StatusOr<T> as a return type
|
||||
// so it is convenient and sensible to be able to do 'return T()'
|
||||
@ -149,9 +143,6 @@ class StatusOr {
|
||||
bool ok() const;
|
||||
|
||||
// Returns a reference to our current value, or CHECK-fails if !this->ok().
|
||||
// If you need to initialize a T object from the stored value,
|
||||
// ConsumeValueOrDie() may be more efficient.
|
||||
const T& ValueOrDie() const;
|
||||
const T& value () const;
|
||||
|
||||
private:
|
||||
@ -162,8 +153,6 @@ class StatusOr {
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
// Implementation details for StatusOr<T>
|
||||
|
||||
namespace internal {
|
||||
|
||||
class PROTOBUF_EXPORT StatusOrHelper {
|
||||
public:
|
||||
// Move type-agnostic error handling to the .cc.
|
||||
@ -185,8 +174,6 @@ struct StatusOrHelper::Specialize<T*> {
|
||||
static inline bool IsValueNull(const T* t) { return t == nullptr; }
|
||||
};
|
||||
|
||||
} // namespace internal
|
||||
|
||||
template<typename T>
|
||||
inline StatusOr<T>::StatusOr()
|
||||
: status_(util::UnknownError("")) {
|
||||
@ -203,7 +190,7 @@ inline StatusOr<T>::StatusOr(const Status& status) {
|
||||
|
||||
template<typename T>
|
||||
inline StatusOr<T>::StatusOr(const T& value) {
|
||||
if (internal::StatusOrHelper::Specialize<T>::IsValueNull(value)) {
|
||||
if (StatusOrHelper::Specialize<T>::IsValueNull(value)) {
|
||||
status_ = util::InternalError("nullptr is not a valid argument.");
|
||||
} else {
|
||||
status_ = util::OkStatus();
|
||||
@ -248,20 +235,17 @@ inline bool StatusOr<T>::ok() const {
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
inline const T& StatusOr<T>::ValueOrDie() const {
|
||||
inline const T& StatusOr<T>::value() const {
|
||||
if (!status_.ok()) {
|
||||
internal::StatusOrHelper::Crash(status_);
|
||||
StatusOrHelper::Crash(status_);
|
||||
}
|
||||
return value_;
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
inline const T& StatusOr<T>::value() const {
|
||||
if (!status_.ok()) {
|
||||
internal::StatusOrHelper::Crash(status_);
|
||||
}
|
||||
return value_;
|
||||
}
|
||||
} // namespace statusor_internal
|
||||
|
||||
using ::google::protobuf::util::statusor_internal::StatusOr;
|
||||
|
||||
} // namespace util
|
||||
} // namespace protobuf
|
||||
} // namespace google
|
||||
|
@ -84,7 +84,7 @@ TEST(StatusOr, TestValueCtor) {
|
||||
const int kI = 4;
|
||||
StatusOr<int> thing(kI);
|
||||
EXPECT_TRUE(thing.ok());
|
||||
EXPECT_EQ(kI, thing.ValueOrDie());
|
||||
EXPECT_EQ(kI, thing.value());
|
||||
}
|
||||
|
||||
TEST(StatusOr, TestCopyCtorStatusOk) {
|
||||
@ -92,7 +92,7 @@ TEST(StatusOr, TestCopyCtorStatusOk) {
|
||||
StatusOr<int> original(kI);
|
||||
StatusOr<int> copy(original);
|
||||
EXPECT_EQ(original.status(), copy.status());
|
||||
EXPECT_EQ(original.ValueOrDie(), copy.ValueOrDie());
|
||||
EXPECT_EQ(original.value(), copy.value());
|
||||
}
|
||||
|
||||
TEST(StatusOr, TestCopyCtorStatusNotOk) {
|
||||
@ -106,7 +106,7 @@ TEST(StatusOr, TestCopyCtorStatusOKConverting) {
|
||||
StatusOr<int> original(kI);
|
||||
StatusOr<double> copy(original);
|
||||
EXPECT_EQ(original.status(), copy.status());
|
||||
EXPECT_EQ(original.ValueOrDie(), copy.ValueOrDie());
|
||||
EXPECT_EQ(original.value(), copy.value());
|
||||
}
|
||||
|
||||
TEST(StatusOr, TestCopyCtorStatusNotOkConverting) {
|
||||
@ -121,7 +121,7 @@ TEST(StatusOr, TestAssignmentStatusOk) {
|
||||
StatusOr<int> target;
|
||||
target = source;
|
||||
EXPECT_EQ(source.status(), target.status());
|
||||
EXPECT_EQ(source.ValueOrDie(), target.ValueOrDie());
|
||||
EXPECT_EQ(source.value(), target.value());
|
||||
}
|
||||
|
||||
TEST(StatusOr, TestAssignmentStatusNotOk) {
|
||||
@ -137,7 +137,7 @@ TEST(StatusOr, TestAssignmentStatusOKConverting) {
|
||||
StatusOr<double> target;
|
||||
target = source;
|
||||
EXPECT_EQ(source.status(), target.status());
|
||||
EXPECT_DOUBLE_EQ(source.ValueOrDie(), target.ValueOrDie());
|
||||
EXPECT_DOUBLE_EQ(source.value(), target.value());
|
||||
}
|
||||
|
||||
TEST(StatusOr, TestAssignmentStatusNotOkConverting) {
|
||||
@ -158,13 +158,13 @@ TEST(StatusOr, TestStatus) {
|
||||
TEST(StatusOr, TestValue) {
|
||||
const int kI = 4;
|
||||
StatusOr<int> thing(kI);
|
||||
EXPECT_EQ(kI, thing.ValueOrDie());
|
||||
EXPECT_EQ(kI, thing.value());
|
||||
}
|
||||
|
||||
TEST(StatusOr, TestValueConst) {
|
||||
const int kI = 4;
|
||||
const StatusOr<int> thing(kI);
|
||||
EXPECT_EQ(kI, thing.ValueOrDie());
|
||||
EXPECT_EQ(kI, thing.value());
|
||||
}
|
||||
|
||||
TEST(StatusOr, TestPointerDefaultCtor) {
|
||||
@ -183,7 +183,7 @@ TEST(StatusOr, TestPointerValueCtor) {
|
||||
const int kI = 4;
|
||||
StatusOr<const int*> thing(&kI);
|
||||
EXPECT_TRUE(thing.ok());
|
||||
EXPECT_EQ(&kI, thing.ValueOrDie());
|
||||
EXPECT_EQ(&kI, thing.value());
|
||||
}
|
||||
|
||||
TEST(StatusOr, TestPointerCopyCtorStatusOk) {
|
||||
@ -191,7 +191,7 @@ TEST(StatusOr, TestPointerCopyCtorStatusOk) {
|
||||
StatusOr<const int*> original(&kI);
|
||||
StatusOr<const int*> copy(original);
|
||||
EXPECT_EQ(original.status(), copy.status());
|
||||
EXPECT_EQ(original.ValueOrDie(), copy.ValueOrDie());
|
||||
EXPECT_EQ(original.value(), copy.value());
|
||||
}
|
||||
|
||||
TEST(StatusOr, TestPointerCopyCtorStatusNotOk) {
|
||||
@ -205,8 +205,7 @@ TEST(StatusOr, TestPointerCopyCtorStatusOKConverting) {
|
||||
StatusOr<Derived*> original(&derived);
|
||||
StatusOr<Base2*> copy(original);
|
||||
EXPECT_EQ(original.status(), copy.status());
|
||||
EXPECT_EQ(static_cast<const Base2*>(original.ValueOrDie()),
|
||||
copy.ValueOrDie());
|
||||
EXPECT_EQ(static_cast<const Base2*>(original.value()), copy.value());
|
||||
}
|
||||
|
||||
TEST(StatusOr, TestPointerCopyCtorStatusNotOkConverting) {
|
||||
@ -221,7 +220,7 @@ TEST(StatusOr, TestPointerAssignmentStatusOk) {
|
||||
StatusOr<const int*> target;
|
||||
target = source;
|
||||
EXPECT_EQ(source.status(), target.status());
|
||||
EXPECT_EQ(source.ValueOrDie(), target.ValueOrDie());
|
||||
EXPECT_EQ(source.value(), target.value());
|
||||
}
|
||||
|
||||
TEST(StatusOr, TestPointerAssignmentStatusNotOk) {
|
||||
@ -237,8 +236,7 @@ TEST(StatusOr, TestPointerAssignmentStatusOKConverting) {
|
||||
StatusOr<Base2*> target;
|
||||
target = source;
|
||||
EXPECT_EQ(source.status(), target.status());
|
||||
EXPECT_EQ(static_cast<const Base2*>(source.ValueOrDie()),
|
||||
target.ValueOrDie());
|
||||
EXPECT_EQ(static_cast<const Base2*>(source.value()), target.value());
|
||||
}
|
||||
|
||||
TEST(StatusOr, TestPointerAssignmentStatusNotOkConverting) {
|
||||
@ -259,13 +257,13 @@ TEST(StatusOr, TestPointerStatus) {
|
||||
TEST(StatusOr, TestPointerValue) {
|
||||
const int kI = 0;
|
||||
StatusOr<const int*> thing(&kI);
|
||||
EXPECT_EQ(&kI, thing.ValueOrDie());
|
||||
EXPECT_EQ(&kI, thing.value());
|
||||
}
|
||||
|
||||
TEST(StatusOr, TestPointerValueConst) {
|
||||
const int kI = 0;
|
||||
const StatusOr<const int*> thing(&kI);
|
||||
EXPECT_EQ(&kI, thing.ValueOrDie());
|
||||
EXPECT_EQ(&kI, thing.value());
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
@ -39,31 +39,13 @@
|
||||
|
||||
namespace google {
|
||||
namespace protobuf {
|
||||
namespace stringpiece_internal {
|
||||
|
||||
std::ostream& operator<<(std::ostream& o, StringPiece piece) {
|
||||
o.write(piece.data(), piece.size());
|
||||
return o;
|
||||
}
|
||||
|
||||
// Out-of-line error path.
|
||||
void StringPiece::LogFatalSizeTooBig(size_t size, const char* details) {
|
||||
GOOGLE_LOG(FATAL) << "size too big: " << size << " details: " << details;
|
||||
}
|
||||
|
||||
StringPiece::StringPiece(StringPiece x, stringpiece_ssize_type pos)
|
||||
: ptr_(x.ptr_ + pos), length_(x.length_ - pos) {
|
||||
GOOGLE_DCHECK_LE(0, pos);
|
||||
GOOGLE_DCHECK_LE(pos, x.length_);
|
||||
}
|
||||
|
||||
StringPiece::StringPiece(StringPiece x,
|
||||
stringpiece_ssize_type pos,
|
||||
stringpiece_ssize_type len)
|
||||
: ptr_(x.ptr_ + pos), length_(std::min(len, x.length_ - pos)) {
|
||||
GOOGLE_DCHECK_LE(0, pos);
|
||||
GOOGLE_DCHECK_LE(pos, x.length_);
|
||||
GOOGLE_DCHECK_GE(len, 0);
|
||||
}
|
||||
|
||||
void StringPiece::CopyToString(std::string* target) const {
|
||||
target->assign(ptr_, length_);
|
||||
}
|
||||
@ -89,10 +71,9 @@ bool StringPiece::ConsumeFromEnd(StringPiece x) {
|
||||
return false;
|
||||
}
|
||||
|
||||
stringpiece_ssize_type StringPiece::copy(char* buf,
|
||||
size_type n,
|
||||
size_type pos) const {
|
||||
stringpiece_ssize_type ret = std::min(length_ - pos, n);
|
||||
StringPiece::size_type StringPiece::copy(
|
||||
char* buf, size_type n, size_type pos) const {
|
||||
size_type ret = std::min(length_ - pos, n);
|
||||
memcpy(buf, ptr_ + pos, ret);
|
||||
return ret;
|
||||
}
|
||||
@ -101,7 +82,8 @@ bool StringPiece::contains(StringPiece s) const {
|
||||
return find(s, 0) != npos;
|
||||
}
|
||||
|
||||
stringpiece_ssize_type StringPiece::find(StringPiece s, size_type pos) const {
|
||||
StringPiece::size_type StringPiece::find(
|
||||
StringPiece s, size_type pos) const {
|
||||
if (length_ <= 0 || pos > static_cast<size_type>(length_)) {
|
||||
if (length_ == 0 && pos == 0 && s.length_ == 0) return 0;
|
||||
return npos;
|
||||
@ -111,7 +93,7 @@ stringpiece_ssize_type StringPiece::find(StringPiece s, size_type pos) const {
|
||||
return result == ptr_ + length_ ? npos : result - ptr_;
|
||||
}
|
||||
|
||||
stringpiece_ssize_type StringPiece::find(char c, size_type pos) const {
|
||||
StringPiece::size_type StringPiece::find(char c, size_type pos) const {
|
||||
if (length_ <= 0 || pos >= static_cast<size_type>(length_)) {
|
||||
return npos;
|
||||
}
|
||||
@ -120,7 +102,7 @@ stringpiece_ssize_type StringPiece::find(char c, size_type pos) const {
|
||||
return result != nullptr ? result - ptr_ : npos;
|
||||
}
|
||||
|
||||
stringpiece_ssize_type StringPiece::rfind(StringPiece s, size_type pos) const {
|
||||
StringPiece::size_type StringPiece::rfind(StringPiece s, size_type pos) const {
|
||||
if (length_ < s.length_) return npos;
|
||||
const size_t ulen = length_;
|
||||
if (s.length_ == 0) return std::min(ulen, pos);
|
||||
@ -131,10 +113,10 @@ stringpiece_ssize_type StringPiece::rfind(StringPiece s, size_type pos) const {
|
||||
}
|
||||
|
||||
// Search range is [0..pos] inclusive. If pos == npos, search everything.
|
||||
stringpiece_ssize_type StringPiece::rfind(char c, size_type pos) const {
|
||||
StringPiece::size_type StringPiece::rfind(char c, size_type pos) const {
|
||||
// Note: memrchr() is not available on Windows.
|
||||
if (length_ <= 0) return npos;
|
||||
for (stringpiece_ssize_type i =
|
||||
if (empty()) return npos;
|
||||
for (difference_type i =
|
||||
std::min(pos, static_cast<size_type>(length_ - 1));
|
||||
i >= 0; --i) {
|
||||
if (ptr_[i] == c) {
|
||||
@ -154,16 +136,16 @@ stringpiece_ssize_type StringPiece::rfind(char c, size_type pos) const {
|
||||
// bool table[UCHAR_MAX + 1]
|
||||
static inline void BuildLookupTable(StringPiece characters_wanted,
|
||||
bool* table) {
|
||||
const stringpiece_ssize_type length = characters_wanted.length();
|
||||
const StringPiece::size_type length = characters_wanted.length();
|
||||
const char* const data = characters_wanted.data();
|
||||
for (stringpiece_ssize_type i = 0; i < length; ++i) {
|
||||
for (StringPiece::size_type i = 0; i < length; ++i) {
|
||||
table[static_cast<unsigned char>(data[i])] = true;
|
||||
}
|
||||
}
|
||||
|
||||
stringpiece_ssize_type StringPiece::find_first_of(StringPiece s,
|
||||
size_type pos) const {
|
||||
if (length_ <= 0 || s.length_ <= 0) {
|
||||
StringPiece::size_type StringPiece::find_first_of(
|
||||
StringPiece s, size_type pos) const {
|
||||
if (empty() || s.empty()) {
|
||||
return npos;
|
||||
}
|
||||
// Avoid the cost of BuildLookupTable() for a single-character search.
|
||||
@ -171,7 +153,7 @@ stringpiece_ssize_type StringPiece::find_first_of(StringPiece s,
|
||||
|
||||
bool lookup[UCHAR_MAX + 1] = { false };
|
||||
BuildLookupTable(s, lookup);
|
||||
for (stringpiece_ssize_type i = pos; i < length_; ++i) {
|
||||
for (size_type i = pos; i < length_; ++i) {
|
||||
if (lookup[static_cast<unsigned char>(ptr_[i])]) {
|
||||
return i;
|
||||
}
|
||||
@ -179,16 +161,16 @@ stringpiece_ssize_type StringPiece::find_first_of(StringPiece s,
|
||||
return npos;
|
||||
}
|
||||
|
||||
stringpiece_ssize_type StringPiece::find_first_not_of(StringPiece s,
|
||||
size_type pos) const {
|
||||
if (length_ <= 0) return npos;
|
||||
if (s.length_ <= 0) return 0;
|
||||
StringPiece::size_type StringPiece::find_first_not_of(
|
||||
StringPiece s, size_type pos) const {
|
||||
if (empty()) return npos;
|
||||
if (s.empty()) return 0;
|
||||
// Avoid the cost of BuildLookupTable() for a single-character search.
|
||||
if (s.length_ == 1) return find_first_not_of(s.ptr_[0], pos);
|
||||
|
||||
bool lookup[UCHAR_MAX + 1] = { false };
|
||||
BuildLookupTable(s, lookup);
|
||||
for (stringpiece_ssize_type i = pos; i < length_; ++i) {
|
||||
for (size_type i = pos; i < length_; ++i) {
|
||||
if (!lookup[static_cast<unsigned char>(ptr_[i])]) {
|
||||
return i;
|
||||
}
|
||||
@ -196,9 +178,9 @@ stringpiece_ssize_type StringPiece::find_first_not_of(StringPiece s,
|
||||
return npos;
|
||||
}
|
||||
|
||||
stringpiece_ssize_type StringPiece::find_first_not_of(char c,
|
||||
size_type pos) const {
|
||||
if (length_ <= 0) return npos;
|
||||
StringPiece::size_type StringPiece::find_first_not_of(
|
||||
char c, size_type pos) const {
|
||||
if (empty()) return npos;
|
||||
|
||||
for (; pos < static_cast<size_type>(length_); ++pos) {
|
||||
if (ptr_[pos] != c) {
|
||||
@ -208,15 +190,15 @@ stringpiece_ssize_type StringPiece::find_first_not_of(char c,
|
||||
return npos;
|
||||
}
|
||||
|
||||
stringpiece_ssize_type StringPiece::find_last_of(StringPiece s,
|
||||
size_type pos) const {
|
||||
if (length_ <= 0 || s.length_ <= 0) return npos;
|
||||
StringPiece::size_type StringPiece::find_last_of(
|
||||
StringPiece s, size_type pos) const {
|
||||
if (empty() || s.empty()) return npos;
|
||||
// Avoid the cost of BuildLookupTable() for a single-character search.
|
||||
if (s.length_ == 1) return find_last_of(s.ptr_[0], pos);
|
||||
|
||||
bool lookup[UCHAR_MAX + 1] = { false };
|
||||
BuildLookupTable(s, lookup);
|
||||
for (stringpiece_ssize_type i =
|
||||
for (difference_type i =
|
||||
std::min(pos, static_cast<size_type>(length_ - 1)); i >= 0; --i) {
|
||||
if (lookup[static_cast<unsigned char>(ptr_[i])]) {
|
||||
return i;
|
||||
@ -225,12 +207,12 @@ stringpiece_ssize_type StringPiece::find_last_of(StringPiece s,
|
||||
return npos;
|
||||
}
|
||||
|
||||
stringpiece_ssize_type StringPiece::find_last_not_of(StringPiece s,
|
||||
size_type pos) const {
|
||||
if (length_ <= 0) return npos;
|
||||
StringPiece::size_type StringPiece::find_last_not_of(
|
||||
StringPiece s, size_type pos) const {
|
||||
if (empty()) return npos;
|
||||
|
||||
stringpiece_ssize_type i = std::min(pos, static_cast<size_type>(length_ - 1));
|
||||
if (s.length_ <= 0) return i;
|
||||
size_type i = std::min(pos, length()-1);
|
||||
if (s.empty()) return i;
|
||||
|
||||
// Avoid the cost of BuildLookupTable() for a single-character search.
|
||||
if (s.length_ == 1) return find_last_not_of(s.ptr_[0], pos);
|
||||
@ -245,11 +227,11 @@ stringpiece_ssize_type StringPiece::find_last_not_of(StringPiece s,
|
||||
return npos;
|
||||
}
|
||||
|
||||
stringpiece_ssize_type StringPiece::find_last_not_of(char c,
|
||||
size_type pos) const {
|
||||
if (length_ <= 0) return npos;
|
||||
StringPiece::size_type StringPiece::find_last_not_of(
|
||||
char c, size_type pos) const {
|
||||
if (empty()) return npos;
|
||||
|
||||
for (stringpiece_ssize_type i =
|
||||
for (difference_type i =
|
||||
std::min(pos, static_cast<size_type>(length_ - 1)); i >= 0; --i) {
|
||||
if (ptr_[i] != c) {
|
||||
return i;
|
||||
@ -259,12 +241,13 @@ stringpiece_ssize_type StringPiece::find_last_not_of(char c,
|
||||
}
|
||||
|
||||
StringPiece StringPiece::substr(size_type pos, size_type n) const {
|
||||
if (pos > length_) pos = length_;
|
||||
if (n > length_ - pos) n = length_ - pos;
|
||||
if (pos > length()) pos = length();
|
||||
if (n > length_ - pos) n = length() - pos;
|
||||
return StringPiece(ptr_ + pos, n);
|
||||
}
|
||||
|
||||
const StringPiece::size_type StringPiece::npos = size_type(-1);
|
||||
|
||||
} // namespace stringpiece_internal
|
||||
} // namespace protobuf
|
||||
} // namespace google
|
||||
|
@ -154,52 +154,26 @@
|
||||
|
||||
namespace google {
|
||||
namespace protobuf {
|
||||
// StringPiece has *two* size types.
|
||||
// StringPiece::size_type
|
||||
// is unsigned
|
||||
// is 32 bits in LP32, 64 bits in LP64, 64 bits in LLP64
|
||||
// no future changes intended
|
||||
// stringpiece_ssize_type
|
||||
// is signed
|
||||
// is 32 bits in LP32, 64 bits in LP64, 64 bits in LLP64
|
||||
// future changes intended: http://go/64BitStringPiece
|
||||
//
|
||||
typedef std::string::difference_type stringpiece_ssize_type;
|
||||
|
||||
// STRINGPIECE_CHECK_SIZE protects us from 32-bit overflows.
|
||||
// TODO(mec): delete this after stringpiece_ssize_type goes 64 bit.
|
||||
#if !defined(NDEBUG)
|
||||
#define STRINGPIECE_CHECK_SIZE 1
|
||||
#elif defined(_FORTIFY_SOURCE) && _FORTIFY_SOURCE > 0
|
||||
#define STRINGPIECE_CHECK_SIZE 1
|
||||
#else
|
||||
#define STRINGPIECE_CHECK_SIZE 0
|
||||
#endif
|
||||
namespace stringpiece_internal {
|
||||
|
||||
class PROTOBUF_EXPORT StringPiece {
|
||||
public:
|
||||
using traits_type = std::char_traits<char>;
|
||||
using value_type = char;
|
||||
using pointer = char*;
|
||||
using const_pointer = const char*;
|
||||
using reference = char&;
|
||||
using const_reference = const char&;
|
||||
using const_iterator = const char*;
|
||||
using iterator = const_iterator;
|
||||
using const_reverse_iterator = std::reverse_iterator<const_iterator>;
|
||||
using reverse_iterator = const_reverse_iterator;
|
||||
using size_type = size_t;
|
||||
using difference_type = std::ptrdiff_t;
|
||||
|
||||
private:
|
||||
const char* ptr_;
|
||||
stringpiece_ssize_type length_;
|
||||
|
||||
// Prevent overflow in debug mode or fortified mode.
|
||||
// sizeof(stringpiece_ssize_type) may be smaller than sizeof(size_t).
|
||||
static stringpiece_ssize_type CheckedSsizeTFromSizeT(size_t size) {
|
||||
#if STRINGPIECE_CHECK_SIZE > 0
|
||||
#ifdef max
|
||||
#undef max
|
||||
#endif
|
||||
if (size > static_cast<size_t>(
|
||||
std::numeric_limits<stringpiece_ssize_type>::max())) {
|
||||
// Some people grep for this message in logs
|
||||
// so take care if you ever change it.
|
||||
LogFatalSizeTooBig(size, "size_t to int conversion");
|
||||
}
|
||||
#endif
|
||||
return static_cast<stringpiece_ssize_type>(size);
|
||||
}
|
||||
|
||||
// Out-of-line error path.
|
||||
static void LogFatalSizeTooBig(size_t size, const char* details);
|
||||
size_type length_;
|
||||
|
||||
public:
|
||||
// We provide non-explicit singleton constructors so users can pass
|
||||
@ -213,7 +187,7 @@ class PROTOBUF_EXPORT StringPiece {
|
||||
StringPiece(const char* str) // NOLINT(runtime/explicit)
|
||||
: ptr_(str), length_(0) {
|
||||
if (str != nullptr) {
|
||||
length_ = CheckedSsizeTFromSizeT(strlen(str));
|
||||
length_ = strlen(str);
|
||||
}
|
||||
}
|
||||
|
||||
@ -221,78 +195,40 @@ class PROTOBUF_EXPORT StringPiece {
|
||||
StringPiece( // NOLINT(runtime/explicit)
|
||||
const std::basic_string<char, std::char_traits<char>, Allocator>& str)
|
||||
: ptr_(str.data()), length_(0) {
|
||||
length_ = CheckedSsizeTFromSizeT(str.size());
|
||||
length_ = str.size();
|
||||
}
|
||||
|
||||
StringPiece(const char* offset, stringpiece_ssize_type len)
|
||||
: ptr_(offset), length_(len) {
|
||||
assert(len >= 0);
|
||||
}
|
||||
|
||||
// Substring of another StringPiece.
|
||||
// pos must be non-negative and <= x.length().
|
||||
StringPiece(StringPiece x, stringpiece_ssize_type pos);
|
||||
// Substring of another StringPiece.
|
||||
// pos must be non-negative and <= x.length().
|
||||
// len must be non-negative and will be pinned to at most x.length() - pos.
|
||||
StringPiece(StringPiece x,
|
||||
stringpiece_ssize_type pos,
|
||||
stringpiece_ssize_type len);
|
||||
StringPiece(const char* offset, size_type len)
|
||||
: ptr_(offset), length_(len) {}
|
||||
|
||||
// data() may return a pointer to a buffer with embedded NULs, and the
|
||||
// returned buffer may or may not be null terminated. Therefore it is
|
||||
// typically a mistake to pass data() to a routine that expects a NUL
|
||||
// terminated string.
|
||||
const char* data() const { return ptr_; }
|
||||
stringpiece_ssize_type size() const { return length_; }
|
||||
stringpiece_ssize_type length() const { return length_; }
|
||||
const_pointer data() const { return ptr_; }
|
||||
size_type size() const { return length_; }
|
||||
size_type length() const { return length_; }
|
||||
bool empty() const { return length_ == 0; }
|
||||
|
||||
void clear() {
|
||||
ptr_ = nullptr;
|
||||
length_ = 0;
|
||||
}
|
||||
|
||||
void set(const char* data, stringpiece_ssize_type len) {
|
||||
assert(len >= 0);
|
||||
ptr_ = data;
|
||||
length_ = len;
|
||||
}
|
||||
|
||||
void set(const char* str) {
|
||||
ptr_ = str;
|
||||
if (str != nullptr)
|
||||
length_ = CheckedSsizeTFromSizeT(strlen(str));
|
||||
else
|
||||
length_ = 0;
|
||||
}
|
||||
|
||||
void set(const void* data, stringpiece_ssize_type len) {
|
||||
ptr_ = reinterpret_cast<const char*>(data);
|
||||
length_ = len;
|
||||
}
|
||||
|
||||
char operator[](stringpiece_ssize_type i) const {
|
||||
assert(0 <= i);
|
||||
char operator[](size_type i) const {
|
||||
assert(i < length_);
|
||||
return ptr_[i];
|
||||
}
|
||||
|
||||
void remove_prefix(stringpiece_ssize_type n) {
|
||||
void remove_prefix(size_type n) {
|
||||
assert(length_ >= n);
|
||||
ptr_ += n;
|
||||
length_ -= n;
|
||||
}
|
||||
|
||||
void remove_suffix(stringpiece_ssize_type n) {
|
||||
void remove_suffix(size_type n) {
|
||||
assert(length_ >= n);
|
||||
length_ -= n;
|
||||
}
|
||||
|
||||
// returns {-1, 0, 1}
|
||||
int compare(StringPiece x) const {
|
||||
const stringpiece_ssize_type min_size =
|
||||
length_ < x.length_ ? length_ : x.length_;
|
||||
size_type min_size = length_ < x.length_ ? length_ : x.length_;
|
||||
int r = memcmp(ptr_, x.ptr_, static_cast<size_t>(min_size));
|
||||
if (r < 0) return -1;
|
||||
if (r > 0) return 1;
|
||||
@ -336,53 +272,41 @@ class PROTOBUF_EXPORT StringPiece {
|
||||
bool ConsumeFromEnd(StringPiece x);
|
||||
|
||||
// standard STL container boilerplate
|
||||
typedef char value_type;
|
||||
typedef const char* pointer;
|
||||
typedef const char& reference;
|
||||
typedef const char& const_reference;
|
||||
typedef size_t size_type;
|
||||
typedef ptrdiff_t difference_type;
|
||||
static const size_type npos;
|
||||
typedef const char* const_iterator;
|
||||
typedef const char* iterator;
|
||||
typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
|
||||
typedef std::reverse_iterator<iterator> reverse_iterator;
|
||||
iterator begin() const { return ptr_; }
|
||||
iterator end() const { return ptr_ + length_; }
|
||||
const_iterator begin() const { return ptr_; }
|
||||
const_iterator end() const { return ptr_ + length_; }
|
||||
const_reverse_iterator rbegin() const {
|
||||
return const_reverse_iterator(ptr_ + length_);
|
||||
}
|
||||
const_reverse_iterator rend() const {
|
||||
return const_reverse_iterator(ptr_);
|
||||
}
|
||||
stringpiece_ssize_type max_size() const { return length_; }
|
||||
stringpiece_ssize_type capacity() const { return length_; }
|
||||
size_type max_size() const { return length_; }
|
||||
size_type capacity() const { return length_; }
|
||||
|
||||
// cpplint.py emits a false positive [build/include_what_you_use]
|
||||
stringpiece_ssize_type copy(char* buf, size_type n, size_type pos = 0) const; // NOLINT
|
||||
size_type copy(char* buf, size_type n, size_type pos = 0) const; // NOLINT
|
||||
|
||||
bool contains(StringPiece s) const;
|
||||
|
||||
stringpiece_ssize_type find(StringPiece s, size_type pos = 0) const;
|
||||
stringpiece_ssize_type find(char c, size_type pos = 0) const;
|
||||
stringpiece_ssize_type rfind(StringPiece s, size_type pos = npos) const;
|
||||
stringpiece_ssize_type rfind(char c, size_type pos = npos) const;
|
||||
size_type find(StringPiece s, size_type pos = 0) const;
|
||||
size_type find(char c, size_type pos = 0) const;
|
||||
size_type rfind(StringPiece s, size_type pos = npos) const;
|
||||
size_type rfind(char c, size_type pos = npos) const;
|
||||
|
||||
stringpiece_ssize_type find_first_of(StringPiece s, size_type pos = 0) const;
|
||||
stringpiece_ssize_type find_first_of(char c, size_type pos = 0) const {
|
||||
size_type find_first_of(StringPiece s, size_type pos = 0) const;
|
||||
size_type find_first_of(char c, size_type pos = 0) const {
|
||||
return find(c, pos);
|
||||
}
|
||||
stringpiece_ssize_type find_first_not_of(StringPiece s,
|
||||
size_type pos = 0) const;
|
||||
stringpiece_ssize_type find_first_not_of(char c, size_type pos = 0) const;
|
||||
stringpiece_ssize_type find_last_of(StringPiece s,
|
||||
size_type pos = npos) const;
|
||||
stringpiece_ssize_type find_last_of(char c, size_type pos = npos) const {
|
||||
size_type find_first_not_of(StringPiece s, size_type pos = 0) const;
|
||||
size_type find_first_not_of(char c, size_type pos = 0) const;
|
||||
size_type find_last_of(StringPiece s, size_type pos = npos) const;
|
||||
size_type find_last_of(char c, size_type pos = npos) const {
|
||||
return rfind(c, pos);
|
||||
}
|
||||
stringpiece_ssize_type find_last_not_of(StringPiece s,
|
||||
size_type find_last_not_of(StringPiece s,
|
||||
size_type pos = npos) const;
|
||||
stringpiece_ssize_type find_last_not_of(char c, size_type pos = npos) const;
|
||||
size_type find_last_not_of(char c, size_type pos = npos) const;
|
||||
|
||||
StringPiece substr(size_type pos, size_type n = npos) const;
|
||||
};
|
||||
@ -391,7 +315,7 @@ class PROTOBUF_EXPORT StringPiece {
|
||||
// one of the arguments is a literal, the compiler can elide a lot of the
|
||||
// following comparisons.
|
||||
inline bool operator==(StringPiece x, StringPiece y) {
|
||||
stringpiece_ssize_type len = x.size();
|
||||
StringPiece::size_type len = x.size();
|
||||
if (len != y.size()) {
|
||||
return false;
|
||||
}
|
||||
@ -405,7 +329,7 @@ inline bool operator!=(StringPiece x, StringPiece y) {
|
||||
}
|
||||
|
||||
inline bool operator<(StringPiece x, StringPiece y) {
|
||||
const stringpiece_ssize_type min_size =
|
||||
const StringPiece::size_type min_size =
|
||||
x.size() < y.size() ? x.size() : y.size();
|
||||
const int r = memcmp(x.data(), y.data(), static_cast<size_t>(min_size));
|
||||
return (r < 0) || (r == 0 && x.size() < y.size());
|
||||
@ -426,6 +350,10 @@ inline bool operator>=(StringPiece x, StringPiece y) {
|
||||
// allow StringPiece to be logged
|
||||
extern std::ostream& operator<<(std::ostream& o, StringPiece piece);
|
||||
|
||||
} // namespace stringpiece_internal
|
||||
|
||||
using ::google::protobuf::stringpiece_internal::StringPiece;
|
||||
|
||||
} // namespace protobuf
|
||||
} // namespace google
|
||||
|
||||
|
@ -305,16 +305,9 @@ TEST(StringPiece, STL2) {
|
||||
const StringPiece a("abcdefghijklmnopqrstuvwxyz");
|
||||
const StringPiece b("abc");
|
||||
const StringPiece c("xyz");
|
||||
StringPiece d("foobar");
|
||||
const StringPiece e;
|
||||
const StringPiece f("123" "\0" "456", 7);
|
||||
|
||||
d.clear();
|
||||
EXPECT_EQ(d.size(), 0);
|
||||
EXPECT_TRUE(d.empty());
|
||||
EXPECT_TRUE(d.data() == nullptr);
|
||||
EXPECT_TRUE(d.begin() == d.end());
|
||||
|
||||
EXPECT_EQ(StringPiece::npos, std::string::npos);
|
||||
|
||||
EXPECT_EQ(a.find(b), 0);
|
||||
@ -324,26 +317,16 @@ TEST(StringPiece, STL2) {
|
||||
EXPECT_EQ(a.find(c, StringPiece::npos), StringPiece::npos);
|
||||
EXPECT_EQ(b.find(c), StringPiece::npos);
|
||||
EXPECT_EQ(b.find(c, StringPiece::npos), StringPiece::npos);
|
||||
EXPECT_EQ(a.find(d), 0);
|
||||
EXPECT_EQ(a.find(e), 0);
|
||||
EXPECT_EQ(a.find(d, 12), 12);
|
||||
EXPECT_EQ(a.find(e, 17), 17);
|
||||
StringPiece g("xx not found bb");
|
||||
EXPECT_EQ(a.find(g), StringPiece::npos);
|
||||
// empty string nonsense
|
||||
EXPECT_EQ(d.find(b), StringPiece::npos);
|
||||
EXPECT_EQ(e.find(b), StringPiece::npos);
|
||||
EXPECT_EQ(d.find(b, 4), StringPiece::npos);
|
||||
EXPECT_EQ(e.find(b, 7), StringPiece::npos);
|
||||
|
||||
size_t empty_search_pos = std::string().find(std::string());
|
||||
EXPECT_EQ(d.find(d), empty_search_pos);
|
||||
EXPECT_EQ(d.find(e), empty_search_pos);
|
||||
EXPECT_EQ(e.find(d), empty_search_pos);
|
||||
EXPECT_EQ(e.find(e), empty_search_pos);
|
||||
EXPECT_EQ(d.find(d, 4), std::string().find(std::string(), 4));
|
||||
EXPECT_EQ(d.find(e, 4), std::string().find(std::string(), 4));
|
||||
EXPECT_EQ(e.find(d, 4), std::string().find(std::string(), 4));
|
||||
EXPECT_EQ(e.find(e, 4), std::string().find(std::string(), 4));
|
||||
|
||||
EXPECT_EQ(a.find('a'), 0);
|
||||
@ -359,13 +342,9 @@ TEST(StringPiece, STL2) {
|
||||
EXPECT_EQ(g.find('o', 5), 8);
|
||||
EXPECT_EQ(a.find('b', 5), StringPiece::npos);
|
||||
// empty string nonsense
|
||||
EXPECT_EQ(d.find('\0'), StringPiece::npos);
|
||||
EXPECT_EQ(e.find('\0'), StringPiece::npos);
|
||||
EXPECT_EQ(d.find('\0', 4), StringPiece::npos);
|
||||
EXPECT_EQ(e.find('\0', 7), StringPiece::npos);
|
||||
EXPECT_EQ(d.find('x'), StringPiece::npos);
|
||||
EXPECT_EQ(e.find('x'), StringPiece::npos);
|
||||
EXPECT_EQ(d.find('x', 4), StringPiece::npos);
|
||||
EXPECT_EQ(e.find('x', 7), StringPiece::npos);
|
||||
|
||||
EXPECT_EQ(a.rfind(b), 0);
|
||||
@ -376,23 +355,13 @@ TEST(StringPiece, STL2) {
|
||||
EXPECT_EQ(a.rfind(c, 0), StringPiece::npos);
|
||||
EXPECT_EQ(b.rfind(c), StringPiece::npos);
|
||||
EXPECT_EQ(b.rfind(c, 0), StringPiece::npos);
|
||||
EXPECT_EQ(a.rfind(d), a.as_string().rfind(std::string()));
|
||||
EXPECT_EQ(a.rfind(e), a.as_string().rfind(std::string()));
|
||||
EXPECT_EQ(a.rfind(d, 12), 12);
|
||||
EXPECT_EQ(a.rfind(e, 17), 17);
|
||||
EXPECT_EQ(a.rfind(g), StringPiece::npos);
|
||||
EXPECT_EQ(d.rfind(b), StringPiece::npos);
|
||||
EXPECT_EQ(e.rfind(b), StringPiece::npos);
|
||||
EXPECT_EQ(d.rfind(b, 4), StringPiece::npos);
|
||||
EXPECT_EQ(e.rfind(b, 7), StringPiece::npos);
|
||||
// empty string nonsense
|
||||
EXPECT_EQ(d.rfind(d, 4), std::string().rfind(std::string()));
|
||||
EXPECT_EQ(e.rfind(d, 7), std::string().rfind(std::string()));
|
||||
EXPECT_EQ(d.rfind(e, 4), std::string().rfind(std::string()));
|
||||
EXPECT_EQ(e.rfind(e, 7), std::string().rfind(std::string()));
|
||||
EXPECT_EQ(d.rfind(d), std::string().rfind(std::string()));
|
||||
EXPECT_EQ(e.rfind(d), std::string().rfind(std::string()));
|
||||
EXPECT_EQ(d.rfind(e), std::string().rfind(std::string()));
|
||||
EXPECT_EQ(e.rfind(e), std::string().rfind(std::string()));
|
||||
|
||||
EXPECT_EQ(g.rfind('o'), 8);
|
||||
@ -405,9 +374,7 @@ TEST(StringPiece, STL2) {
|
||||
EXPECT_EQ(f.rfind('3'), 2);
|
||||
EXPECT_EQ(f.rfind('5'), 5);
|
||||
// empty string nonsense
|
||||
EXPECT_EQ(d.rfind('o'), StringPiece::npos);
|
||||
EXPECT_EQ(e.rfind('o'), StringPiece::npos);
|
||||
EXPECT_EQ(d.rfind('o', 4), StringPiece::npos);
|
||||
EXPECT_EQ(e.rfind('o', 7), StringPiece::npos);
|
||||
|
||||
EXPECT_EQ(a.find_first_of(b), 0);
|
||||
@ -425,13 +392,8 @@ TEST(StringPiece, STL2) {
|
||||
EXPECT_EQ(a.find_first_of(f), StringPiece::npos);
|
||||
EXPECT_EQ(f.find_first_of(a), StringPiece::npos);
|
||||
// empty string nonsense
|
||||
EXPECT_EQ(a.find_first_of(d), StringPiece::npos);
|
||||
EXPECT_EQ(a.find_first_of(e), StringPiece::npos);
|
||||
EXPECT_EQ(d.find_first_of(b), StringPiece::npos);
|
||||
EXPECT_EQ(e.find_first_of(b), StringPiece::npos);
|
||||
EXPECT_EQ(d.find_first_of(d), StringPiece::npos);
|
||||
EXPECT_EQ(e.find_first_of(d), StringPiece::npos);
|
||||
EXPECT_EQ(d.find_first_of(e), StringPiece::npos);
|
||||
EXPECT_EQ(e.find_first_of(e), StringPiece::npos);
|
||||
|
||||
EXPECT_EQ(a.find_first_not_of(b), 3);
|
||||
@ -440,14 +402,9 @@ TEST(StringPiece, STL2) {
|
||||
EXPECT_EQ(c.find_first_not_of(a), StringPiece::npos);
|
||||
EXPECT_EQ(f.find_first_not_of(a), 0);
|
||||
EXPECT_EQ(a.find_first_not_of(f), 0);
|
||||
EXPECT_EQ(a.find_first_not_of(d), 0);
|
||||
EXPECT_EQ(a.find_first_not_of(e), 0);
|
||||
// empty string nonsense
|
||||
EXPECT_EQ(d.find_first_not_of(a), StringPiece::npos);
|
||||
EXPECT_EQ(e.find_first_not_of(a), StringPiece::npos);
|
||||
EXPECT_EQ(d.find_first_not_of(d), StringPiece::npos);
|
||||
EXPECT_EQ(e.find_first_not_of(d), StringPiece::npos);
|
||||
EXPECT_EQ(d.find_first_not_of(e), StringPiece::npos);
|
||||
EXPECT_EQ(e.find_first_not_of(e), StringPiece::npos);
|
||||
|
||||
StringPiece h("====");
|
||||
@ -459,9 +416,7 @@ TEST(StringPiece, STL2) {
|
||||
EXPECT_EQ(f.find_first_not_of('\0', 3), 4);
|
||||
EXPECT_EQ(f.find_first_not_of('\0', 2), 2);
|
||||
// empty string nonsense
|
||||
EXPECT_EQ(d.find_first_not_of('x'), StringPiece::npos);
|
||||
EXPECT_EQ(e.find_first_not_of('x'), StringPiece::npos);
|
||||
EXPECT_EQ(d.find_first_not_of('\0'), StringPiece::npos);
|
||||
EXPECT_EQ(e.find_first_not_of('\0'), StringPiece::npos);
|
||||
|
||||
// StringPiece g("xx not found bb");
|
||||
@ -483,21 +438,11 @@ TEST(StringPiece, STL2) {
|
||||
EXPECT_EQ(f.find_last_of(i, 6), 6);
|
||||
EXPECT_EQ(f.find_last_of(a, 4), StringPiece::npos);
|
||||
// empty string nonsense
|
||||
EXPECT_EQ(f.find_last_of(d), StringPiece::npos);
|
||||
EXPECT_EQ(f.find_last_of(e), StringPiece::npos);
|
||||
EXPECT_EQ(f.find_last_of(d, 4), StringPiece::npos);
|
||||
EXPECT_EQ(f.find_last_of(e, 4), StringPiece::npos);
|
||||
EXPECT_EQ(d.find_last_of(d), StringPiece::npos);
|
||||
EXPECT_EQ(d.find_last_of(e), StringPiece::npos);
|
||||
EXPECT_EQ(e.find_last_of(d), StringPiece::npos);
|
||||
EXPECT_EQ(e.find_last_of(e), StringPiece::npos);
|
||||
EXPECT_EQ(d.find_last_of(f), StringPiece::npos);
|
||||
EXPECT_EQ(e.find_last_of(f), StringPiece::npos);
|
||||
EXPECT_EQ(d.find_last_of(d, 4), StringPiece::npos);
|
||||
EXPECT_EQ(d.find_last_of(e, 4), StringPiece::npos);
|
||||
EXPECT_EQ(e.find_last_of(d, 4), StringPiece::npos);
|
||||
EXPECT_EQ(e.find_last_of(e, 4), StringPiece::npos);
|
||||
EXPECT_EQ(d.find_last_of(f, 4), StringPiece::npos);
|
||||
EXPECT_EQ(e.find_last_of(f, 4), StringPiece::npos);
|
||||
|
||||
EXPECT_EQ(a.find_last_not_of(b), a.size()-1);
|
||||
@ -509,21 +454,11 @@ TEST(StringPiece, STL2) {
|
||||
EXPECT_EQ(a.find_last_not_of(b, 3), 3);
|
||||
EXPECT_EQ(a.find_last_not_of(b, 2), StringPiece::npos);
|
||||
// empty string nonsense
|
||||
EXPECT_EQ(f.find_last_not_of(d), f.size()-1);
|
||||
EXPECT_EQ(f.find_last_not_of(e), f.size()-1);
|
||||
EXPECT_EQ(f.find_last_not_of(d, 4), 4);
|
||||
EXPECT_EQ(f.find_last_not_of(e, 4), 4);
|
||||
EXPECT_EQ(d.find_last_not_of(d), StringPiece::npos);
|
||||
EXPECT_EQ(d.find_last_not_of(e), StringPiece::npos);
|
||||
EXPECT_EQ(e.find_last_not_of(d), StringPiece::npos);
|
||||
EXPECT_EQ(e.find_last_not_of(e), StringPiece::npos);
|
||||
EXPECT_EQ(d.find_last_not_of(f), StringPiece::npos);
|
||||
EXPECT_EQ(e.find_last_not_of(f), StringPiece::npos);
|
||||
EXPECT_EQ(d.find_last_not_of(d, 4), StringPiece::npos);
|
||||
EXPECT_EQ(d.find_last_not_of(e, 4), StringPiece::npos);
|
||||
EXPECT_EQ(e.find_last_not_of(d, 4), StringPiece::npos);
|
||||
EXPECT_EQ(e.find_last_not_of(e, 4), StringPiece::npos);
|
||||
EXPECT_EQ(d.find_last_not_of(f, 4), StringPiece::npos);
|
||||
EXPECT_EQ(e.find_last_not_of(f, 4), StringPiece::npos);
|
||||
|
||||
EXPECT_EQ(h.find_last_not_of('x'), h.size() - 1);
|
||||
@ -533,9 +468,7 @@ TEST(StringPiece, STL2) {
|
||||
EXPECT_EQ(h.find_last_not_of('=', 2), StringPiece::npos);
|
||||
EXPECT_EQ(b.find_last_not_of('b', 1), 0);
|
||||
// empty string nonsense
|
||||
EXPECT_EQ(d.find_last_not_of('x'), StringPiece::npos);
|
||||
EXPECT_EQ(e.find_last_not_of('x'), StringPiece::npos);
|
||||
EXPECT_EQ(d.find_last_not_of('\0'), StringPiece::npos);
|
||||
EXPECT_EQ(e.find_last_not_of('\0'), StringPiece::npos);
|
||||
|
||||
EXPECT_EQ(a.substr(0, 3), b);
|
||||
@ -546,33 +479,15 @@ TEST(StringPiece, STL2) {
|
||||
EXPECT_EQ(a.substr(3, 2), "de");
|
||||
// empty string nonsense
|
||||
EXPECT_EQ(a.substr(99, 2), e);
|
||||
EXPECT_EQ(d.substr(99), e);
|
||||
EXPECT_EQ(d.substr(0, 99), e);
|
||||
EXPECT_EQ(d.substr(99, 99), e);
|
||||
EXPECT_EQ(e.substr(99), e);
|
||||
EXPECT_EQ(e.substr(0, 99), e);
|
||||
EXPECT_EQ(e.substr(99, 99), e);
|
||||
// use of npos
|
||||
EXPECT_EQ(a.substr(0, StringPiece::npos), a);
|
||||
EXPECT_EQ(a.substr(23, StringPiece::npos), c);
|
||||
EXPECT_EQ(a.substr(StringPiece::npos, 0), e);
|
||||
EXPECT_EQ(a.substr(StringPiece::npos, 1), e);
|
||||
EXPECT_EQ(a.substr(StringPiece::npos, StringPiece::npos), e);
|
||||
|
||||
// Substring constructors.
|
||||
EXPECT_EQ(StringPiece(a, 0, 3), b);
|
||||
EXPECT_EQ(StringPiece(a, 23), c);
|
||||
EXPECT_EQ(StringPiece(a, 23, 3), c);
|
||||
EXPECT_EQ(StringPiece(a, 23, 99), c);
|
||||
EXPECT_EQ(StringPiece(a, 0), a);
|
||||
EXPECT_EQ(StringPiece(a, 3, 2), "de");
|
||||
// empty string nonsense
|
||||
EXPECT_EQ(StringPiece(d, 0, 99), e);
|
||||
// Verify that they work taking an actual string, not just a StringPiece.
|
||||
std::string a2 = a.as_string();
|
||||
EXPECT_EQ(StringPiece(a2, 0, 3), b);
|
||||
EXPECT_EQ(StringPiece(a2, 23), c);
|
||||
EXPECT_EQ(StringPiece(a2, 23, 3), c);
|
||||
EXPECT_EQ(StringPiece(a2, 23, 99), c);
|
||||
EXPECT_EQ(StringPiece(a2, 0), a);
|
||||
EXPECT_EQ(StringPiece(a2, 3, 2), "de");
|
||||
}
|
||||
|
||||
TEST(StringPiece, Custom) {
|
||||
@ -647,23 +562,7 @@ TEST(StringPiece, Custom) {
|
||||
c.remove_suffix(c.size());
|
||||
EXPECT_EQ(c, e);
|
||||
|
||||
// set
|
||||
c.set("foobar", 6);
|
||||
EXPECT_EQ(c, a);
|
||||
c.set("foobar", 0);
|
||||
EXPECT_EQ(c, e);
|
||||
c.set("foobar", 7);
|
||||
EXPECT_NE(c, a);
|
||||
|
||||
c.set("foobar");
|
||||
EXPECT_EQ(c, a);
|
||||
|
||||
c.set(static_cast<const void*>("foobar"), 6);
|
||||
EXPECT_EQ(c, a);
|
||||
c.set(static_cast<const void*>("foobar"), 0);
|
||||
EXPECT_EQ(c, e);
|
||||
c.set(static_cast<const void*>("foobar"), 7);
|
||||
EXPECT_NE(c, a);
|
||||
c = StringPiece("foobar", 7);
|
||||
|
||||
// as_string
|
||||
std::string s3(a.as_string().c_str(), 7);
|
||||
@ -680,21 +579,25 @@ TEST(StringPiece, Custom) {
|
||||
}
|
||||
|
||||
// Consume
|
||||
a.set("foobar");
|
||||
EXPECT_TRUE(a.Consume("foo"));
|
||||
EXPECT_EQ(a, "bar");
|
||||
EXPECT_FALSE(a.Consume("foo"));
|
||||
EXPECT_FALSE(a.Consume("barbar"));
|
||||
EXPECT_FALSE(a.Consume("ar"));
|
||||
EXPECT_EQ(a, "bar");
|
||||
{
|
||||
StringPiece str("foobar");
|
||||
EXPECT_TRUE(str.Consume("foo"));
|
||||
EXPECT_EQ(str, "bar");
|
||||
EXPECT_FALSE(str.Consume("foo"));
|
||||
EXPECT_FALSE(str.Consume("barbar"));
|
||||
EXPECT_FALSE(str.Consume("ar"));
|
||||
EXPECT_EQ(str, "bar");
|
||||
}
|
||||
|
||||
a.set("foobar");
|
||||
EXPECT_TRUE(a.ConsumeFromEnd("bar"));
|
||||
EXPECT_EQ(a, "foo");
|
||||
EXPECT_FALSE(a.ConsumeFromEnd("bar"));
|
||||
EXPECT_FALSE(a.ConsumeFromEnd("foofoo"));
|
||||
EXPECT_FALSE(a.ConsumeFromEnd("fo"));
|
||||
EXPECT_EQ(a, "foo");
|
||||
{
|
||||
StringPiece str("foobar");
|
||||
EXPECT_TRUE(str.ConsumeFromEnd("bar"));
|
||||
EXPECT_EQ(str, "foo");
|
||||
EXPECT_FALSE(str.ConsumeFromEnd("bar"));
|
||||
EXPECT_FALSE(str.ConsumeFromEnd("foofoo"));
|
||||
EXPECT_FALSE(str.ConsumeFromEnd("fo"));
|
||||
EXPECT_EQ(str, "foo");
|
||||
}
|
||||
}
|
||||
|
||||
TEST(StringPiece, Contains) {
|
||||
@ -713,10 +616,6 @@ TEST(StringPiece, NullInput) {
|
||||
EXPECT_EQ(s.data(), (const char*)nullptr);
|
||||
EXPECT_EQ(s.size(), 0);
|
||||
|
||||
s.set(nullptr);
|
||||
EXPECT_EQ(s.data(), (const char*)nullptr);
|
||||
EXPECT_EQ(s.size(), 0);
|
||||
|
||||
// .ToString() on a StringPiece with nullptr should produce the empty string.
|
||||
EXPECT_EQ("", s.ToString());
|
||||
EXPECT_EQ("", s.as_string());
|
||||
|
@ -162,7 +162,7 @@ std::string StringPrintfVector(const char* format,
|
||||
// that accepts an array of arguments. The best I can do is stick
|
||||
// this COMPILE_ASSERT right next to the actual statement.
|
||||
|
||||
GOOGLE_COMPILE_ASSERT(kStringPrintfVectorMaxArgs == 32, arg_count_mismatch);
|
||||
static_assert(kStringPrintfVectorMaxArgs == 32, "arg_count_mismatch");
|
||||
return StringPrintf(format,
|
||||
cstr[0], cstr[1], cstr[2], cstr[3], cstr[4],
|
||||
cstr[5], cstr[6], cstr[7], cstr[8], cstr[9],
|
||||
|
@ -545,7 +545,7 @@ static inline size_t CEscapedLength(StringPiece src) {
|
||||
};
|
||||
|
||||
size_t escaped_len = 0;
|
||||
for (int i = 0; i < src.size(); ++i) {
|
||||
for (StringPiece::size_type i = 0; i < src.size(); ++i) {
|
||||
unsigned char c = static_cast<unsigned char>(src[i]);
|
||||
escaped_len += c_escaped_len[c];
|
||||
}
|
||||
@ -569,7 +569,7 @@ void CEscapeAndAppend(StringPiece src, std::string *dest) {
|
||||
dest->resize(cur_dest_len + escaped_len);
|
||||
char* append_ptr = &(*dest)[cur_dest_len];
|
||||
|
||||
for (int i = 0; i < src.size(); ++i) {
|
||||
for (StringPiece::size_type i = 0; i < src.size(); ++i) {
|
||||
unsigned char c = static_cast<unsigned char>(src[i]);
|
||||
switch (c) {
|
||||
case '\n': *append_ptr++ = '\\'; *append_ptr++ = 'n'; break;
|
||||
@ -1244,7 +1244,7 @@ char* DoubleToBuffer(double value, char* buffer) {
|
||||
// platforms these days. Just in case some system exists where DBL_DIG
|
||||
// is significantly larger -- and risks overflowing our buffer -- we have
|
||||
// this assert.
|
||||
GOOGLE_COMPILE_ASSERT(DBL_DIG < 20, DBL_DIG_is_too_big);
|
||||
static_assert(DBL_DIG < 20, "DBL_DIG_is_too_big");
|
||||
|
||||
if (value == std::numeric_limits<double>::infinity()) {
|
||||
strcpy(buffer, "inf");
|
||||
@ -1362,7 +1362,7 @@ char* FloatToBuffer(float value, char* buffer) {
|
||||
// platforms these days. Just in case some system exists where FLT_DIG
|
||||
// is significantly larger -- and risks overflowing our buffer -- we have
|
||||
// this assert.
|
||||
GOOGLE_COMPILE_ASSERT(FLT_DIG < 10, FLT_DIG_is_too_big);
|
||||
static_assert(FLT_DIG < 10, "FLT_DIG_is_too_big");
|
||||
|
||||
if (value == std::numeric_limits<double>::infinity()) {
|
||||
strcpy(buffer, "inf");
|
||||
@ -1619,7 +1619,8 @@ int GlobalReplaceSubstring(const std::string &substring,
|
||||
std::string tmp;
|
||||
int num_replacements = 0;
|
||||
int pos = 0;
|
||||
for (int match_pos = s->find(substring.data(), pos, substring.length());
|
||||
for (StringPiece::size_type match_pos =
|
||||
s->find(substring.data(), pos, substring.length());
|
||||
match_pos != std::string::npos; pos = match_pos + substring.length(),
|
||||
match_pos = s->find(substring.data(), pos, substring.length())) {
|
||||
++num_replacements;
|
||||
|
@ -377,14 +377,14 @@ inline uint32 strtou32(const char *nptr, char **endptr, int base) {
|
||||
// For now, long long is 64-bit on all the platforms we care about, so these
|
||||
// functions can simply pass the call to strto[u]ll.
|
||||
inline int64 strto64(const char *nptr, char **endptr, int base) {
|
||||
GOOGLE_COMPILE_ASSERT(sizeof(int64) == sizeof(long long),
|
||||
sizeof_int64_is_not_sizeof_long_long);
|
||||
static_assert(sizeof(int64) == sizeof(long long),
|
||||
"sizeof_int64_is_not_sizeof_long_long");
|
||||
return strtoll(nptr, endptr, base);
|
||||
}
|
||||
|
||||
inline uint64 strtou64(const char *nptr, char **endptr, int base) {
|
||||
GOOGLE_COMPILE_ASSERT(sizeof(uint64) == sizeof(unsigned long long),
|
||||
sizeof_uint64_is_not_sizeof_long_long);
|
||||
static_assert(sizeof(uint64) == sizeof(unsigned long long),
|
||||
"sizeof_uint64_is_not_sizeof_long_long");
|
||||
return strtoull(nptr, endptr, base);
|
||||
}
|
||||
|
||||
|
@ -74,7 +74,7 @@ void ObjectWriter::RenderDataPieceTo(const DataPiece& data,
|
||||
break;
|
||||
}
|
||||
case DataPiece::TYPE_BYTES: {
|
||||
ow->RenderBytes(name, data.ToBytes().ValueOrDie());
|
||||
ow->RenderBytes(name, data.ToBytes().value());
|
||||
break;
|
||||
}
|
||||
case DataPiece::TYPE_NULL: {
|
||||
|
@ -253,7 +253,7 @@ inline util::Status WriteBytes(int field_number, const DataPiece& data,
|
||||
CodedOutputStream* stream) {
|
||||
util::StatusOr<std::string> c = data.ToBytes();
|
||||
if (c.ok()) {
|
||||
WireFormatLite::WriteBytes(field_number, c.ValueOrDie(), stream);
|
||||
WireFormatLite::WriteBytes(field_number, c.value(), stream);
|
||||
}
|
||||
return c.status();
|
||||
}
|
||||
|
@ -436,7 +436,7 @@ void ProtoStreamObjectWriter::AnyWriter::Event::DeepCopy() {
|
||||
StrAppend(&value_storage_, value_.str());
|
||||
value_ = DataPiece(value_storage_, value_.use_strict_base64_decoding());
|
||||
} else if (value_.type() == DataPiece::TYPE_BYTES) {
|
||||
value_storage_ = value_.ToBytes().ValueOrDie();
|
||||
value_storage_ = value_.ToBytes().value();
|
||||
value_ =
|
||||
DataPiece(value_storage_, true, value_.use_strict_base64_decoding());
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user