1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137
|
// 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 "chromeos/components/onc/onc_mapper.h"
#include <utility>
#include "base/logging.h"
#include "base/memory/ptr_util.h"
#include "base/values.h"
#include "chromeos/components/onc/onc_signature.h"
namespace chromeos {
namespace onc {
Mapper::Mapper() = default;
Mapper::~Mapper() = default;
base::Value Mapper::MapValue(const OncValueSignature& signature,
const base::Value& onc_value,
bool* error) {
switch (onc_value.type()) {
case base::Value::Type::DICT: {
if (signature.onc_type != base::Value::Type::DICT) {
*error = true;
return {};
}
return base::Value(MapObject(signature, onc_value.GetDict(), error));
}
case base::Value::Type::LIST: {
if (signature.onc_type != base::Value::Type::LIST) {
*error = true;
return {};
}
return base::Value(MapArray(signature, onc_value.GetList(), error));
}
default: {
if ((signature.onc_type == base::Value::Type::DICT) ||
(signature.onc_type == base::Value::Type::LIST)) {
*error = true;
return {};
}
return MapPrimitive(signature, onc_value, error);
}
}
}
base::Value::Dict Mapper::MapObject(const OncValueSignature& signature,
const base::Value::Dict& onc_object,
bool* error) {
base::Value::Dict result;
bool found_unknown_field = false;
MapFields(signature, onc_object, &found_unknown_field, error, &result);
if (found_unknown_field)
*error = true;
return result;
}
base::Value Mapper::MapPrimitive(const OncValueSignature& signature,
const base::Value& onc_primitive,
bool* error) {
return onc_primitive.Clone();
}
void Mapper::MapFields(const OncValueSignature& object_signature,
const base::Value::Dict& onc_object,
bool* found_unknown_field,
bool* nested_error,
base::Value::Dict* result) {
for (const auto [field_name, onc_value] : onc_object) {
bool current_field_unknown = false;
base::Value result_value = MapField(field_name, object_signature, onc_value,
¤t_field_unknown, nested_error);
if (current_field_unknown)
*found_unknown_field = true;
else if (!result_value.is_none())
result->Set(field_name, std::move(result_value));
else
DCHECK(*nested_error);
}
}
base::Value Mapper::MapField(const std::string& field_name,
const OncValueSignature& object_signature,
const base::Value& onc_value,
bool* found_unknown_field,
bool* error) {
const OncFieldSignature* field_signature =
GetFieldSignature(object_signature, field_name);
if (field_signature != nullptr) {
DCHECK(field_signature->value_signature != nullptr)
<< "Found missing value signature at field '" << field_name << "'.";
return MapValue(*field_signature->value_signature, onc_value, error);
}
DVLOG(1) << "Found unknown field name: '" << field_name << "'";
*found_unknown_field = true;
return {};
}
base::Value::List Mapper::MapArray(const OncValueSignature& array_signature,
const base::Value::List& onc_array,
bool* nested_error) {
DCHECK(array_signature.onc_array_entry_signature != nullptr)
<< "Found missing onc_array_entry_signature.";
base::Value::List result_array;
int original_index = 0;
for (const auto& entry : onc_array) {
bool error = false;
base::Value result_entry =
MapEntry(original_index, *array_signature.onc_array_entry_signature,
entry, &error);
if (!error) {
result_array.Append(std::move(result_entry));
}
*nested_error |= error;
++original_index;
}
return result_array;
}
base::Value Mapper::MapEntry(int index,
const OncValueSignature& signature,
const base::Value& onc_value,
bool* error) {
return MapValue(signature, onc_value, error);
}
} // namespace onc
} // namespace chromeos
|