| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "base/values.h" | 5 #include "base/values.h" |
| 6 | 6 |
| 7 #include <string.h> | 7 #include <string.h> |
| 8 | 8 |
| 9 #include <algorithm> | 9 #include <algorithm> |
| 10 #include <cmath> | 10 #include <cmath> |
| (...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 62 std::unique_ptr<Value> CopyWithoutEmptyChildren(const Value& node) { | 62 std::unique_ptr<Value> CopyWithoutEmptyChildren(const Value& node) { |
| 63 switch (node.GetType()) { | 63 switch (node.GetType()) { |
| 64 case Value::Type::LIST: | 64 case Value::Type::LIST: |
| 65 return CopyListWithoutEmptyChildren(static_cast<const ListValue&>(node)); | 65 return CopyListWithoutEmptyChildren(static_cast<const ListValue&>(node)); |
| 66 | 66 |
| 67 case Value::Type::DICTIONARY: | 67 case Value::Type::DICTIONARY: |
| 68 return CopyDictionaryWithoutEmptyChildren( | 68 return CopyDictionaryWithoutEmptyChildren( |
| 69 static_cast<const DictionaryValue&>(node)); | 69 static_cast<const DictionaryValue&>(node)); |
| 70 | 70 |
| 71 default: | 71 default: |
| 72 return node.CreateDeepCopy(); | 72 return MakeUnique<Value>(node); |
| 73 } | 73 } |
| 74 } | 74 } |
| 75 | 75 |
| 76 } // namespace | 76 } // namespace |
| 77 | 77 |
| 78 // static | 78 // static |
| 79 std::unique_ptr<Value> Value::CreateNullValue() { | 79 std::unique_ptr<Value> Value::CreateNullValue() { |
| 80 return WrapUnique(new Value(Type::NONE)); | 80 return WrapUnique(new Value(Type::NONE)); |
| 81 } | 81 } |
| 82 | 82 |
| (...skipping 251 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 334 | 334 |
| 335 bool Value::GetAsDictionary(const DictionaryValue** out_value) const { | 335 bool Value::GetAsDictionary(const DictionaryValue** out_value) const { |
| 336 if (out_value && is_dict()) { | 336 if (out_value && is_dict()) { |
| 337 *out_value = static_cast<const DictionaryValue*>(this); | 337 *out_value = static_cast<const DictionaryValue*>(this); |
| 338 return true; | 338 return true; |
| 339 } | 339 } |
| 340 return is_dict(); | 340 return is_dict(); |
| 341 } | 341 } |
| 342 | 342 |
| 343 Value* Value::DeepCopy() const { | 343 Value* Value::DeepCopy() const { |
| 344 // This method should only be getting called for null Values--all subclasses | 344 return new Value(*this); |
| 345 // need to provide their own implementation;. | |
| 346 switch (type()) { | |
| 347 case Type::NONE: | |
| 348 return CreateNullValue().release(); | |
| 349 | |
| 350 case Type::BOOLEAN: | |
| 351 return new Value(bool_value_); | |
| 352 case Type::INTEGER: | |
| 353 return new Value(int_value_); | |
| 354 case Type::DOUBLE: | |
| 355 return new Value(double_value_); | |
| 356 case Type::STRING: | |
| 357 return new Value(*string_value_); | |
| 358 // For now, make BinaryValues for backward-compatibility. Convert to | |
| 359 // Value when that code is deleted. | |
| 360 case Type::BINARY: | |
| 361 return new Value(*binary_value_); | |
| 362 | |
| 363 // TODO(crbug.com/646113): Clean this up when DictionaryValue and ListValue | |
| 364 // are completely inlined. | |
| 365 case Type::DICTIONARY: { | |
| 366 DictionaryValue* result = new DictionaryValue; | |
| 367 | |
| 368 for (const auto& current_entry : **dict_ptr_) { | |
| 369 result->SetWithoutPathExpansion(current_entry.first, | |
| 370 current_entry.second->CreateDeepCopy()); | |
| 371 } | |
| 372 | |
| 373 return result; | |
| 374 } | |
| 375 | |
| 376 case Type::LIST: { | |
| 377 ListValue* result = new ListValue; | |
| 378 | |
| 379 for (const auto& entry : *list_) | |
| 380 result->Append(entry->CreateDeepCopy()); | |
| 381 | |
| 382 return result; | |
| 383 } | |
| 384 | |
| 385 default: | |
| 386 NOTREACHED(); | |
| 387 return nullptr; | |
| 388 } | |
| 389 } | 345 } |
| 390 | 346 |
| 391 std::unique_ptr<Value> Value::CreateDeepCopy() const { | 347 std::unique_ptr<Value> Value::CreateDeepCopy() const { |
| 392 return WrapUnique(DeepCopy()); | 348 return MakeUnique<Value>(*this); |
| 393 } | 349 } |
| 394 | 350 |
| 395 bool operator==(const Value& lhs, const Value& rhs) { | 351 bool operator==(const Value& lhs, const Value& rhs) { |
| 396 if (lhs.type_ != rhs.type_) | 352 if (lhs.type_ != rhs.type_) |
| 397 return false; | 353 return false; |
| 398 | 354 |
| 399 switch (lhs.type_) { | 355 switch (lhs.type_) { |
| 400 case Value::Type::NONE: | 356 case Value::Type::NONE: |
| 401 return true; | 357 return true; |
| 402 case Value::Type::BOOLEAN: | 358 case Value::Type::BOOLEAN: |
| (...skipping 132 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 535 InternalCopyFundamentalValue(that); | 491 InternalCopyFundamentalValue(that); |
| 536 return; | 492 return; |
| 537 | 493 |
| 538 case Type::STRING: | 494 case Type::STRING: |
| 539 string_value_.Init(*that.string_value_); | 495 string_value_.Init(*that.string_value_); |
| 540 return; | 496 return; |
| 541 case Type::BINARY: | 497 case Type::BINARY: |
| 542 binary_value_.Init(*that.binary_value_); | 498 binary_value_.Init(*that.binary_value_); |
| 543 return; | 499 return; |
| 544 // DictStorage and ListStorage are move-only types due to the presence of | 500 // DictStorage and ListStorage are move-only types due to the presence of |
| 545 // unique_ptrs. This is why the call to |CreateDeepCopy| is necessary here. | 501 // unique_ptrs. This is why the explicit copy of every element is necessary |
| 502 // here. |
| 546 // TODO(crbug.com/646113): Clean this up when DictStorage and ListStorage | 503 // TODO(crbug.com/646113): Clean this up when DictStorage and ListStorage |
| 547 // can be copied directly. | 504 // can be copied directly. |
| 548 case Type::DICTIONARY: | 505 case Type::DICTIONARY: |
| 549 dict_ptr_.Init(std::move(*that.CreateDeepCopy()->dict_ptr_)); | 506 dict_ptr_.Init(MakeUnique<DictStorage>()); |
| 507 for (const auto& it : **that.dict_ptr_) { |
| 508 (*dict_ptr_) |
| 509 ->emplace_hint((*dict_ptr_)->end(), it.first, |
| 510 MakeUnique<Value>(*it.second)); |
| 511 } |
| 550 return; | 512 return; |
| 551 case Type::LIST: | 513 case Type::LIST: |
| 552 list_.Init(std::move(*that.CreateDeepCopy()->list_)); | 514 list_.Init(); |
| 515 list_->reserve(that.list_->size()); |
| 516 for (const auto& it : *that.list_) |
| 517 list_->push_back(MakeUnique<Value>(*it)); |
| 553 return; | 518 return; |
| 554 } | 519 } |
| 555 } | 520 } |
| 556 | 521 |
| 557 void Value::InternalMoveConstructFrom(Value&& that) { | 522 void Value::InternalMoveConstructFrom(Value&& that) { |
| 558 type_ = that.type_; | 523 type_ = that.type_; |
| 559 | 524 |
| 560 switch (type_) { | 525 switch (type_) { |
| 561 case Type::NONE: | 526 case Type::NONE: |
| 562 case Type::BOOLEAN: | 527 case Type::BOOLEAN: |
| (...skipping 30 matching lines...) Expand all Loading... |
| 593 InternalCopyFundamentalValue(that); | 558 InternalCopyFundamentalValue(that); |
| 594 return; | 559 return; |
| 595 | 560 |
| 596 case Type::STRING: | 561 case Type::STRING: |
| 597 *string_value_ = *that.string_value_; | 562 *string_value_ = *that.string_value_; |
| 598 return; | 563 return; |
| 599 case Type::BINARY: | 564 case Type::BINARY: |
| 600 *binary_value_ = *that.binary_value_; | 565 *binary_value_ = *that.binary_value_; |
| 601 return; | 566 return; |
| 602 // DictStorage and ListStorage are move-only types due to the presence of | 567 // DictStorage and ListStorage are move-only types due to the presence of |
| 603 // unique_ptrs. This is why the call to |CreateDeepCopy| is necessary here. | 568 // unique_ptrs. This is why the explicit call to the copy constructor is |
| 569 // necessary here. |
| 604 // TODO(crbug.com/646113): Clean this up when DictStorage and ListStorage | 570 // TODO(crbug.com/646113): Clean this up when DictStorage and ListStorage |
| 605 // can be copied directly. | 571 // can be copied directly. |
| 606 case Type::DICTIONARY: | 572 case Type::DICTIONARY: |
| 607 *dict_ptr_ = std::move(*that.CreateDeepCopy()->dict_ptr_); | 573 *dict_ptr_ = std::move(*Value(that).dict_ptr_); |
| 608 return; | 574 return; |
| 609 case Type::LIST: | 575 case Type::LIST: |
| 610 *list_ = std::move(*that.CreateDeepCopy()->list_); | 576 *list_ = std::move(*Value(that).list_); |
| 611 return; | 577 return; |
| 612 } | 578 } |
| 613 } | 579 } |
| 614 | 580 |
| 615 void Value::InternalCleanup() { | 581 void Value::InternalCleanup() { |
| 616 switch (type_) { | 582 switch (type_) { |
| 617 case Type::NONE: | 583 case Type::NONE: |
| 618 case Type::BOOLEAN: | 584 case Type::BOOLEAN: |
| 619 case Type::INTEGER: | 585 case Type::INTEGER: |
| 620 case Type::DOUBLE: | 586 case Type::DOUBLE: |
| (...skipping 445 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1066 // Check whether we have to merge dictionaries. | 1032 // Check whether we have to merge dictionaries. |
| 1067 if (merge_value->IsType(Value::Type::DICTIONARY)) { | 1033 if (merge_value->IsType(Value::Type::DICTIONARY)) { |
| 1068 DictionaryValue* sub_dict; | 1034 DictionaryValue* sub_dict; |
| 1069 if (GetDictionaryWithoutPathExpansion(it.key(), &sub_dict)) { | 1035 if (GetDictionaryWithoutPathExpansion(it.key(), &sub_dict)) { |
| 1070 sub_dict->MergeDictionary( | 1036 sub_dict->MergeDictionary( |
| 1071 static_cast<const DictionaryValue*>(merge_value)); | 1037 static_cast<const DictionaryValue*>(merge_value)); |
| 1072 continue; | 1038 continue; |
| 1073 } | 1039 } |
| 1074 } | 1040 } |
| 1075 // All other cases: Make a copy and hook it up. | 1041 // All other cases: Make a copy and hook it up. |
| 1076 SetWithoutPathExpansion(it.key(), | 1042 SetWithoutPathExpansion(it.key(), MakeUnique<Value>(*merge_value)); |
| 1077 base::WrapUnique(merge_value->DeepCopy())); | |
| 1078 } | 1043 } |
| 1079 } | 1044 } |
| 1080 | 1045 |
| 1081 void DictionaryValue::Swap(DictionaryValue* other) { | 1046 void DictionaryValue::Swap(DictionaryValue* other) { |
| 1082 CHECK(other->is_dict()); | 1047 CHECK(other->is_dict()); |
| 1083 dict_ptr_->swap(*(other->dict_ptr_)); | 1048 dict_ptr_->swap(*(other->dict_ptr_)); |
| 1084 } | 1049 } |
| 1085 | 1050 |
| 1086 DictionaryValue::Iterator::Iterator(const DictionaryValue& target) | 1051 DictionaryValue::Iterator::Iterator(const DictionaryValue& target) |
| 1087 : target_(target), it_((*target.dict_ptr_)->begin()) {} | 1052 : target_(target), it_((*target.dict_ptr_)->begin()) {} |
| 1088 | 1053 |
| 1089 DictionaryValue::Iterator::Iterator(const Iterator& other) = default; | 1054 DictionaryValue::Iterator::Iterator(const Iterator& other) = default; |
| 1090 | 1055 |
| 1091 DictionaryValue::Iterator::~Iterator() {} | 1056 DictionaryValue::Iterator::~Iterator() {} |
| 1092 | 1057 |
| 1093 DictionaryValue* DictionaryValue::DeepCopy() const { | 1058 DictionaryValue* DictionaryValue::DeepCopy() const { |
| 1094 return static_cast<DictionaryValue*>(Value::DeepCopy()); | 1059 return new DictionaryValue(*this); |
| 1095 } | 1060 } |
| 1096 | 1061 |
| 1097 std::unique_ptr<DictionaryValue> DictionaryValue::CreateDeepCopy() const { | 1062 std::unique_ptr<DictionaryValue> DictionaryValue::CreateDeepCopy() const { |
| 1098 return WrapUnique(DeepCopy()); | 1063 return MakeUnique<DictionaryValue>(*this); |
| 1099 } | 1064 } |
| 1100 | 1065 |
| 1101 ///////////////////// ListValue //////////////////// | 1066 ///////////////////// ListValue //////////////////// |
| 1102 | 1067 |
| 1103 // static | 1068 // static |
| 1104 std::unique_ptr<ListValue> ListValue::From(std::unique_ptr<Value> value) { | 1069 std::unique_ptr<ListValue> ListValue::From(std::unique_ptr<Value> value) { |
| 1105 ListValue* out; | 1070 ListValue* out; |
| 1106 if (value && value->GetAsList(&out)) { | 1071 if (value && value->GetAsList(&out)) { |
| 1107 ignore_result(value.release()); | 1072 ignore_result(value.release()); |
| 1108 return WrapUnique(out); | 1073 return WrapUnique(out); |
| (...skipping 242 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1351 return *entry == value; | 1316 return *entry == value; |
| 1352 }); | 1317 }); |
| 1353 } | 1318 } |
| 1354 | 1319 |
| 1355 void ListValue::Swap(ListValue* other) { | 1320 void ListValue::Swap(ListValue* other) { |
| 1356 CHECK(other->is_list()); | 1321 CHECK(other->is_list()); |
| 1357 list_->swap(*(other->list_)); | 1322 list_->swap(*(other->list_)); |
| 1358 } | 1323 } |
| 1359 | 1324 |
| 1360 ListValue* ListValue::DeepCopy() const { | 1325 ListValue* ListValue::DeepCopy() const { |
| 1361 return static_cast<ListValue*>(Value::DeepCopy()); | 1326 return new ListValue(*this); |
| 1362 } | 1327 } |
| 1363 | 1328 |
| 1364 std::unique_ptr<ListValue> ListValue::CreateDeepCopy() const { | 1329 std::unique_ptr<ListValue> ListValue::CreateDeepCopy() const { |
| 1365 return WrapUnique(DeepCopy()); | 1330 return MakeUnique<ListValue>(*this); |
| 1366 } | 1331 } |
| 1367 | 1332 |
| 1368 ValueSerializer::~ValueSerializer() { | 1333 ValueSerializer::~ValueSerializer() { |
| 1369 } | 1334 } |
| 1370 | 1335 |
| 1371 ValueDeserializer::~ValueDeserializer() { | 1336 ValueDeserializer::~ValueDeserializer() { |
| 1372 } | 1337 } |
| 1373 | 1338 |
| 1374 std::ostream& operator<<(std::ostream& out, const Value& value) { | 1339 std::ostream& operator<<(std::ostream& out, const Value& value) { |
| 1375 std::string json; | 1340 std::string json; |
| 1376 JSONWriter::WriteWithOptions(value, JSONWriter::OPTIONS_PRETTY_PRINT, &json); | 1341 JSONWriter::WriteWithOptions(value, JSONWriter::OPTIONS_PRETTY_PRINT, &json); |
| 1377 return out << json; | 1342 return out << json; |
| 1378 } | 1343 } |
| 1379 | 1344 |
| 1380 std::ostream& operator<<(std::ostream& out, const Value::Type& type) { | 1345 std::ostream& operator<<(std::ostream& out, const Value::Type& type) { |
| 1381 if (static_cast<int>(type) < 0 || | 1346 if (static_cast<int>(type) < 0 || |
| 1382 static_cast<size_t>(type) >= arraysize(kTypeNames)) | 1347 static_cast<size_t>(type) >= arraysize(kTypeNames)) |
| 1383 return out << "Invalid Type (index = " << static_cast<int>(type) << ")"; | 1348 return out << "Invalid Type (index = " << static_cast<int>(type) << ")"; |
| 1384 return out << Value::GetTypeName(type); | 1349 return out << Value::GetTypeName(type); |
| 1385 } | 1350 } |
| 1386 | 1351 |
| 1387 } // namespace base | 1352 } // namespace base |
| OLD | NEW |