Backed out changeset a53aa43ab5f4 for Windows build bustage on a CLOSED TREE

--HG--
extra : rebase_source : d3a1aecd8882bc591898684c0a97f8929b7809a9
This commit is contained in:
Terrence Cole 2014-09-19 09:40:53 -07:00
Родитель 2fe4282ad3
Коммит 05be72f555
4 изменённых файлов: 53 добавлений и 241 удалений

Просмотреть файл

@ -14,7 +14,6 @@
#include "mozilla/NullPtr.h" #include "mozilla/NullPtr.h"
#include "mozilla/Scoped.h" #include "mozilla/Scoped.h"
#include "mozilla/TemplateLib.h" #include "mozilla/TemplateLib.h"
#include "mozilla/UniquePtr.h"
#include <stdlib.h> #include <stdlib.h>
#include <string.h> #include <string.h>
@ -627,14 +626,6 @@ namespace js {
typedef uint32_t HashNumber; typedef uint32_t HashNumber;
const unsigned HashNumberSizeBits = 32; const unsigned HashNumberSizeBits = 32;
typedef mozilla::UniquePtr<char, JS::FreePolicy> UniqueChars;
static inline UniqueChars make_string_copy(const char* str)
{
JS_OOM_POSSIBLY_FAIL();
return UniqueChars(strdup(str));
}
namespace detail { namespace detail {
/* /*

Просмотреть файл

@ -7,7 +7,6 @@
#include "gc/Statistics.h" #include "gc/Statistics.h"
#include "mozilla/PodOperations.h" #include "mozilla/PodOperations.h"
#include "mozilla/UniquePtr.h"
#include <ctype.h> #include <ctype.h>
#include <stdarg.h> #include <stdarg.h>
@ -27,8 +26,8 @@ using namespace js::gcstats;
using mozilla::PodArrayZero; using mozilla::PodArrayZero;
/* Except for the first and last, slices of less than 10ms are not reported. */ /* Except for the first and last, slices of less than 42ms are not reported. */
static const int64_t SLICE_MIN_REPORT_TIME = 10 * PRMJ_USEC_PER_MSEC; static const int64_t SLICE_MIN_REPORT_TIME = 42 * PRMJ_USEC_PER_MSEC;
class gcstats::StatisticsSerializer class gcstats::StatisticsSerializer
{ {
@ -277,44 +276,44 @@ static const PhaseInfo phases[] = {
{ PHASE_MARK_DISCARD_CODE, "Mark Discard Code", PHASE_NO_PARENT }, { PHASE_MARK_DISCARD_CODE, "Mark Discard Code", PHASE_NO_PARENT },
{ PHASE_PURGE, "Purge", PHASE_NO_PARENT }, { PHASE_PURGE, "Purge", PHASE_NO_PARENT },
{ PHASE_MARK, "Mark", PHASE_NO_PARENT }, { PHASE_MARK, "Mark", PHASE_NO_PARENT },
{ PHASE_MARK_ROOTS, "Mark Roots", PHASE_MARK }, { PHASE_MARK_ROOTS, "Mark Roots", PHASE_MARK },
{ PHASE_MARK_DELAYED, "Mark Delayed", PHASE_MARK }, { PHASE_MARK_DELAYED, "Mark Delayed", PHASE_MARK },
{ PHASE_SWEEP, "Sweep", PHASE_NO_PARENT }, { PHASE_SWEEP, "Sweep", PHASE_NO_PARENT },
{ PHASE_SWEEP_MARK, "Mark During Sweeping", PHASE_SWEEP }, { PHASE_SWEEP_MARK, "Mark During Sweeping", PHASE_SWEEP },
{ PHASE_SWEEP_MARK_TYPES, "Mark Types During Sweeping", PHASE_SWEEP_MARK }, { PHASE_SWEEP_MARK_TYPES, "Mark Types During Sweeping", PHASE_SWEEP_MARK },
{ PHASE_SWEEP_MARK_INCOMING_BLACK, "Mark Incoming Black Pointers", PHASE_SWEEP_MARK }, { PHASE_SWEEP_MARK_INCOMING_BLACK, "Mark Incoming Black Pointers", PHASE_SWEEP_MARK },
{ PHASE_SWEEP_MARK_WEAK, "Mark Weak", PHASE_SWEEP_MARK }, { PHASE_SWEEP_MARK_WEAK, "Mark Weak", PHASE_SWEEP_MARK },
{ PHASE_SWEEP_MARK_INCOMING_GRAY, "Mark Incoming Gray Pointers", PHASE_SWEEP_MARK }, { PHASE_SWEEP_MARK_INCOMING_GRAY, "Mark Incoming Gray Pointers", PHASE_SWEEP_MARK },
{ PHASE_SWEEP_MARK_GRAY, "Mark Gray", PHASE_SWEEP_MARK }, { PHASE_SWEEP_MARK_GRAY, "Mark Gray", PHASE_SWEEP_MARK },
{ PHASE_SWEEP_MARK_GRAY_WEAK, "Mark Gray and Weak", PHASE_SWEEP_MARK }, { PHASE_SWEEP_MARK_GRAY_WEAK, "Mark Gray and Weak", PHASE_SWEEP_MARK },
{ PHASE_FINALIZE_START, "Finalize Start Callback", PHASE_SWEEP }, { PHASE_FINALIZE_START, "Finalize Start Callback", PHASE_SWEEP },
{ PHASE_SWEEP_ATOMS, "Sweep Atoms", PHASE_SWEEP }, { PHASE_SWEEP_ATOMS, "Sweep Atoms", PHASE_SWEEP },
{ PHASE_SWEEP_SYMBOL_REGISTRY, "Sweep Symbol Registry", PHASE_SWEEP }, { PHASE_SWEEP_SYMBOL_REGISTRY, "Sweep Symbol Registry", PHASE_SWEEP },
{ PHASE_SWEEP_COMPARTMENTS, "Sweep Compartments", PHASE_SWEEP }, { PHASE_SWEEP_COMPARTMENTS, "Sweep Compartments", PHASE_SWEEP },
{ PHASE_SWEEP_DISCARD_CODE, "Sweep Discard Code", PHASE_SWEEP_COMPARTMENTS }, { PHASE_SWEEP_DISCARD_CODE, "Sweep Discard Code", PHASE_SWEEP_COMPARTMENTS },
{ PHASE_SWEEP_TABLES, "Sweep Tables", PHASE_SWEEP_COMPARTMENTS }, { PHASE_SWEEP_TABLES, "Sweep Tables", PHASE_SWEEP_COMPARTMENTS },
{ PHASE_SWEEP_TABLES_INNER_VIEWS, "Sweep Inner Views", PHASE_SWEEP_TABLES }, { PHASE_SWEEP_TABLES_INNER_VIEWS, "Sweep Inner Views", PHASE_SWEEP_TABLES },
{ PHASE_SWEEP_TABLES_WRAPPER, "Sweep Cross Compartment Wrappers", PHASE_SWEEP_TABLES }, { PHASE_SWEEP_TABLES_WRAPPER, "Sweep Cross Compartment Wrappers", PHASE_SWEEP_TABLES },
{ PHASE_SWEEP_TABLES_BASE_SHAPE, "Sweep Base Shapes", PHASE_SWEEP_TABLES }, { PHASE_SWEEP_TABLES_BASE_SHAPE, "Sweep Base Shapes", PHASE_SWEEP_TABLES },
{ PHASE_SWEEP_TABLES_INITIAL_SHAPE, "Sweep Initial Shapes", PHASE_SWEEP_TABLES }, { PHASE_SWEEP_TABLES_INITIAL_SHAPE, "Sweep Initial Shapes", PHASE_SWEEP_TABLES },
{ PHASE_SWEEP_TABLES_TYPE_OBJECT, "Sweep Type Objects", PHASE_SWEEP_TABLES }, { PHASE_SWEEP_TABLES_TYPE_OBJECT, "Sweep Type Objects", PHASE_SWEEP_TABLES },
{ PHASE_SWEEP_TABLES_BREAKPOINT, "Sweep Breakpoints", PHASE_SWEEP_TABLES }, { PHASE_SWEEP_TABLES_BREAKPOINT, "Sweep Breakpoints", PHASE_SWEEP_TABLES },
{ PHASE_SWEEP_TABLES_REGEXP, "Sweep Regexps", PHASE_SWEEP_TABLES }, { PHASE_SWEEP_TABLES_REGEXP, "Sweep Regexps", PHASE_SWEEP_TABLES },
{ PHASE_DISCARD_ANALYSIS, "Discard Analysis", PHASE_SWEEP_COMPARTMENTS }, { PHASE_DISCARD_ANALYSIS, "Discard Analysis", PHASE_SWEEP_COMPARTMENTS },
{ PHASE_DISCARD_TI, "Discard TI", PHASE_DISCARD_ANALYSIS }, { PHASE_DISCARD_TI, "Discard TI", PHASE_DISCARD_ANALYSIS },
{ PHASE_FREE_TI_ARENA, "Free TI Arena", PHASE_DISCARD_ANALYSIS }, { PHASE_FREE_TI_ARENA, "Free TI Arena", PHASE_DISCARD_ANALYSIS },
{ PHASE_SWEEP_TYPES, "Sweep Types", PHASE_DISCARD_ANALYSIS }, { PHASE_SWEEP_TYPES, "Sweep Types", PHASE_DISCARD_ANALYSIS },
{ PHASE_SWEEP_OBJECT, "Sweep Object", PHASE_SWEEP }, { PHASE_SWEEP_OBJECT, "Sweep Object", PHASE_SWEEP },
{ PHASE_SWEEP_STRING, "Sweep String", PHASE_SWEEP }, { PHASE_SWEEP_STRING, "Sweep String", PHASE_SWEEP },
{ PHASE_SWEEP_SCRIPT, "Sweep Script", PHASE_SWEEP }, { PHASE_SWEEP_SCRIPT, "Sweep Script", PHASE_SWEEP },
{ PHASE_SWEEP_SHAPE, "Sweep Shape", PHASE_SWEEP }, { PHASE_SWEEP_SHAPE, "Sweep Shape", PHASE_SWEEP },
{ PHASE_SWEEP_JITCODE, "Sweep JIT code", PHASE_SWEEP }, { PHASE_SWEEP_JITCODE, "Sweep JIT code", PHASE_SWEEP },
{ PHASE_FINALIZE_END, "Finalize End Callback", PHASE_SWEEP },
{ PHASE_DESTROY, "Deallocate", PHASE_SWEEP },
{ PHASE_COMPACT, "Compact", PHASE_NO_PARENT }, { PHASE_COMPACT, "Compact", PHASE_NO_PARENT },
{ PHASE_COMPACT_MOVE, "Compact Move", PHASE_COMPACT }, { PHASE_COMPACT_MOVE, "Compact Move", PHASE_COMPACT },
{ PHASE_COMPACT_UPDATE, "Compact Update", PHASE_COMPACT, }, { PHASE_COMPACT_UPDATE, "Compact Update", PHASE_COMPACT, },
{ PHASE_COMPACT_UPDATE_GRAY, "Compact Update Gray", PHASE_COMPACT_UPDATE, }, { PHASE_COMPACT_UPDATE_GRAY, "Compact Update Gray", PHASE_COMPACT_UPDATE, },
{ PHASE_FINALIZE_END, "Finalize End Callback", PHASE_SWEEP },
{ PHASE_DESTROY, "Deallocate", PHASE_SWEEP },
{ PHASE_GC_END, "End Callback", PHASE_NO_PARENT }, { PHASE_GC_END, "End Callback", PHASE_NO_PARENT },
{ PHASE_LIMIT, nullptr, PHASE_NO_PARENT } { PHASE_LIMIT, nullptr, PHASE_NO_PARENT }
}; };
@ -371,7 +370,7 @@ Statistics::formatData(StatisticsSerializer &ss, uint64_t timestamp)
else else
ss.appendString("Reason", ExplainReason(slices[0].reason)); ss.appendString("Reason", ExplainReason(slices[0].reason));
ss.appendDecimal("Total Time", "ms", t(total)); ss.appendDecimal("Total Time", "ms", t(total));
ss.appendNumber("Zones Collected", "%d", "", zoneStats.collectedZoneCount); ss.appendNumber("Zones Collected", "%d", "", zoneStats.collectedCount);
ss.appendNumber("Total Zones", "%d", "", zoneStats.zoneCount); ss.appendNumber("Total Zones", "%d", "", zoneStats.zoneCount);
ss.appendNumber("Total Compartments", "%d", "", zoneStats.compartmentCount); ss.appendNumber("Total Compartments", "%d", "", zoneStats.compartmentCount);
ss.appendNumber("Minor GCs", "%d", "", counts[STAT_MINOR_GC]); ss.appendNumber("Minor GCs", "%d", "", counts[STAT_MINOR_GC]);
@ -428,174 +427,6 @@ Statistics::formatData(StatisticsSerializer &ss, uint64_t timestamp)
return !ss.isOOM(); return !ss.isOOM();
} }
typedef Vector<UniqueChars, 8, SystemAllocPolicy> FragmentVector;
static UniqueChars
Join(const FragmentVector &fragments) {
size_t length = 0;
for (size_t i = 0; i < fragments.length(); ++i)
length += fragments[i] ? strlen(fragments[i].get()) : 0;
char *joined = js_pod_malloc<char>(length + 1);
joined[length] = '\0';
char *cursor = joined;
for (size_t i = 0; i < fragments.length(); ++i) {
if (fragments[i])
strcpy(cursor, fragments[i].get());
cursor += fragments[i] ? strlen(fragments[i].get()) : 0;
}
return UniqueChars(joined);
}
UniqueChars
Statistics::formatDescription()
{
int64_t sccTotal, sccLongest;
sccDurations(&sccTotal, &sccLongest);
double mmu20 = computeMMU(20 * PRMJ_USEC_PER_MSEC);
double mmu50 = computeMMU(50 * PRMJ_USEC_PER_MSEC);
const char *format =
"=================================================================\n\
Reason: %s\n\
Incremental: %s%s\n\
Zones Collected: %d of %d\n\
Compartments Collected: %d of %d\n\
MinorGCs since last GC: %d\n\
MMU 20ms:%.3f; 50ms:%.3f\n\
SCC Sweep Total (MaxPause): %.3fms (%.3fms)\n\
HeapSize: %.3f MiB\n\
Chunk Delta (magnitude): %+d (%d)\n\
";
char buffer[1024];
memset(buffer, 0, sizeof(buffer));
snprintf(buffer, sizeof(buffer), format,
ExplainReason(slices[0].reason),
nonincrementalReason ? "no - " : "yes", nonincrementalReason ? nonincrementalReason : "",
zoneStats.collectedZoneCount, zoneStats.zoneCount,
zoneStats.collectedCompartmentCount, zoneStats.compartmentCount,
counts[STAT_MINOR_GC],
mmu20, mmu50,
t(sccTotal), t(sccLongest),
double(preBytes) / 1024. / 1024.,
counts[STAT_NEW_CHUNK] - counts[STAT_DESTROY_CHUNK], counts[STAT_NEW_CHUNK] +
counts[STAT_DESTROY_CHUNK]);
return make_string_copy(buffer);
}
UniqueChars
Statistics::formatSliceDescription(unsigned i, const SliceData &slice)
{
const char *format =
"\
---- Slice %u ----\n\
Reason: %s\n\
Reset: %s%s\n\
Page Faults: %ld\n\
Pause: %.3fms (@ %.3fms)\n\
";
char buffer[1024];
memset(buffer, 0, sizeof(buffer));
snprintf(buffer, sizeof(buffer), format, i,
ExplainReason(slice.reason),
slice.resetReason ? "yes - " : "no", slice.resetReason ? slice.resetReason : "",
uint64_t(slice.endFaults - slice.startFaults),
t(slice.duration()), t(slice.start - slices[0].start));
return make_string_copy(buffer);
}
UniqueChars
Statistics::formatTotals()
{
int64_t total, longest;
gcDuration(&total, &longest);
const char *format =
"\
---- Totals ----\n\
Total Time: %.3f\n\
Max Pause: %.3f\n\
";
char buffer[1024];
memset(buffer, 0, sizeof(buffer));
snprintf(buffer, sizeof(buffer), format, t(total), t(longest));
return make_string_copy(buffer);
}
static int64_t
SumChildTimes(Phase phase, int64_t *phaseTimes)
{
int64_t total = 0;
for (unsigned i = 0; phases[i].name; i++) {
if (phases[i].parent == phase)
total += phaseTimes[phases[i].index];
}
return total;
}
UniqueChars
Statistics::formatPhaseTimes(int64_t *phaseTimes)
{
static const char *LevelToIndent[] = { "", " ", " ", " " };
FragmentVector fragments;
char buffer[128];
for (unsigned i = 0; phases[i].name; i++) {
unsigned level = 0;
unsigned current = i;
while (phases[current].parent != PHASE_NO_PARENT) {
current = phases[current].parent;
level++;
}
MOZ_ASSERT(level < 4);
int64_t ownTime = phaseTimes[phases[i].index];
int64_t childTime = SumChildTimes(Phase(i), phaseTimes);
if (ownTime > 0) {
// If we have children and large parts of the time spent in this
// phase are not accounted to specific children, report the difference
// so that it is more obvious that we are losing time somewhere.
if (childTime && ownTime - childTime > 50) {
snprintf(buffer, sizeof(buffer), " %s%s: %.3fms (unaccounted: %.3fms)\n",
LevelToIndent[level], phases[i].name, t(ownTime), t(ownTime - childTime));
} else {
snprintf(buffer, sizeof(buffer), " %s%s: %.3fms\n",
LevelToIndent[level], phases[i].name, t(ownTime));
}
if (!fragments.append(make_string_copy(buffer)))
return UniqueChars(nullptr);
}
}
return Join(fragments);
}
UniqueChars
Statistics::formatDetailedMessage()
{
FragmentVector fragments;
if (!fragments.append(formatDescription()))
return UniqueChars(nullptr);
if (slices.length() > 1) {
for (unsigned i = 0; i < slices.length(); i++) {
if (!fragments.append(formatSliceDescription(i, slices[i])))
return UniqueChars(nullptr);
if (!fragments.append(formatPhaseTimes(slices[i].phaseTimes)))
return UniqueChars(nullptr);
}
}
if (!fragments.append(formatTotals()))
return UniqueChars(nullptr);
if (!fragments.append(formatPhaseTimes(phaseTimes)))
return UniqueChars(nullptr);
return Join(fragments);
}
char16_t * char16_t *
Statistics::formatMessage() Statistics::formatMessage()
{ {
@ -691,9 +522,13 @@ void
Statistics::printStats() Statistics::printStats()
{ {
if (fullFormat) { if (fullFormat) {
UniqueChars msg = formatDetailedMessage(); StatisticsSerializer ss(StatisticsSerializer::AsText);
if (msg) formatData(ss, 0);
fprintf(fp, "GC(T+%.3fs) %s\n", t(slices[0].start - startupTime) / 1000.0, msg.get()); char *msg = ss.finishCString();
if (msg) {
fprintf(fp, "GC(T+%.3fs) %s\n", t(slices[0].start - startupTime) / 1000.0, msg);
js_free(msg);
}
} else { } else {
int64_t total, longest; int64_t total, longest;
gcDuration(&total, &longest); gcDuration(&total, &longest);

Просмотреть файл

@ -9,7 +9,6 @@
#include "mozilla/DebugOnly.h" #include "mozilla/DebugOnly.h"
#include "mozilla/PodOperations.h" #include "mozilla/PodOperations.h"
#include "mozilla/UniquePtr.h"
#include "jsalloc.h" #include "jsalloc.h"
#include "jspubtd.h" #include "jspubtd.h"
@ -60,12 +59,12 @@ enum Phase {
PHASE_SWEEP_SCRIPT, PHASE_SWEEP_SCRIPT,
PHASE_SWEEP_SHAPE, PHASE_SWEEP_SHAPE,
PHASE_SWEEP_JITCODE, PHASE_SWEEP_JITCODE,
PHASE_FINALIZE_END,
PHASE_DESTROY,
PHASE_COMPACT, PHASE_COMPACT,
PHASE_COMPACT_MOVE, PHASE_COMPACT_MOVE,
PHASE_COMPACT_UPDATE, PHASE_COMPACT_UPDATE,
PHASE_COMPACT_UPDATE_GRAY, PHASE_COMPACT_UPDATE_GRAY,
PHASE_FINALIZE_END,
PHASE_DESTROY,
PHASE_GC_END, PHASE_GC_END,
PHASE_LIMIT PHASE_LIMIT
@ -84,22 +83,17 @@ class StatisticsSerializer;
struct ZoneGCStats struct ZoneGCStats
{ {
/* Number of zones collected in this GC. */ /* Number of zones collected in this GC. */
int collectedZoneCount; int collectedCount;
/* Total number of zones in the Runtime at the start of this GC. */ /* Total number of zones in the Runtime at the start of this GC. */
int zoneCount; int zoneCount;
/* Total number of comaprtments in all zones collected. */
int collectedCompartmentCount;
/* Total number of compartments in the Runtime at the start of this GC. */ /* Total number of compartments in the Runtime at the start of this GC. */
int compartmentCount; int compartmentCount;
bool isCollectingAllZones() const { return collectedZoneCount == zoneCount; } bool isCollectingAllZones() const { return collectedCount == zoneCount; }
ZoneGCStats() ZoneGCStats() : collectedCount(0), zoneCount(0), compartmentCount(0) {}
: collectedZoneCount(0), zoneCount(0), collectedCompartmentCount(0), compartmentCount(0)
{}
}; };
struct Statistics struct Statistics
@ -126,7 +120,6 @@ struct Statistics
char16_t *formatMessage(); char16_t *formatMessage();
char16_t *formatJSON(uint64_t timestamp); char16_t *formatJSON(uint64_t timestamp);
UniqueChars formatDetailedMessage();
JS::GCSliceCallback setSliceCallback(JS::GCSliceCallback callback); JS::GCSliceCallback setSliceCallback(JS::GCSliceCallback callback);
@ -207,11 +200,6 @@ struct Statistics
void printStats(); void printStats();
bool formatData(StatisticsSerializer &ss, uint64_t timestamp); bool formatData(StatisticsSerializer &ss, uint64_t timestamp);
UniqueChars formatDescription();
UniqueChars formatSliceDescription(unsigned i, const SliceData &slice);
UniqueChars formatTotals();
UniqueChars formatPhaseTimes(int64_t *phaseTimes);
double computeMMU(int64_t resolution); double computeMMU(int64_t resolution);
}; };

Просмотреть файл

@ -5637,10 +5637,8 @@ GCRuntime::scanZonesBeforeGC()
zone->scheduleGC(); zone->scheduleGC();
zoneStats.zoneCount++; zoneStats.zoneCount++;
if (zone->isGCScheduled()) { if (zone->isGCScheduled())
zoneStats.collectedZoneCount++; zoneStats.collectedCount++;
zoneStats.collectedCompartmentCount += zone->compartments.length();
}
} }
for (CompartmentsIter c(rt, WithAtoms); !c.done(); c.next()) for (CompartmentsIter c(rt, WithAtoms); !c.done(); c.next())