зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1328385 - Replace the profile entry tag with an enum. r=kvijayan.
--HG-- extra : rebase_source : 4e8de98fc4e89a772e8fdc2261e0ebb8d30e2642
This commit is contained in:
Родитель
2835870c9c
Коммит
11b9557938
|
@ -31,67 +31,50 @@ using mozilla::JSONWriter;
|
|||
|
||||
ProfileEntry::ProfileEntry()
|
||||
: mTagData(nullptr)
|
||||
, mTagName(0)
|
||||
, mKind(Kind::INVALID)
|
||||
{ }
|
||||
|
||||
// aTagData must not need release (i.e. be a string from the text segment)
|
||||
ProfileEntry::ProfileEntry(char aTagName, const char *aTagData)
|
||||
ProfileEntry::ProfileEntry(Kind aKind, const char *aTagData)
|
||||
: mTagData(aTagData)
|
||||
, mTagName(aTagName)
|
||||
, mKind(aKind)
|
||||
{ }
|
||||
|
||||
ProfileEntry::ProfileEntry(char aTagName, ProfilerMarker *aTagMarker)
|
||||
ProfileEntry::ProfileEntry(Kind aKind, ProfilerMarker *aTagMarker)
|
||||
: mTagMarker(aTagMarker)
|
||||
, mTagName(aTagName)
|
||||
, mKind(aKind)
|
||||
{ }
|
||||
|
||||
ProfileEntry::ProfileEntry(char aTagName, void *aTagPtr)
|
||||
ProfileEntry::ProfileEntry(Kind aKind, void *aTagPtr)
|
||||
: mTagPtr(aTagPtr)
|
||||
, mTagName(aTagName)
|
||||
, mKind(aKind)
|
||||
{ }
|
||||
|
||||
ProfileEntry::ProfileEntry(char aTagName, double aTagDouble)
|
||||
ProfileEntry::ProfileEntry(Kind aKind, double aTagDouble)
|
||||
: mTagDouble(aTagDouble)
|
||||
, mTagName(aTagName)
|
||||
, mKind(aKind)
|
||||
{ }
|
||||
|
||||
ProfileEntry::ProfileEntry(char aTagName, uintptr_t aTagOffset)
|
||||
ProfileEntry::ProfileEntry(Kind aKind, uintptr_t aTagOffset)
|
||||
: mTagOffset(aTagOffset)
|
||||
, mTagName(aTagName)
|
||||
, mKind(aKind)
|
||||
{ }
|
||||
|
||||
ProfileEntry::ProfileEntry(char aTagName, Address aTagAddress)
|
||||
ProfileEntry::ProfileEntry(Kind aKind, Address aTagAddress)
|
||||
: mTagAddress(aTagAddress)
|
||||
, mTagName(aTagName)
|
||||
, mKind(aKind)
|
||||
{ }
|
||||
|
||||
ProfileEntry::ProfileEntry(char aTagName, int aTagInt)
|
||||
ProfileEntry::ProfileEntry(Kind aKind, int aTagInt)
|
||||
: mTagInt(aTagInt)
|
||||
, mTagName(aTagName)
|
||||
, mKind(aKind)
|
||||
{ }
|
||||
|
||||
ProfileEntry::ProfileEntry(char aTagName, char aTagChar)
|
||||
ProfileEntry::ProfileEntry(Kind aKind, char aTagChar)
|
||||
: mTagChar(aTagChar)
|
||||
, mTagName(aTagName)
|
||||
, mKind(aKind)
|
||||
{ }
|
||||
|
||||
bool ProfileEntry::is_ent_hint(char hintChar) {
|
||||
return mTagName == 'h' && mTagChar == hintChar;
|
||||
}
|
||||
|
||||
bool ProfileEntry::is_ent_hint() {
|
||||
return mTagName == 'h';
|
||||
}
|
||||
|
||||
bool ProfileEntry::is_ent(char tagChar) {
|
||||
return mTagName == tagChar;
|
||||
}
|
||||
|
||||
void* ProfileEntry::get_tagPtr() {
|
||||
// No consistency checking. Oh well.
|
||||
return mTagPtr;
|
||||
}
|
||||
|
||||
// END ProfileEntry
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
|
@ -607,40 +590,40 @@ void ProfileBuffer::StreamSamplesToJSON(SpliceableJSONWriter& aWriter, int aThre
|
|||
|
||||
while (readPos != mWritePos) {
|
||||
ProfileEntry entry = mEntries[readPos];
|
||||
if (entry.mTagName == 'T') {
|
||||
if (entry.isThreadId()) {
|
||||
currentThreadID = entry.mTagInt;
|
||||
currentTime.reset();
|
||||
int readAheadPos = (readPos + 1) % mEntrySize;
|
||||
if (readAheadPos != mWritePos) {
|
||||
ProfileEntry readAheadEntry = mEntries[readAheadPos];
|
||||
if (readAheadEntry.mTagName == 't') {
|
||||
if (readAheadEntry.isTime()) {
|
||||
currentTime = Some(readAheadEntry.mTagDouble);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (currentThreadID == aThreadId && (currentTime.isNothing() || *currentTime >= aSinceTime)) {
|
||||
switch (entry.mTagName) {
|
||||
case 'r':
|
||||
switch (entry.kind()) {
|
||||
case ProfileEntry::Kind::Responsiveness:
|
||||
if (sample.isSome()) {
|
||||
sample->mResponsiveness = Some(entry.mTagDouble);
|
||||
}
|
||||
break;
|
||||
case 'R':
|
||||
case ProfileEntry::Kind::ResidentMemory:
|
||||
if (sample.isSome()) {
|
||||
sample->mRSS = Some(entry.mTagDouble);
|
||||
}
|
||||
break;
|
||||
case 'U':
|
||||
case ProfileEntry::Kind::UnsharedMemory:
|
||||
if (sample.isSome()) {
|
||||
sample->mUSS = Some(entry.mTagDouble);
|
||||
}
|
||||
break;
|
||||
case 'f':
|
||||
case ProfileEntry::Kind::FrameNumber:
|
||||
if (sample.isSome()) {
|
||||
sample->mFrameNumber = Some(entry.mTagInt);
|
||||
}
|
||||
break;
|
||||
case 's':
|
||||
case ProfileEntry::Kind::Sample:
|
||||
{
|
||||
// end the previous sample if there was one
|
||||
if (sample.isSome()) {
|
||||
|
@ -660,49 +643,51 @@ void ProfileBuffer::StreamSamplesToJSON(SpliceableJSONWriter& aWriter, int aThre
|
|||
|
||||
int framePos = (readPos + 1) % mEntrySize;
|
||||
ProfileEntry frame = mEntries[framePos];
|
||||
while (framePos != mWritePos && frame.mTagName != 's' && frame.mTagName != 'T') {
|
||||
while (framePos != mWritePos && !frame.isSample() && !frame.isThreadId()) {
|
||||
int incBy = 1;
|
||||
frame = mEntries[framePos];
|
||||
|
||||
// Read ahead to the next tag, if it's a 'd' tag process it now
|
||||
// Read ahead to the next tag, if it's an EmbeddedString
|
||||
// tag process it now
|
||||
const char* tagStringData = frame.mTagData;
|
||||
int readAheadPos = (framePos + 1) % mEntrySize;
|
||||
// Make sure the string is always null terminated if it fills up
|
||||
// DYNAMIC_MAX_STRING-2
|
||||
tagBuff[DYNAMIC_MAX_STRING-1] = '\0';
|
||||
|
||||
if (readAheadPos != mWritePos && mEntries[readAheadPos].mTagName == 'd') {
|
||||
if (readAheadPos != mWritePos && mEntries[readAheadPos].isEmbeddedString()) {
|
||||
tagStringData = processDynamicTag(framePos, &incBy, tagBuff.get());
|
||||
}
|
||||
|
||||
// Write one frame. It can have either
|
||||
// 1. only location - 'l' containing a memory address
|
||||
// 2. location and line number - 'c' followed by 'd's,
|
||||
// an optional 'n' and an optional 'y'
|
||||
// 3. a JIT return address - 'j' containing native code address
|
||||
if (frame.mTagName == 'l') {
|
||||
// 1. only location - a NativeLeafAddr containing a memory address
|
||||
// 2. location and line number - a CodeLocation followed by
|
||||
// EmbeddedStrings, an optional LineNumber and an
|
||||
// optional Category
|
||||
// 3. a JitReturnAddress containing a native code address
|
||||
if (frame.isNativeLeafAddr()) {
|
||||
// Bug 753041
|
||||
// We need a double cast here to tell GCC that we don't want to sign
|
||||
// extend 32-bit addresses starting with 0xFXXXXXX.
|
||||
unsigned long long pc = (unsigned long long)(uintptr_t)frame.mTagPtr;
|
||||
snprintf(tagBuff.get(), DYNAMIC_MAX_STRING, "%#llx", pc);
|
||||
stack.AppendFrame(UniqueStacks::OnStackFrameKey(tagBuff.get()));
|
||||
} else if (frame.mTagName == 'c') {
|
||||
} else if (frame.isCodeLocation()) {
|
||||
UniqueStacks::OnStackFrameKey frameKey(tagStringData);
|
||||
readAheadPos = (framePos + incBy) % mEntrySize;
|
||||
if (readAheadPos != mWritePos &&
|
||||
mEntries[readAheadPos].mTagName == 'n') {
|
||||
mEntries[readAheadPos].isLineNumber()) {
|
||||
frameKey.mLine = Some((unsigned) mEntries[readAheadPos].mTagInt);
|
||||
incBy++;
|
||||
}
|
||||
readAheadPos = (framePos + incBy) % mEntrySize;
|
||||
if (readAheadPos != mWritePos &&
|
||||
mEntries[readAheadPos].mTagName == 'y') {
|
||||
mEntries[readAheadPos].isCategory()) {
|
||||
frameKey.mCategory = Some((unsigned) mEntries[readAheadPos].mTagInt);
|
||||
incBy++;
|
||||
}
|
||||
stack.AppendFrame(frameKey);
|
||||
} else if (frame.mTagName == 'J') {
|
||||
} else if (frame.isJitReturnAddr()) {
|
||||
// A JIT frame may expand to multiple frames due to inlining.
|
||||
void* pc = frame.mTagPtr;
|
||||
unsigned depth = aUniqueStacks.LookupJITFrameDepth(pc);
|
||||
|
@ -723,7 +708,9 @@ void ProfileBuffer::StreamSamplesToJSON(SpliceableJSONWriter& aWriter, int aThre
|
|||
sample->mStack = stack.GetOrAddIndex();
|
||||
break;
|
||||
}
|
||||
}
|
||||
default:
|
||||
break;
|
||||
} /* switch (entry.kind()) */
|
||||
}
|
||||
readPos = (readPos + 1) % mEntrySize;
|
||||
}
|
||||
|
@ -739,9 +726,9 @@ void ProfileBuffer::StreamMarkersToJSON(SpliceableJSONWriter& aWriter, int aThre
|
|||
int currentThreadID = -1;
|
||||
while (readPos != mWritePos) {
|
||||
ProfileEntry entry = mEntries[readPos];
|
||||
if (entry.mTagName == 'T') {
|
||||
if (entry.isThreadId()) {
|
||||
currentThreadID = entry.mTagInt;
|
||||
} else if (currentThreadID == aThreadId && entry.mTagName == 'm') {
|
||||
} else if (currentThreadID == aThreadId && entry.isMarker()) {
|
||||
const ProfilerMarker* marker = entry.getMarker();
|
||||
if (marker->GetTime() >= aSinceTime) {
|
||||
entry.getMarker()->StreamJSON(aWriter, aUniqueStacks);
|
||||
|
@ -759,7 +746,7 @@ int ProfileBuffer::FindLastSampleOfThread(int aThreadId)
|
|||
readPos != (mReadPos + mEntrySize - 1) % mEntrySize;
|
||||
readPos = (readPos + mEntrySize - 1) % mEntrySize) {
|
||||
ProfileEntry entry = mEntries[readPos];
|
||||
if (entry.mTagName == 'T' && entry.mTagInt == aThreadId) {
|
||||
if (entry.isThreadId() && entry.mTagInt == aThreadId) {
|
||||
return readPos;
|
||||
}
|
||||
}
|
||||
|
@ -774,7 +761,7 @@ void ProfileBuffer::DuplicateLastSample(int aThreadId)
|
|||
return;
|
||||
}
|
||||
|
||||
MOZ_ASSERT(mEntries[lastSampleStartPos].mTagName == 'T');
|
||||
MOZ_ASSERT(mEntries[lastSampleStartPos].isThreadId());
|
||||
|
||||
addTag(mEntries[lastSampleStartPos]);
|
||||
|
||||
|
@ -782,20 +769,19 @@ void ProfileBuffer::DuplicateLastSample(int aThreadId)
|
|||
for (int readPos = (lastSampleStartPos + 1) % mEntrySize;
|
||||
readPos != mWritePos;
|
||||
readPos = (readPos + 1) % mEntrySize) {
|
||||
switch (mEntries[readPos].mTagName) {
|
||||
case 'T':
|
||||
switch (mEntries[readPos].kind()) {
|
||||
case ProfileEntry::Kind::ThreadId:
|
||||
// We're done.
|
||||
return;
|
||||
case 't':
|
||||
case ProfileEntry::Kind::Time:
|
||||
// Copy with new time
|
||||
addTag(ProfileEntry('t', (mozilla::TimeStamp::Now() - sStartTime).ToMilliseconds()));
|
||||
addTag(ProfileEntry::Time((mozilla::TimeStamp::Now() - sStartTime).ToMilliseconds()));
|
||||
break;
|
||||
case 'm':
|
||||
case ProfileEntry::Kind::Marker:
|
||||
// Don't copy markers
|
||||
break;
|
||||
// Copy anything else we don't know about
|
||||
// L, B, S, c, s, d, l, f, h, r, t, p
|
||||
default:
|
||||
// Copy anything else we don't know about
|
||||
addTag(mEntries[readPos]);
|
||||
break;
|
||||
}
|
||||
|
|
|
@ -25,6 +25,22 @@
|
|||
#include "mozilla/HashFunctions.h"
|
||||
#include "mozilla/UniquePtr.h"
|
||||
|
||||
#define PROFILE_ENTRY_KIND_LIST(_) \
|
||||
_(Category, int) \
|
||||
_(CodeLocation, const char *) \
|
||||
_(EmbeddedString, void *) \
|
||||
_(FrameNumber, int) \
|
||||
_(JitReturnAddr, void *) \
|
||||
_(LineNumber, int) \
|
||||
_(NativeLeafAddr, void *) \
|
||||
_(Marker, ProfilerMarker *) \
|
||||
_(ResidentMemory, double) \
|
||||
_(Responsiveness, double) \
|
||||
_(Sample, const char *) \
|
||||
_(ThreadId, int) \
|
||||
_(Time, double) \
|
||||
_(UnsharedMemory, double)
|
||||
|
||||
// NB: Packing this structure has been shown to cause SIGBUS issues on ARM.
|
||||
#ifndef __arm__
|
||||
#pragma pack(push, 1)
|
||||
|
@ -33,28 +49,46 @@
|
|||
class ProfileEntry
|
||||
{
|
||||
public:
|
||||
enum class Kind : uint8_t {
|
||||
INVALID = 0,
|
||||
# define DEF_ENUM_(k, t) k,
|
||||
PROFILE_ENTRY_KIND_LIST(DEF_ENUM_)
|
||||
# undef DEF_ENUM_
|
||||
LIMIT
|
||||
};
|
||||
|
||||
ProfileEntry();
|
||||
|
||||
private:
|
||||
// aTagData must not need release (i.e. be a string from the text segment)
|
||||
ProfileEntry(char aTagName, const char *aTagData);
|
||||
ProfileEntry(char aTagName, void *aTagPtr);
|
||||
ProfileEntry(char aTagName, ProfilerMarker *aTagMarker);
|
||||
ProfileEntry(char aTagName, double aTagDouble);
|
||||
ProfileEntry(char aTagName, uintptr_t aTagOffset);
|
||||
ProfileEntry(char aTagName, Address aTagAddress);
|
||||
ProfileEntry(char aTagName, int aTagLine);
|
||||
ProfileEntry(char aTagName, char aTagChar);
|
||||
bool is_ent_hint(char hintChar);
|
||||
bool is_ent_hint();
|
||||
bool is_ent(char tagName);
|
||||
void* get_tagPtr();
|
||||
ProfileEntry(Kind aKind, const char *aTagData);
|
||||
ProfileEntry(Kind aKind, void *aTagPtr);
|
||||
ProfileEntry(Kind aKind, ProfilerMarker *aTagMarker);
|
||||
ProfileEntry(Kind aKind, double aTagDouble);
|
||||
ProfileEntry(Kind aKind, uintptr_t aTagOffset);
|
||||
ProfileEntry(Kind aKind, Address aTagAddress);
|
||||
ProfileEntry(Kind aKind, int aTagLine);
|
||||
ProfileEntry(Kind aKind, char aTagChar);
|
||||
|
||||
public:
|
||||
# define DEF_MAKE_(k, t) \
|
||||
static ProfileEntry k(t val) { return ProfileEntry(Kind::k, val); }
|
||||
PROFILE_ENTRY_KIND_LIST(DEF_MAKE_)
|
||||
# undef DEF_MAKE_
|
||||
|
||||
Kind kind() const { return mKind; }
|
||||
bool hasKind(Kind k) const { return kind() == k; }
|
||||
|
||||
# define DEF_METHODS_(k, t) \
|
||||
bool is##k() const { return hasKind(Kind::k); }
|
||||
PROFILE_ENTRY_KIND_LIST(DEF_METHODS_)
|
||||
# undef DEF_METHODS_
|
||||
|
||||
const ProfilerMarker* getMarker() {
|
||||
MOZ_ASSERT(mTagName == 'm');
|
||||
MOZ_ASSERT(isMarker());
|
||||
return mTagMarker;
|
||||
}
|
||||
|
||||
char getTagName() const { return mTagName; }
|
||||
|
||||
private:
|
||||
FRIEND_TEST(ThreadProfile, InsertOneTag);
|
||||
FRIEND_TEST(ThreadProfile, InsertOneTagWithTinyBuffer);
|
||||
|
@ -73,7 +107,7 @@ private:
|
|||
int mTagInt;
|
||||
char mTagChar;
|
||||
};
|
||||
char mTagName;
|
||||
Kind mKind;
|
||||
};
|
||||
|
||||
#ifndef __arm__
|
||||
|
|
|
@ -767,9 +767,9 @@ void PseudoStack::flushSamplerOnJSShutdown()
|
|||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
static
|
||||
void addDynamicTag(ThreadInfo& aInfo, char aTagName, const char* aStr)
|
||||
void addDynamicCodeLocationTag(ThreadInfo& aInfo, const char* aStr)
|
||||
{
|
||||
aInfo.addTag(ProfileEntry(aTagName, ""));
|
||||
aInfo.addTag(ProfileEntry::CodeLocation(""));
|
||||
// Add one to store the null termination
|
||||
size_t strLen = strlen(aStr) + 1;
|
||||
for (size_t j = 0; j < strLen;) {
|
||||
|
@ -782,7 +782,7 @@ void addDynamicTag(ThreadInfo& aInfo, char aTagName, const char* aStr)
|
|||
memcpy(text, &aStr[j], len);
|
||||
j += sizeof(void*)/sizeof(char);
|
||||
// Cast to *((void**) to pass the text data to a void*
|
||||
aInfo.addTag(ProfileEntry('d', *((void**)(&text[0]))));
|
||||
aInfo.addTag(ProfileEntry::EmbeddedString(*((void**)(&text[0]))));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -797,14 +797,14 @@ void addPseudoEntry(volatile StackEntry& entry, ThreadInfo& aInfo,
|
|||
|
||||
int lineno = -1;
|
||||
|
||||
// First entry has tagName 's' (start)
|
||||
// First entry has kind CodeLocation
|
||||
// Check for magic pointer bit 1 to indicate copy
|
||||
const char* sampleLabel = entry.label();
|
||||
if (entry.isCopyLabel()) {
|
||||
// Store the string using 1 or more 'd' (dynamic) tags
|
||||
// Store the string using 1 or more EmbeddedString tags
|
||||
// that will happen to the preceding tag
|
||||
|
||||
addDynamicTag(aInfo, 'c', sampleLabel);
|
||||
addDynamicCodeLocationTag(aInfo, sampleLabel);
|
||||
if (entry.isJs()) {
|
||||
JSScript* script = entry.script();
|
||||
if (script) {
|
||||
|
@ -827,7 +827,7 @@ void addPseudoEntry(volatile StackEntry& entry, ThreadInfo& aInfo,
|
|||
lineno = entry.line();
|
||||
}
|
||||
} else {
|
||||
aInfo.addTag(ProfileEntry('c', sampleLabel));
|
||||
aInfo.addTag(ProfileEntry::CodeLocation(sampleLabel));
|
||||
|
||||
// XXX: Bug 1010578. Don't assume a CPP entry and try to get the
|
||||
// line for js entries as well.
|
||||
|
@ -837,7 +837,7 @@ void addPseudoEntry(volatile StackEntry& entry, ThreadInfo& aInfo,
|
|||
}
|
||||
|
||||
if (lineno != -1) {
|
||||
aInfo.addTag(ProfileEntry('n', lineno));
|
||||
aInfo.addTag(ProfileEntry::LineNumber(lineno));
|
||||
}
|
||||
|
||||
uint32_t category = entry.category();
|
||||
|
@ -845,7 +845,7 @@ void addPseudoEntry(volatile StackEntry& entry, ThreadInfo& aInfo,
|
|||
MOZ_ASSERT(!(category & StackEntry::FRAME_LABEL_COPY));
|
||||
|
||||
if (category) {
|
||||
aInfo.addTag(ProfileEntry('y', (int)category));
|
||||
aInfo.addTag(ProfileEntry::Category((int)category));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -928,7 +928,7 @@ mergeStacksIntoProfile(ThreadInfo& aInfo, TickSample* aSample,
|
|||
}
|
||||
|
||||
// Start the sample with a root entry.
|
||||
aInfo.addTag(ProfileEntry('s', "(root)"));
|
||||
aInfo.addTag(ProfileEntry::Sample("(root)"));
|
||||
|
||||
// While the pseudo-stack array is ordered oldest-to-youngest, the JS and
|
||||
// native arrays are ordered youngest-to-oldest. We must add frames to
|
||||
|
@ -1012,7 +1012,7 @@ mergeStacksIntoProfile(ThreadInfo& aInfo, TickSample* aSample,
|
|||
|
||||
// Stringifying non-wasm JIT frames is delayed until streaming
|
||||
// time. To re-lookup the entry in the JitcodeGlobalTable, we need to
|
||||
// store the JIT code address ('J') in the circular buffer.
|
||||
// store the JIT code address (OptInfoAddr) in the circular buffer.
|
||||
//
|
||||
// Note that we cannot do this when we are sychronously sampling the
|
||||
// current thread; that is, when called from profiler_get_backtrace. The
|
||||
|
@ -1020,16 +1020,16 @@ mergeStacksIntoProfile(ThreadInfo& aInfo, TickSample* aSample,
|
|||
// amount of time, such as in nsRefreshDriver. Problematically, the
|
||||
// stored backtrace may be alive across a GC during which the profiler
|
||||
// itself is disabled. In that case, the JS engine is free to discard
|
||||
// its JIT code. This means that if we inserted such 'J' entries into
|
||||
// the buffer, nsRefreshDriver would now be holding on to a backtrace
|
||||
// with stale JIT code return addresses.
|
||||
// its JIT code. This means that if we inserted such OptInfoAddr entries
|
||||
// into the buffer, nsRefreshDriver would now be holding on to a
|
||||
// backtrace with stale JIT code return addresses.
|
||||
if (aSample->isSamplingCurrentThread ||
|
||||
jsFrame.kind == JS::ProfilingFrameIterator::Frame_Wasm) {
|
||||
addDynamicTag(aInfo, 'c', jsFrame.label);
|
||||
addDynamicCodeLocationTag(aInfo, jsFrame.label);
|
||||
} else {
|
||||
MOZ_ASSERT(jsFrame.kind == JS::ProfilingFrameIterator::Frame_Ion ||
|
||||
jsFrame.kind == JS::ProfilingFrameIterator::Frame_Baseline);
|
||||
aInfo.addTag(ProfileEntry('J', jsFrames[jsIndex].returnAddress));
|
||||
aInfo.addTag(ProfileEntry::JitReturnAddr(jsFrames[jsIndex].returnAddress));
|
||||
}
|
||||
|
||||
jsIndex--;
|
||||
|
@ -1041,7 +1041,7 @@ mergeStacksIntoProfile(ThreadInfo& aInfo, TickSample* aSample,
|
|||
if (nativeStackAddr) {
|
||||
MOZ_ASSERT(nativeIndex >= 0);
|
||||
aInfo
|
||||
.addTag(ProfileEntry('l', (void*)aNativeStack.pc_array[nativeIndex]));
|
||||
.addTag(ProfileEntry::NativeLeafAddr((void*)aNativeStack.pc_array[nativeIndex]));
|
||||
}
|
||||
if (nativeIndex >= 0) {
|
||||
nativeIndex--;
|
||||
|
@ -1299,7 +1299,7 @@ doSampleStackTrace(ThreadInfo& aInfo, TickSample* aSample,
|
|||
|
||||
#ifdef ENABLE_LEAF_DATA
|
||||
if (aSample && aAddLeafAddresses) {
|
||||
aInfo.addTag(ProfileEntry('l', (void*)aSample->pc));
|
||||
aInfo.addTag(ProfileEntry::NativeLeafAddr((void*)aSample->pc));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
@ -1316,10 +1316,10 @@ Sampler::InplaceTick(TickSample* sample)
|
|||
{
|
||||
ThreadInfo& currThreadInfo = *sample->threadInfo;
|
||||
|
||||
currThreadInfo.addTag(ProfileEntry('T', currThreadInfo.ThreadId()));
|
||||
currThreadInfo.addTag(ProfileEntry::ThreadId(currThreadInfo.ThreadId()));
|
||||
|
||||
mozilla::TimeDuration delta = sample->timestamp - sStartTime;
|
||||
currThreadInfo.addTag(ProfileEntry('t', delta.ToMilliseconds()));
|
||||
currThreadInfo.addTag(ProfileEntry::Time(delta.ToMilliseconds()));
|
||||
|
||||
PseudoStack* stack = currThreadInfo.Stack();
|
||||
|
||||
|
@ -1341,27 +1341,27 @@ Sampler::InplaceTick(TickSample* sample)
|
|||
while (pendingMarkersList && pendingMarkersList->peek()) {
|
||||
ProfilerMarker* marker = pendingMarkersList->popHead();
|
||||
currThreadInfo.addStoredMarker(marker);
|
||||
currThreadInfo.addTag(ProfileEntry('m', marker));
|
||||
currThreadInfo.addTag(ProfileEntry::Marker(marker));
|
||||
}
|
||||
}
|
||||
|
||||
if (currThreadInfo.GetThreadResponsiveness()->HasData()) {
|
||||
mozilla::TimeDuration delta = currThreadInfo.GetThreadResponsiveness()->GetUnresponsiveDuration(sample->timestamp);
|
||||
currThreadInfo.addTag(ProfileEntry('r', delta.ToMilliseconds()));
|
||||
currThreadInfo.addTag(ProfileEntry::Responsiveness(delta.ToMilliseconds()));
|
||||
}
|
||||
|
||||
// rssMemory is equal to 0 when we are not recording.
|
||||
if (sample->rssMemory != 0) {
|
||||
currThreadInfo.addTag(ProfileEntry('R', static_cast<double>(sample->rssMemory)));
|
||||
currThreadInfo.addTag(ProfileEntry::ResidentMemory(static_cast<double>(sample->rssMemory)));
|
||||
}
|
||||
|
||||
// ussMemory is equal to 0 when we are not recording.
|
||||
if (sample->ussMemory != 0) {
|
||||
currThreadInfo.addTag(ProfileEntry('U', static_cast<double>(sample->ussMemory)));
|
||||
currThreadInfo.addTag(ProfileEntry::UnsharedMemory(static_cast<double>(sample->ussMemory)));
|
||||
}
|
||||
|
||||
if (sLastFrameNumber != sFrameNumber) {
|
||||
currThreadInfo.addTag(ProfileEntry('f', sFrameNumber));
|
||||
currThreadInfo.addTag(ProfileEntry::FrameNumber(sFrameNumber));
|
||||
sLastFrameNumber = sFrameNumber;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -23,9 +23,9 @@ TEST(ThreadProfile, InsertOneTag) {
|
|||
Thread::tid_t tid = 1000;
|
||||
ThreadInfo info("testThread", tid, true, stack, nullptr);
|
||||
RefPtr<ProfileBuffer> pb = new ProfileBuffer(10);
|
||||
pb->addTag(ProfileEntry('t', 123.1));
|
||||
pb->addTag(ProfileEntry::Time(123.1));
|
||||
ASSERT_TRUE(pb->mEntries != nullptr);
|
||||
ASSERT_TRUE(pb->mEntries[pb->mReadPos].mTagName == 't');
|
||||
ASSERT_TRUE(pb->mEntries[pb->mReadPos].kind() == ProfileEntry::Kind::Time);
|
||||
ASSERT_TRUE(pb->mEntries[pb->mReadPos].mTagDouble == 123.1);
|
||||
}
|
||||
|
||||
|
@ -37,13 +37,13 @@ TEST(ThreadProfile, InsertTagsNoWrap) {
|
|||
RefPtr<ProfileBuffer> pb = new ProfileBuffer(100);
|
||||
int test_size = 50;
|
||||
for (int i = 0; i < test_size; i++) {
|
||||
pb->addTag(ProfileEntry('t', i));
|
||||
pb->addTag(ProfileEntry::Time(i));
|
||||
}
|
||||
ASSERT_TRUE(pb->mEntries != nullptr);
|
||||
int readPos = pb->mReadPos;
|
||||
while (readPos != pb->mWritePos) {
|
||||
ASSERT_TRUE(pb->mEntries[readPos].mTagName == 't');
|
||||
ASSERT_TRUE(pb->mEntries[readPos].mTagInt == readPos);
|
||||
ASSERT_TRUE(pb->mEntries[readPos].kind() == ProfileEntry::Kind::Time);
|
||||
ASSERT_TRUE(pb->mEntries[readPos].mTagDouble == readPos);
|
||||
readPos = (readPos + 1) % pb->mEntrySize;
|
||||
}
|
||||
}
|
||||
|
@ -59,15 +59,15 @@ TEST(ThreadProfile, InsertTagsWrap) {
|
|||
RefPtr<ProfileBuffer> pb = new ProfileBuffer(buffer_size);
|
||||
int test_size = 43;
|
||||
for (int i = 0; i < test_size; i++) {
|
||||
pb->addTag(ProfileEntry('t', i));
|
||||
pb->addTag(ProfileEntry::Time(i));
|
||||
}
|
||||
ASSERT_TRUE(pb->mEntries != nullptr);
|
||||
int readPos = pb->mReadPos;
|
||||
int ctr = 0;
|
||||
while (readPos != pb->mWritePos) {
|
||||
ASSERT_TRUE(pb->mEntries[readPos].mTagName == 't');
|
||||
ASSERT_TRUE(pb->mEntries[readPos].kind() == ProfileEntry::Kind::Time);
|
||||
// the first few tags were discarded when we wrapped
|
||||
ASSERT_TRUE(pb->mEntries[readPos].mTagInt == ctr + (test_size - tags));
|
||||
ASSERT_TRUE(pb->mEntries[readPos].mTagDouble == ctr + (test_size - tags));
|
||||
ctr++;
|
||||
readPos = (readPos + 1) % pb->mEntrySize;
|
||||
}
|
||||
|
|
Загрузка…
Ссылка в новой задаче