1b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat// Copyright 2015 The Chromium Authors. All rights reserved.
2b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat// Use of this source code is governed by a BSD-style license that can be
3b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat// found in the LICENSE file.
4b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat
5b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat#ifndef BASE_TRACE_EVENT_MEMORY_ALLOCATOR_DUMP_H_
6b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat#define BASE_TRACE_EVENT_MEMORY_ALLOCATOR_DUMP_H_
7b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat
80d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko#include <stdint.h>
90d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko
1094ffa55491333f3dcc701befd0d2652922916d99Luis Hector Chavez#include <memory>
11b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat#include <string>
12b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat
13b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat#include "base/base_export.h"
14319afc59a539d6261307aadbdab4d4ee93eaf1ffJakub Pawlowski#include "base/gtest_prod_util.h"
15b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat#include "base/logging.h"
160d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko#include "base/macros.h"
17b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat#include "base/trace_event/memory_allocator_dump_guid.h"
18b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat#include "base/values.h"
19b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat
20b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Eratnamespace base {
21b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Eratnamespace trace_event {
22b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat
23b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Eratclass ProcessMemoryDump;
24b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Eratclass TracedValue;
25b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat
26b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat// Data model for user-land memory allocator dumps.
27b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Eratclass BASE_EXPORT MemoryAllocatorDump {
28b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat public:
2945779228f8c9e40851cfd23f727e2bd8ffdd4714Alex Vakulenko  enum Flags {
3045779228f8c9e40851cfd23f727e2bd8ffdd4714Alex Vakulenko    DEFAULT = 0,
3145779228f8c9e40851cfd23f727e2bd8ffdd4714Alex Vakulenko
3245779228f8c9e40851cfd23f727e2bd8ffdd4714Alex Vakulenko    // A dump marked weak will be discarded by TraceViewer.
3345779228f8c9e40851cfd23f727e2bd8ffdd4714Alex Vakulenko    WEAK = 1 << 0,
3445779228f8c9e40851cfd23f727e2bd8ffdd4714Alex Vakulenko  };
3545779228f8c9e40851cfd23f727e2bd8ffdd4714Alex Vakulenko
36b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  // MemoryAllocatorDump is owned by ProcessMemoryDump.
37b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  MemoryAllocatorDump(const std::string& absolute_name,
38b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat                      ProcessMemoryDump* process_memory_dump,
39b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat                      const MemoryAllocatorDumpGuid& guid);
40b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  MemoryAllocatorDump(const std::string& absolute_name,
41b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat                      ProcessMemoryDump* process_memory_dump);
42b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  ~MemoryAllocatorDump();
43b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat
440d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko  // Standard attribute |name|s for the AddScalar and AddString() methods.
450d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko  static const char kNameSize[];          // To represent allocated space.
460d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko  static const char kNameObjectCount[];   // To represent number of objects.
47b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat
480d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko  // Standard attribute |unit|s for the AddScalar and AddString() methods.
49b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  static const char kUnitsBytes[];    // Unit name to represent bytes.
50b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  static const char kUnitsObjects[];  // Unit name to represent #objects.
51b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat
520d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko  // Constants used only internally and by tests.
530d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko  static const char kTypeScalar[];  // Type name for scalar attributes.
540d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko  static const char kTypeString[];  // Type name for string attributes.
55b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat
560d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko  // Setters for scalar attributes. Some examples:
570d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko  // - "size" column (all dumps are expected to have at least this one):
580d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko  //     AddScalar(kNameSize, kUnitsBytes, 1234);
590d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko  // - Some extra-column reporting internal details of the subsystem:
600d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko  //    AddScalar("number_of_freelist_entires", kUnitsObjects, 42)
610d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko  // - Other informational column (will not be auto-added in the UI)
620d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko  //    AddScalarF("kittens_ratio", "ratio", 42.0f)
630d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko  void AddScalar(const char* name, const char* units, uint64_t value);
64b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  void AddScalarF(const char* name, const char* units, double value);
65b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  void AddString(const char* name, const char* units, const std::string& value);
66b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat
670d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko  // Absolute name, unique within the scope of an entire ProcessMemoryDump.
680d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko  const std::string& absolute_name() const { return absolute_name_; }
690d205d712abd16eeed2f5d5b1052a367d23a223fAlex Vakulenko
70b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  // Called at trace generation time to populate the TracedValue.
71b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  void AsValueInto(TracedValue* value) const;
72b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat
7345779228f8c9e40851cfd23f727e2bd8ffdd4714Alex Vakulenko  // Use enum Flags to set values.
7445779228f8c9e40851cfd23f727e2bd8ffdd4714Alex Vakulenko  void set_flags(int flags) { flags_ |= flags; }
7545779228f8c9e40851cfd23f727e2bd8ffdd4714Alex Vakulenko  void clear_flags(int flags) { flags_ &= ~flags; }
7645779228f8c9e40851cfd23f727e2bd8ffdd4714Alex Vakulenko  int flags() { return flags_; }
7745779228f8c9e40851cfd23f727e2bd8ffdd4714Alex Vakulenko
78b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  // |guid| is an optional global dump identifier, unique across all processes
79b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  // within the scope of a global dump. It is only required when using the
80b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  // graph APIs (see TODO_method_name) to express retention / suballocation or
81b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  // cross process sharing. See crbug.com/492102 for design docs.
82b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  // Subsequent MemoryAllocatorDump(s) with the same |absolute_name| are
83b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  // expected to have the same guid.
84b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  const MemoryAllocatorDumpGuid& guid() const { return guid_; }
85b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat
86b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  TracedValue* attributes_for_testing() const { return attributes_.get(); }
87b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat
88b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat private:
89319afc59a539d6261307aadbdab4d4ee93eaf1ffJakub Pawlowski  // TODO(hjd): Transitional until we send the full PMD. See crbug.com/704203
90319afc59a539d6261307aadbdab4d4ee93eaf1ffJakub Pawlowski  friend class MemoryDumpManager;
91319afc59a539d6261307aadbdab4d4ee93eaf1ffJakub Pawlowski  FRIEND_TEST_ALL_PREFIXES(MemoryAllocatorDumpTest, GetSize);
92319afc59a539d6261307aadbdab4d4ee93eaf1ffJakub Pawlowski
93319afc59a539d6261307aadbdab4d4ee93eaf1ffJakub Pawlowski  // Get the size for this dump.
94319afc59a539d6261307aadbdab4d4ee93eaf1ffJakub Pawlowski  // The size is the value set with AddScalar(kNameSize, kUnitsBytes, size);
95319afc59a539d6261307aadbdab4d4ee93eaf1ffJakub Pawlowski  // TODO(hjd): Transitional until we send the full PMD. See crbug.com/704203
96319afc59a539d6261307aadbdab4d4ee93eaf1ffJakub Pawlowski  uint64_t GetSize() const { return size_; };
97319afc59a539d6261307aadbdab4d4ee93eaf1ffJakub Pawlowski
98b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  const std::string absolute_name_;
99b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  ProcessMemoryDump* const process_memory_dump_;  // Not owned (PMD owns this).
10094ffa55491333f3dcc701befd0d2652922916d99Luis Hector Chavez  std::unique_ptr<TracedValue> attributes_;
101b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  MemoryAllocatorDumpGuid guid_;
10245779228f8c9e40851cfd23f727e2bd8ffdd4714Alex Vakulenko  int flags_;  // See enum Flags.
103319afc59a539d6261307aadbdab4d4ee93eaf1ffJakub Pawlowski  uint64_t size_;
104b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat
105b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  // A local buffer for Sprintf conversion on fastpath. Avoids allocating
106b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  // temporary strings on each AddScalar() call.
107b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  std::string string_conversion_buffer_;
108b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat
109b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat  DISALLOW_COPY_AND_ASSIGN(MemoryAllocatorDump);
110b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat};
111b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat
112b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat}  // namespace trace_event
113b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat}  // namespace base
114b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat
115b8cf94937c52feb53b55c39e3f82094d27de464cDaniel Erat#endif  // BASE_TRACE_EVENT_MEMORY_ALLOCATOR_DUMP_H_
116