author | Ryan VanderMeulen <ryanvm@gmail.com> |
Fri, 10 Jan 2014 08:28:02 -0500 | |
changeset 162934 | d4bdd22683d92ed9591021f3c98208547fa929bf |
parent 162933 | a01d64b4d98570ebc0fcaa7202ffa7474ec7995b |
child 162935 | 2984d53fe0cf45004ddc0d24deff8897dba0b8d6 |
push id | 25975 |
push user | ryanvm@gmail.com |
push date | Fri, 10 Jan 2014 19:46:47 +0000 |
treeherder | autoland@e89afc241513 [default view] [failures only] |
perfherder | [talos] [build metrics] [platform microbench] (compared to previous push) |
bugs | 948204 |
milestone | 29.0a1 |
backs out | e65b4f1bea8801d617f04d8159cccb76576ae5fb |
first release with | nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
|
last release without | nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
|
--- a/xpcom/base/SystemMemoryReporter.cpp +++ b/xpcom/base/SystemMemoryReporter.cpp @@ -17,17 +17,16 @@ #include "nsHashKeys.h" #include <dirent.h> #include <inttypes.h> #include <stdio.h> #include <sys/stat.h> #include <sys/types.h> #include <unistd.h> -#include <errno.h> // This file implements a Linux-specific, system-wide memory reporter. It // gathers all the useful memory measurements obtainable from the OS in a // single place, giving a high-level view of memory consumption for the entire // machine/device. // // Other memory reporters measure part of a single process's memory consumption. // This reporter is different in that it measures memory consumption of many @@ -109,34 +108,30 @@ IsAnonymous(const nsACString& aName) StringBeginsWith(aName, NS_LITERAL_CSTRING("[stack:")); } class SystemReporter MOZ_FINAL : public nsIMemoryReporter { public: NS_DECL_THREADSAFE_ISUPPORTS -#define REPORT_WITH_CLEANUP(_path, _amount, _desc, _cleanup) \ +#define REPORT(_path, _amount, _desc) \ do { \ size_t amount = _amount; /* evaluate _amount only once */ \ if (amount > 0) { \ nsresult rv; \ rv = aHandleReport->Callback(NS_LITERAL_CSTRING("System"), _path, \ KIND_NONHEAP, UNITS_BYTES, amount, _desc, \ aData); \ if (NS_WARN_IF(NS_FAILED(rv))) { \ - _cleanup; \ return rv; \ } \ } \ } while (0) -#define REPORT(_path, _amount, _desc) \ - REPORT_WITH_CLEANUP(_path, _amount, _desc, (void)0) - NS_IMETHOD CollectReports(nsIHandleReportCallback* aHandleReport, nsISupports* aData) { if (!Preferences::GetBool("memory.system_memory_reporter")) { return NS_OK; } // Read relevant fields from /proc/meminfo. @@ -153,20 +148,17 @@ public: REPORT(NS_LITERAL_CSTRING("mem/other"), other, NS_LITERAL_CSTRING( "Memory which is neither owned by any user-space process nor free. Note that " "this includes memory holding cached files from the disk which can be " "reclaimed by the OS at any time.")); REPORT(NS_LITERAL_CSTRING("mem/free"), memFree, NS_LITERAL_CSTRING( "Memory which is free and not being used for any purpose.")); - // Report reserved memory not included in memTotal. - rv = CollectPmemReports(aHandleReport, aData); - - return rv; + return NS_OK; } private: // Keep this in sync with SystemReporter::kindPathSuffixes! enum ProcessSizeKind { AnonymousOutsideBrk = 0, AnonymousBrkHeap = 1, SharedLibrariesRX = 2, @@ -504,117 +496,16 @@ private: REPORT(path, *aPss, aDescription); } else { *aPss = 0; } return NS_OK; } - nsresult CollectPmemReports(nsIHandleReportCallback* aHandleReport, - nsISupports* aData) - { - // The pmem subsystem allocates physically contiguous memory for - // interfacing with hardware. In order to ensure availability, - // this memory is reserved during boot, and allocations are made - // within these regions at runtime. - // - // There are typically several of these pools allocated at boot. - // The /sys/kernel/pmem_regions directory contains a subdirectory - // for each one. Within each subdirectory, the files we care - // about are "size" (the total amount of physical memory) and - // "mapped_regions" (a list of the current allocations within that - // area). - DIR* d = opendir("/sys/kernel/pmem_regions"); - if (!d) { - if (NS_WARN_IF(errno != ENOENT)) { - return NS_ERROR_FAILURE; - } - // If ENOENT, system doesn't use pmem. - return NS_OK; - } - - struct dirent* ent; - while ((ent = readdir(d))) { - const char* name = ent->d_name; - uint64_t size; - int scanned; - - // Skip "." and ".." (and any other dotfiles). - if (name[0] == '.') { - continue; - } - - // Read the total size. The file gives the size in decimal and - // hex, in the form "13631488(0xd00000)"; we parse the former. - nsPrintfCString sizePath("/sys/kernel/pmem_regions/%s/size", name); - FILE* sizeFile = fopen(sizePath.get(), "r"); - if (NS_WARN_IF(!sizeFile)) { - continue; - } - scanned = fscanf(sizeFile, "%"SCNu64, &size); - if (NS_WARN_IF(scanned != 1)) { - continue; - } - fclose(sizeFile); - - // Read mapped regions; format described below. - uint64_t freeSize = size; - nsPrintfCString regionsPath("/sys/kernel/pmem_regions/%s/mapped_regions", - name); - FILE* regionsFile = fopen(regionsPath.get(), "r"); - if (regionsFile) { - static const size_t bufLen = 4096; - char buf[bufLen]; - while (fgets(buf, bufLen, regionsFile)) { - int pid; - - // Skip header line. - if (strncmp(buf, "pid #", 5) == 0) { - continue; - } - // Line format: "pid N:" + zero or more "(Start,Len) ". - // N is decimal; Start and Len are in hex. - scanned = sscanf(buf, "pid %d", &pid); - if (NS_WARN_IF(scanned != 1)) { - continue; - } - for (const char* nextParen = strchr(buf, '('); - nextParen != nullptr; - nextParen = strchr(nextParen + 1, '(')) { - uint64_t mapStart, mapLen; - - scanned = sscanf(nextParen + 1, "%"SCNx64",%"SCNx64, - &mapStart, &mapLen); - if (NS_WARN_IF(scanned != 2)) { - break; - } - - nsPrintfCString path("mem/pmem/used/%s/segment(pid=%d, " - "offset=0x%"PRIx64")", name, pid, mapStart); - nsPrintfCString desc("Physical memory reserved for the \"%s\" pool " - "and allocated to a buffer.", name); - REPORT_WITH_CLEANUP(path, mapLen, desc, - (fclose(regionsFile), closedir(d))); - freeSize -= mapLen; - } - } - fclose(regionsFile); - } - - nsPrintfCString path("mem/pmem/free/%s", name); - nsPrintfCString desc("Physical memory reserved for the \"%s\" pool and " - "unavailable to the rest of the system, but not " - "currently allocated.", name); - REPORT_WITH_CLEANUP(path, freeSize, desc, closedir(d)); - } - closedir(d); - return NS_OK; - } - #undef REPORT }; NS_IMPL_ISUPPORTS1(SystemReporter, nsIMemoryReporter) // Keep this in sync with SystemReporter::ProcessSizeKind! const char* SystemReporter::kindPathSuffixes[] = { "anonymous/outside-brk",