| 3106 | namespace platform { |
| 3107 | |
| 3108 | void outOfMemory() { |
| 3109 | #ifdef ALLOC_INSTRUMENTATION |
| 3110 | delete[] g_extra_memory; |
| 3111 | std::vector<std::pair<std::string, const char*>> typeNames; |
| 3112 | for (auto i = allocInstr.begin(); i != allocInstr.end(); ++i) { |
| 3113 | std::string s; |
| 3114 | #ifdef __linux__ |
| 3115 | char* demangled = abi::__cxa_demangle(i->first, nullptr, nullptr, nullptr); |
| 3116 | if (demangled) { |
| 3117 | s = demangled; |
| 3118 | if (StringRef(s).startsWith(LiteralStringRef("(anonymous namespace)::"))) |
| 3119 | s = s.substr(LiteralStringRef("(anonymous namespace)::").size()); |
| 3120 | free(demangled); |
| 3121 | } else |
| 3122 | s = i->first; |
| 3123 | #else |
| 3124 | s = i->first; |
| 3125 | if (StringRef(s).startsWith(LiteralStringRef("class `anonymous namespace'::"))) |
| 3126 | s = s.substr(LiteralStringRef("class `anonymous namespace'::").size()); |
| 3127 | else if (StringRef(s).startsWith(LiteralStringRef("class "))) |
| 3128 | s = s.substr(LiteralStringRef("class ").size()); |
| 3129 | else if (StringRef(s).startsWith(LiteralStringRef("struct "))) |
| 3130 | s = s.substr(LiteralStringRef("struct ").size()); |
| 3131 | #endif |
| 3132 | typeNames.emplace_back(s, i->first); |
| 3133 | } |
| 3134 | std::sort(typeNames.begin(), typeNames.end()); |
| 3135 | for (int i = 0; i < typeNames.size(); i++) { |
| 3136 | const char* n = typeNames[i].second; |
| 3137 | auto& f = allocInstr[n]; |
| 3138 | if (f.maxAllocated > 10000) |
| 3139 | TraceEvent("AllocInstrument") |
| 3140 | .detail("CurrentAlloc", f.allocCount - f.deallocCount) |
| 3141 | .detail("Name", typeNames[i].first.c_str()); |
| 3142 | } |
| 3143 | |
| 3144 | std::unordered_map<uint32_t, BackTraceAccount> traceCounts; |
| 3145 | size_t memSampleSize; |
| 3146 | memSample_entered = true; |
| 3147 | { |
| 3148 | ThreadSpinLockHolder holder(memLock); |
| 3149 | traceCounts = backTraceLookup; |
| 3150 | memSampleSize = memSample.size(); |
| 3151 | } |
| 3152 | memSample_entered = false; |
| 3153 | |
| 3154 | TraceEvent("MemSampleSummary") |
| 3155 | .detail("InverseByteSampleRatio", SAMPLE_BYTES) |
| 3156 | .detail("MemorySamples", memSampleSize) |
| 3157 | .detail("BackTraces", traceCounts.size()); |
| 3158 | |
| 3159 | for (auto i = traceCounts.begin(); i != traceCounts.end(); ++i) { |
| 3160 | char buf[1024]; |
| 3161 | std::vector<void*>* frames = i->second.backTrace; |
| 3162 | std::string backTraceStr; |
| 3163 | #if defined(_WIN32) |
| 3164 | for (int j = 1; j < frames->size(); j++) { |
| 3165 | _snprintf(buf, 1024, "%p ", frames->at(j)); |
no test coverage detected