chromium/base/values.cc

// Copyright 2012 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "base/values.h"

#include <array>
#include <cmath>
#include <memory>
#include <optional>
#include <ostream>
#include <string_view>
#include <tuple>
#include <utility>

#include "base/bit_cast.h"
#include "base/check.h"
#include "base/check_op.h"
#include "base/containers/checked_iterators.h"
#include "base/containers/map_util.h"
#include "base/json/json_writer.h"
#include "base/logging.h"
#include "base/memory/ptr_util.h"
#include "base/notreached.h"
#include "base/ranges/algorithm.h"
#include "base/strings/string_util.h"
#include "base/strings/utf_string_conversions.h"
#include "base/trace_event/base_tracing.h"
#include "base/tracing_buildflags.h"
#include "base/types/to_address.h"
#include "third_party/abseil-cpp/absl/types/variant.h"

#if BUILDFLAG(ENABLE_BASE_TRACING)
#include "base/trace_event/memory_usage_estimator.h"  // no-presubmit-check
#endif  // BUILDFLAG(ENABLE_BASE_TRACING)

namespace base {

namespace {

constexpr auto kTypeNames =;
static_assert;

// Helper class to enumerate the path components from a std::string_view
// without performing heap allocations. Components are simply separated
// by single dots (e.g. "foo.bar.baz"  -> ["foo", "bar", "baz"]).
//
// Usage example:
//    PathSplitter splitter(some_path);
//    while (splitter.HasNext()) {
//       std::string_view component = splitter.Next();
//       ...
//    }
//
class PathSplitter {};

std::string DebugStringImpl(ValueView value) {}

}  // namespace

// A helper used to provide templated functions for cloning to Value, and
// ValueView. This private class is used so the cloning method may have access
// to the special private constructors in Value, created specifically for
// cloning.
class Value::CloningHelper {};

// static
Value Value::FromUniquePtrValue(std::unique_ptr<Value> val) {}

// static
std::unique_ptr<Value> Value::ToUniquePtrValue(Value val) {}

Value::Value() noexcept = default;

Value::Value(Value&&) noexcept = default;

Value& Value::operator=(Value&&) noexcept = default;

Value::Value(Type type) {}

Value::Value(bool value) :{}

Value::Value(int value) :{}

Value::Value(double value)
    :{}

Value::Value(std::string_view value) :{}

Value::Value(std::u16string_view value) :{}

Value::Value(const char* value) :{}

Value::Value(const char16_t* value) :{}

Value::Value(std::string&& value) noexcept :{}

Value::Value(const std::vector<char>& value)
    :{}

Value::Value(base::span<const uint8_t> value)
    :{}

Value::Value(BlobStorage&& value) noexcept :{}

Value::Value(Dict&& value) noexcept :{}

Value::Value(List&& value) noexcept :{}

Value::Value(absl::monostate) {}

Value::Value(DoubleStorage storage) :{}

Value::DoubleStorage::DoubleStorage(double v) :{}

Value Value::Clone() const {}

Value::~Value() = default;

// static
const char* Value::GetTypeName(Value::Type type) {}

std::optional<bool> Value::GetIfBool() const {}

std::optional<int> Value::GetIfInt() const {}

std::optional<double> Value::GetIfDouble() const {}

const std::string* Value::GetIfString() const {}

std::string* Value::GetIfString() {}

const Value::BlobStorage* Value::GetIfBlob() const {}

const Value::Dict* Value::GetIfDict() const {}

Value::Dict* Value::GetIfDict() {}

const Value::List* Value::GetIfList() const {}

Value::List* Value::GetIfList() {}

bool Value::GetBool() const {}

int Value::GetInt() const {}

double Value::GetDouble() const {}

const std::string& Value::GetString() const {}

std::string& Value::GetString() {}

const Value::BlobStorage& Value::GetBlob() const {}

const Value::Dict& Value::GetDict() const {}

Value::Dict& Value::GetDict() {}

const Value::List& Value::GetList() const {}

Value::List& Value::GetList() {}

std::string Value::TakeString() && {}

Value::Dict Value::TakeDict() && {}

Value::List Value::TakeList() && {}

Value::Dict::Dict() = default;

Value::Dict::Dict(Dict&&) noexcept = default;

Value::Dict& Value::Dict::operator=(Dict&&) noexcept = default;

Value::Dict::~Dict() = default;

bool Value::Dict::empty() const {}

size_t Value::Dict::size() const {}

Value::Dict::iterator Value::Dict::begin() {}

Value::Dict::const_iterator Value::Dict::begin() const {}

Value::Dict::const_iterator Value::Dict::cbegin() const {}

Value::Dict::iterator Value::Dict::end() {}

Value::Dict::const_iterator Value::Dict::end() const {}

Value::Dict::const_iterator Value::Dict::cend() const {}

bool Value::Dict::contains(std::string_view key) const {}

void Value::Dict::clear() {}

Value::Dict::iterator Value::Dict::erase(iterator pos) {}

Value::Dict::iterator Value::Dict::erase(const_iterator pos) {}

Value::Dict Value::Dict::Clone() const {}

void Value::Dict::Merge(Dict dict) {}

const Value* Value::Dict::Find(std::string_view key) const {}

Value* Value::Dict::Find(std::string_view key) {}

std::optional<bool> Value::Dict::FindBool(std::string_view key) const {}

std::optional<int> Value::Dict::FindInt(std::string_view key) const {}

std::optional<double> Value::Dict::FindDouble(std::string_view key) const {}

const std::string* Value::Dict::FindString(std::string_view key) const {}

std::string* Value::Dict::FindString(std::string_view key) {}

const Value::BlobStorage* Value::Dict::FindBlob(std::string_view key) const {}

const Value::Dict* Value::Dict::FindDict(std::string_view key) const {}

Value::Dict* Value::Dict::FindDict(std::string_view key) {}

const Value::List* Value::Dict::FindList(std::string_view key) const {}

Value::List* Value::Dict::FindList(std::string_view key) {}

Value::Dict* Value::Dict::EnsureDict(std::string_view key) {}

Value::List* Value::Dict::EnsureList(std::string_view key) {}

Value* Value::Dict::Set(std::string_view key, Value&& value) & {}

Value* Value::Dict::Set(std::string_view key, bool value) & {}

Value* Value::Dict::Set(std::string_view key, int value) & {}

Value* Value::Dict::Set(std::string_view key, double value) & {}

Value* Value::Dict::Set(std::string_view key, std::string_view value) & {}

Value* Value::Dict::Set(std::string_view key, std::u16string_view value) & {}

Value* Value::Dict::Set(std::string_view key, const char* value) & {}

Value* Value::Dict::Set(std::string_view key, const char16_t* value) & {}

Value* Value::Dict::Set(std::string_view key, std::string&& value) & {}

Value* Value::Dict::Set(std::string_view key, BlobStorage&& value) & {}

Value* Value::Dict::Set(std::string_view key, Dict&& value) & {}

Value* Value::Dict::Set(std::string_view key, List&& value) & {}

Value::Dict&& Value::Dict::Set(std::string_view key, Value&& value) && {}

Value::Dict&& Value::Dict::Set(std::string_view key, bool value) && {}

Value::Dict&& Value::Dict::Set(std::string_view key, int value) && {}

Value::Dict&& Value::Dict::Set(std::string_view key, double value) && {}

Value::Dict&& Value::Dict::Set(std::string_view key,
                               std::string_view value) && {}

Value::Dict&& Value::Dict::Set(std::string_view key,
                               std::u16string_view value) && {}

Value::Dict&& Value::Dict::Set(std::string_view key, const char* value) && {}

Value::Dict&& Value::Dict::Set(std::string_view key, const char16_t* value) && {}

Value::Dict&& Value::Dict::Set(std::string_view key, std::string&& value) && {}

Value::Dict&& Value::Dict::Set(std::string_view key, BlobStorage&& value) && {}

Value::Dict&& Value::Dict::Set(std::string_view key, Dict&& value) && {}

Value::Dict&& Value::Dict::Set(std::string_view key, List&& value) && {}

bool Value::Dict::Remove(std::string_view key) {}

std::optional<Value> Value::Dict::Extract(std::string_view key) {}

const Value* Value::Dict::FindByDottedPath(std::string_view path) const {}

Value* Value::Dict::FindByDottedPath(std::string_view path) {}

std::optional<bool> Value::Dict::FindBoolByDottedPath(
    std::string_view path) const {}

std::optional<int> Value::Dict::FindIntByDottedPath(
    std::string_view path) const {}

std::optional<double> Value::Dict::FindDoubleByDottedPath(
    std::string_view path) const {}

const std::string* Value::Dict::FindStringByDottedPath(
    std::string_view path) const {}

std::string* Value::Dict::FindStringByDottedPath(std::string_view path) {}

const Value::BlobStorage* Value::Dict::FindBlobByDottedPath(
    std::string_view path) const {}

const Value::Dict* Value::Dict::FindDictByDottedPath(
    std::string_view path) const {}

Value::Dict* Value::Dict::FindDictByDottedPath(std::string_view path) {}

const Value::List* Value::Dict::FindListByDottedPath(
    std::string_view path) const {}

Value::List* Value::Dict::FindListByDottedPath(std::string_view path) {}

Value* Value::Dict::SetByDottedPath(std::string_view path, Value&& value) & {}

Value* Value::Dict::SetByDottedPath(std::string_view path, bool value) & {}

Value* Value::Dict::SetByDottedPath(std::string_view path, int value) & {}

Value* Value::Dict::SetByDottedPath(std::string_view path, double value) & {}

Value* Value::Dict::SetByDottedPath(std::string_view path,
                                    std::string_view value) & {}

Value* Value::Dict::SetByDottedPath(std::string_view path,
                                    std::u16string_view value) & {}

Value* Value::Dict::SetByDottedPath(std::string_view path,
                                    const char* value) & {}

Value* Value::Dict::SetByDottedPath(std::string_view path,
                                    const char16_t* value) & {}

Value* Value::Dict::SetByDottedPath(std::string_view path,
                                    std::string&& value) & {}

Value* Value::Dict::SetByDottedPath(std::string_view path,
                                    BlobStorage&& value) & {}

Value* Value::Dict::SetByDottedPath(std::string_view path, Dict&& value) & {}

Value* Value::Dict::SetByDottedPath(std::string_view path, List&& value) & {}

bool Value::Dict::RemoveByDottedPath(std::string_view path) {}

Value::Dict&& Value::Dict::SetByDottedPath(std::string_view path,
                                           Value&& value) && {}

Value::Dict&& Value::Dict::SetByDottedPath(std::string_view path,
                                           bool value) && {}

Value::Dict&& Value::Dict::SetByDottedPath(std::string_view path,
                                           int value) && {}

Value::Dict&& Value::Dict::SetByDottedPath(std::string_view path,
                                           double value) && {}

Value::Dict&& Value::Dict::SetByDottedPath(std::string_view path,
                                           std::string_view value) && {}

Value::Dict&& Value::Dict::SetByDottedPath(std::string_view path,
                                           std::u16string_view value) && {}

Value::Dict&& Value::Dict::SetByDottedPath(std::string_view path,
                                           const char* value) && {}

Value::Dict&& Value::Dict::SetByDottedPath(std::string_view path,
                                           const char16_t* value) && {}

Value::Dict&& Value::Dict::SetByDottedPath(std::string_view path,
                                           std::string&& value) && {}

Value::Dict&& Value::Dict::SetByDottedPath(std::string_view path,
                                           BlobStorage&& value) && {}

Value::Dict&& Value::Dict::SetByDottedPath(std::string_view path,
                                           Dict&& value) && {}

Value::Dict&& Value::Dict::SetByDottedPath(std::string_view path,
                                           List&& value) && {}

std::optional<Value> Value::Dict::ExtractByDottedPath(std::string_view path) {}

size_t Value::Dict::EstimateMemoryUsage() const {}

std::string Value::Dict::DebugString() const {}

#if BUILDFLAG(ENABLE_BASE_TRACING)
void Value::Dict::WriteIntoTrace(perfetto::TracedValue context) const {}
#endif  // BUILDFLAG(ENABLE_BASE_TRACING)

Value::Dict::Dict(
    const flat_map<std::string, std::unique_ptr<Value>>& storage) {}

bool operator==(const Value::Dict& lhs, const Value::Dict& rhs) {}

bool operator!=(const Value::Dict& lhs, const Value::Dict& rhs) {}

bool operator<(const Value::Dict& lhs, const Value::Dict& rhs) {}

bool operator>(const Value::Dict& lhs, const Value::Dict& rhs) {}

bool operator<=(const Value::Dict& lhs, const Value::Dict& rhs) {}

bool operator>=(const Value::Dict& lhs, const Value::Dict& rhs) {}

// static
Value::List Value::List::with_capacity(size_t capacity) {}

Value::List::List() = default;

Value::List::List(List&&) noexcept = default;

Value::List& Value::List::operator=(List&&) noexcept = default;

Value::List::~List() = default;

bool Value::List::empty() const {}

size_t Value::List::size() const {}

Value::List::iterator Value::List::begin() {}

Value::List::const_iterator Value::List::begin() const {}

Value::List::const_iterator Value::List::cbegin() const {}

Value::List::iterator Value::List::end() {}

Value::List::const_iterator Value::List::end() const {}

Value::List::const_iterator Value::List::cend() const {}

Value::List::reverse_iterator Value::List::rend() {}

Value::List::const_reverse_iterator Value::List::rend() const {}

Value::List::reverse_iterator Value::List::rbegin() {}

Value::List::const_reverse_iterator Value::List::rbegin() const {}

const Value& Value::List::front() const {}

Value& Value::List::front() {}

const Value& Value::List::back() const {}

Value& Value::List::back() {}

void Value::List::reserve(size_t capacity) {}

void Value::List::resize(size_t new_size) {}

const Value& Value::List::operator[](size_t index) const {}

Value& Value::List::operator[](size_t index) {}

void Value::List::clear() {}

Value::List::iterator Value::List::erase(iterator pos) {}

Value::List::const_iterator Value::List::erase(const_iterator pos) {}

Value::List::iterator Value::List::erase(iterator first, iterator last) {}

Value::List::const_iterator Value::List::erase(const_iterator first,
                                               const_iterator last) {}

Value::List Value::List::Clone() const {}

void Value::List::Append(Value&& value) & {}

void Value::List::Append(bool value) & {}

void Value::List::Append(int value) & {}

void Value::List::Append(double value) & {}

void Value::List::Append(std::string_view value) & {}

void Value::List::Append(std::u16string_view value) & {}

void Value::List::Append(const char* value) & {}

void Value::List::Append(const char16_t* value) & {}

void Value::List::Append(std::string&& value) & {}

void Value::List::Append(BlobStorage&& value) & {}

void Value::List::Append(Dict&& value) & {}

void Value::List::Append(List&& value) & {}

Value::List&& Value::List::Append(Value&& value) && {}

Value::List&& Value::List::Append(bool value) && {}

Value::List&& Value::List::Append(int value) && {}

Value::List&& Value::List::Append(double value) && {}

Value::List&& Value::List::Append(std::string_view value) && {}

Value::List&& Value::List::Append(std::u16string_view value) && {}

Value::List&& Value::List::Append(const char* value) && {}

Value::List&& Value::List::Append(const char16_t* value) && {}

Value::List&& Value::List::Append(std::string&& value) && {}

Value::List&& Value::List::Append(BlobStorage&& value) && {}

Value::List&& Value::List::Append(Dict&& value) && {}

Value::List&& Value::List::Append(List&& value) && {}

Value::List::iterator Value::List::Insert(const_iterator pos, Value&& value) {}

size_t Value::List::EraseValue(const Value& value) {}

size_t Value::List::EstimateMemoryUsage() const {}

std::string Value::List::DebugString() const {}

#if BUILDFLAG(ENABLE_BASE_TRACING)
void Value::List::WriteIntoTrace(perfetto::TracedValue context) const {}
#endif  // BUILDFLAG(ENABLE_BASE_TRACING)

Value::List::List(const std::vector<Value>& storage) {}

bool operator==(const Value::List& lhs, const Value::List& rhs) {}

bool operator!=(const Value::List& lhs, const Value::List& rhs) {}

bool operator<(const Value::List& lhs, const Value::List& rhs) {}

bool operator>(const Value::List& lhs, const Value::List& rhs) {}

bool operator<=(const Value::List& lhs, const Value::List& rhs) {}

bool operator>=(const Value::List& lhs, const Value::List& rhs) {}

bool operator==(const Value& lhs, const Value& rhs) {}

bool operator!=(const Value& lhs, const Value& rhs) {}

bool operator<(const Value& lhs, const Value& rhs) {}

bool operator>(const Value& lhs, const Value& rhs) {}

bool operator<=(const Value& lhs, const Value& rhs) {}

bool operator>=(const Value& lhs, const Value& rhs) {}

bool operator==(const Value& lhs, bool rhs) {}

bool operator==(const Value& lhs, int rhs) {}

bool operator==(const Value& lhs, double rhs) {}

bool operator==(const Value& lhs, std::string_view rhs) {}

bool operator==(const Value& lhs, const Value::Dict& rhs) {}

bool operator==(const Value& lhs, const Value::List& rhs) {}

size_t Value::EstimateMemoryUsage() const {}

std::string Value::DebugString() const {}

#if BUILDFLAG(ENABLE_BASE_TRACING)
void Value::WriteIntoTrace(perfetto::TracedValue context) const {}
#endif  // BUILDFLAG(ENABLE_BASE_TRACING)

ValueView::ValueView(const Value& value)
    :{}

Value ValueView::ToValue() const {}

ValueSerializer::~ValueSerializer() = default;

ValueDeserializer::~ValueDeserializer() = default;

std::ostream& operator<<(std::ostream& out, const Value& value) {}

std::ostream& operator<<(std::ostream& out, const Value::Dict& dict) {}

std::ostream& operator<<(std::ostream& out, const Value::List& list) {}

std::ostream& operator<<(std::ostream& out, const Value::Type& type) {}

}  // namespace base