Index: components/sync/protocol/proto_size_estimations.cc |
diff --git a/components/sync/protocol/proto_size_estimations.cc b/components/sync/protocol/proto_size_estimations.cc |
new file mode 100644 |
index 0000000000000000000000000000000000000000..40ccb162a30e206c6d8079bc8218ec111a8be5cd |
--- /dev/null |
+++ b/components/sync/protocol/proto_size_estimations.cc |
@@ -0,0 +1,166 @@ |
+// Copyright (c) 2016 The Chromium Authors. All rights reserved. |
+// Use of this source code is governed by a BSD-style license that can be |
+// found in the LICENSE file. |
+ |
+// Keep this file in sync with the .proto files in this directory. |
+ |
+#include "components/sync/protocol/proto_size_estimations.h" |
+ |
+#include "base/trace_event/memory_usage_estimators.h" |
+#include "components/sync/protocol/proto_visitors.h" |
+ |
+namespace { |
+ |
+using base::trace_event::EstimateMemoryUsage; |
+ |
+class MemoryUsageVisitor { |
+ public: |
+ MemoryUsageVisitor(): memory_usage_(0) {} |
+ |
+ size_t memory_usage() const { return memory_usage_; } |
+ |
+ template <class P> |
+ void VisitBytes(P& proto, const char* field_name, |
+ const std::string& field_value) { |
+ // Delegate to Visit(const std::string&) below. |
+ Visit(proto, field_name, field_value); |
+ } |
+ |
+ template <class P, class E> |
+ void VisitEnum(P& proto, const char* field_name, E field_value) {} |
+ |
+ template <class P, class F> |
+ typename std::enable_if< |
+ std::is_base_of<google::protobuf::MessageLite, F>::value |
+ >::type |
+ Visit(P& proto, const char* field_name, const F& field_value) { |
+ memory_usage_ += sizeof(F) + EstimateMemoryUsage(field_value); |
+ } |
+ |
+ template <class P, class F> |
+ typename std::enable_if< |
+ !std::is_base_of<google::protobuf::MessageLite, F>::value |
+ >::type |
+ Visit(P& proto, const char* field_name, const F& field_value) { |
+ memory_usage_ += EstimateMemoryUsage(field_value); |
+ } |
+ |
+ template <class P> |
+ void Visit(P& proto, const char* field_name, |
+ const std::string& field_value) { |
+ // All strings are of type ArenaStringPtr, which essentially |
+ // is std::string*. |
+ memory_usage_ += sizeof(std::string) + EstimateMemoryUsage(field_value); |
+ } |
+ |
+ template <class P, class F> |
+ void Visit(P& proto, const char* field_name, |
+ const google::protobuf::RepeatedPtrField<F>& field_values) { |
+ // Can't use SpaceUsedExcludingSelf() because it will end up calling |
+ // undefined TypeHandler::SpaceUsed() method. |
+ memory_usage_ += field_values.Capacity() ? sizeof(void*) : 0; // header |
+ memory_usage_ += field_values.Capacity() * sizeof(void*); |
+ for (const auto& field_value: field_values) { |
+ memory_usage_ += sizeof(F) + EstimateMemoryUsage(field_value); |
+ } |
+ } |
+ |
+ template <class P, class F> |
+ void Visit(P& proto, const char* field_name, |
+ const google::protobuf::RepeatedField<F>& field_values) { |
+ memory_usage_ += field_values.SpaceUsedExcludingSelf(); |
+ for (const auto& field_value: field_values) { |
+ memory_usage_ += EstimateMemoryUsage(field_value); |
+ } |
+ } |
+ |
+ private: |
+ size_t memory_usage_; |
+}; |
+ |
+} // namespace |
+ |
+namespace sync_pb { |
+ |
+template <class P> |
+size_t EstimateMemoryUsage(const P& proto) { |
+ MemoryUsageVisitor visitor; |
+ syncer::VisitProtoFields(visitor, proto); |
+ return visitor.memory_usage(); |
+} |
+ |
+// Explicit instantiations |
+ |
+#define INSTANTIATE(Proto) \ |
+ template size_t EstimateMemoryUsage<Proto>(const Proto&); |
+ |
+INSTANTIATE(EntitySpecifics) |
+INSTANTIATE(AttachmentMetadata) |
+INSTANTIATE(DataTypeContext) |
+ |
+// TODO(dskiba): needed only for testing, remove |
+ |
+INSTANTIATE(EncryptedData) |
+INSTANTIATE(AppListSpecifics) |
+INSTANTIATE(AppNotificationSettings) |
+INSTANTIATE(LinkedAppIconInfo) |
+INSTANTIATE(ArcPackageSpecifics) |
+INSTANTIATE(SessionHeader) |
+INSTANTIATE(SessionTab) |
+INSTANTIATE(SessionWindow) |
+INSTANTIATE(TabNavigation) |
+INSTANTIATE(NavigationRedirect) |
+INSTANTIATE(PasswordSpecificsData) |
+INSTANTIATE(GlobalIdDirective) |
+INSTANTIATE(TimeRangeDirective) |
+INSTANTIATE(SessionSpecifics) |
+INSTANTIATE(PrinterPPDData) |
+INSTANTIATE(AppNotification) |
+INSTANTIATE(AppSettingSpecifics) |
+INSTANTIATE(AppSpecifics) |
+INSTANTIATE(ArticleSpecifics) |
+INSTANTIATE(AutofillSpecifics) |
+INSTANTIATE(AutofillProfileSpecifics) |
+INSTANTIATE(WalletMetadataSpecifics) |
+INSTANTIATE(AutofillWalletSpecifics) |
+INSTANTIATE(BookmarkSpecifics) |
+INSTANTIATE(DeviceInfoSpecifics) |
+INSTANTIATE(DictionarySpecifics) |
+INSTANTIATE(ExperimentsSpecifics) |
+INSTANTIATE(PriorityPreferenceSpecifics) |
+INSTANTIATE(ExtensionSettingSpecifics) |
+INSTANTIATE(ExtensionSpecifics) |
+INSTANTIATE(FaviconImageSpecifics) |
+INSTANTIATE(FaviconTrackingSpecifics) |
+INSTANTIATE(HistoryDeleteDirectiveSpecifics) |
+INSTANTIATE(ManagedUserSettingSpecifics) |
+INSTANTIATE(ManagedUserSpecifics) |
+INSTANTIATE(ManagedUserSharedSettingSpecifics) |
+INSTANTIATE(ManagedUserWhitelistSpecifics) |
+INSTANTIATE(NigoriSpecifics) |
+INSTANTIATE(PasswordSpecifics) |
+INSTANTIATE(PreferenceSpecifics) |
+INSTANTIATE(PrinterSpecifics) |
+INSTANTIATE(ReadingListSpecifics) |
+INSTANTIATE(SyncedNotificationAppInfoSpecifics) |
+INSTANTIATE(SyncedNotificationSpecifics) |
+INSTANTIATE(SearchEngineSpecifics) |
+INSTANTIATE(ThemeSpecifics) |
+INSTANTIATE(TypedUrlSpecifics) |
+INSTANTIATE(WalletMaskedCreditCard) |
+INSTANTIATE(WalletPostalAddress) |
+INSTANTIATE(WifiCredentialSpecifics) |
+INSTANTIATE(SyncEntity) |
+INSTANTIATE(ClientToServerMessage) |
+INSTANTIATE(ClientToServerResponse) |
+INSTANTIATE(DatatypeAssociationStats) |
+INSTANTIATE(DebugEventInfo) |
+INSTANTIATE(DebugInfo) |
+INSTANTIATE(SyncCycleCompletedEventInfo) |
+INSTANTIATE(ClientConfigParams) |
+INSTANTIATE(AttachmentIdProto) |
+INSTANTIATE(EntityMetadata) |
+ |
+#undef INSTANTIATE |
+ |
+} // namespace sync_pb |