1 /** 2 * Copyright (c) 2021-2022 Huawei Device Co., Ltd. 3 * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 #ifndef PANDA_RUNTIME_MEM_STATS_H 16 #define PANDA_RUNTIME_MEM_STATS_H 17 18 #include <chrono> 19 #include <cstdint> 20 #include <cstring> 21 22 #include "libpandabase/macros.h" 23 #include "libpandabase/mem/base_mem_stats.h" 24 #include "libpandabase/os/mutex.h" 25 #include "runtime/include/mem/panda_string.h" 26 #include "runtime/mem/gc/gc_phase.h" 27 28 namespace panda { 29 class BaseClass; 30 } // namespace panda 31 32 namespace panda::mem { 33 34 class HeapManager; 35 36 /** 37 * Class for recording memory usage in the VM. Allocators use this class for both cases: object allocation in heap and 38 * raw memory for VM needs as well. This class uses CRTP for storing additional information in DEBUG mode. 39 */ 40 template <typename T> 41 class MemStats : public BaseMemStats { 42 public: 43 NO_COPY_SEMANTIC(MemStats); 44 NO_MOVE_SEMANTIC(MemStats); 45 46 MemStats() = default; 47 48 ~MemStats() override = default; 49 50 void RecordAllocateObject(size_t size, SpaceType type_mem); 51 52 void RecordAllocateObjects(size_t total_object_num, size_t total_object_size, SpaceType type_mem); 53 54 void RecordYoungMovedObjects(size_t young_object_num, size_t size, SpaceType type_mem); 55 56 void RecordTenuredMovedObjects(size_t tenured_object_num, size_t size, SpaceType type_mem); 57 58 void RecordFreeObject(size_t object_size, SpaceType type_mem); 59 60 void RecordFreeObjects(size_t total_object_num, size_t total_object_size, SpaceType type_mem); 61 62 void RecordGCPauseStart(); 63 void RecordGCPauseEnd(); 64 65 /** 66 * Number of allocated objects for all time 67 */ 68 [[nodiscard]] uint64_t GetTotalObjectsAllocated() const; 69 70 /** 71 * Number of freed objects for all time 72 */ 73 [[nodiscard]] uint64_t GetTotalObjectsFreed() const; 74 75 /** 76 * Number of allocated large and regular (size <= FREELIST_MAX_ALLOC_SIZE) objects for all time 77 */ 78 [[nodiscard]] uint64_t GetTotalRegularObjectsAllocated() const; 79 80 /** 81 * Number of freed large and regular (size <= FREELIST_MAX_ALLOC_SIZE) objects for all time 82 */ 83 [[nodiscard]] uint64_t GetTotalRegularObjectsFreed() const; 84 85 /** 86 * Number of allocated humongous (size > FREELIST_MAX_ALLOC_SIZE) objects for all time 87 */ 88 [[nodiscard]] uint64_t GetTotalHumongousObjectsAllocated() const; 89 90 /** 91 * Number of freed humongous (size > FREELIST_MAX_ALLOC_SIZE) objects for all time 92 */ 93 [[nodiscard]] uint64_t GetTotalHumongousObjectsFreed() const; 94 95 /** 96 * Number of alive objects now 97 */ 98 [[nodiscard]] uint64_t GetObjectsCountAlive() const; 99 100 /** 101 * Number of alive large and regular (size <= FREELIST_MAX_ALLOC_SIZE) objects now 102 */ 103 [[nodiscard]] uint64_t GetRegularObjectsCountAlive() const; 104 105 /** 106 * Number of alive humongous (size > FREELIST_MAX_ALLOC_SIZE) objects now 107 */ 108 [[nodiscard]] uint64_t GetHumonguousObjectsCountAlive() const; 109 110 /** 111 * Number of moved bytes in last gc 112 */ 113 [[nodiscard]] uint64_t GetLastYoungObjectsMovedBytes() const; 114 ClearLastYoungObjectsMovedBytes()115 void ClearLastYoungObjectsMovedBytes() 116 { 117 last_young_objects_moved_bytes_ = 0; 118 } 119 120 PandaString GetStatistics(HeapManager *heap_manager); 121 122 uint64_t GetMinGCPause() const; 123 uint64_t GetMaxGCPause() const; 124 uint64_t GetAverageGCPause() const; 125 uint64_t GetTotalGCPause() const; 126 127 protected: 128 using clock = std::chrono::high_resolution_clock; 129 using duration = std::chrono::duration<uint64_t, std::nano>; 130 131 private: 132 clock::time_point pause_start_time_ = clock::now(); 133 duration min_pause_ = duration(0); 134 duration max_pause_ = duration(0); 135 duration sum_pause_ = duration(0); 136 uint64_t pause_count_ = 0; 137 138 std::atomic_uint64_t last_young_objects_moved_bytes_ = 0; 139 140 // make groups of different parts of the VM (JIT, interpreter, etc) 141 std::atomic_uint64_t objects_allocated_ = 0; 142 std::atomic_uint64_t objects_freed_ = 0; 143 144 std::atomic_uint64_t humongous_objects_allocated_ = 0; 145 std::atomic_uint64_t humongous_objects_freed_ = 0; 146 }; 147 148 } // namespace panda::mem 149 #endif // PANDA_RUNTIME_MEM_STATS_H 150