Bug 1542830: Part 7 - Support MFBT Vector in ProcessedStack and add Swap operation to CombinedStacks; r=janerik

Untrusted modules 2.0 uses MFBT `Vector`, so this patch adds the ability for
`ProcessedStack` to receive those as input.

Depends on D43160

Differential Revision: https://phabricator.services.mozilla.com/D43161

--HG--
extra : moz-landing-system : lando
This commit is contained in:
Aaron Klotz 2019-09-23 20:19:42 +00:00
Родитель a66f824994
Коммит 7eea579d88
4 изменённых файлов: 80 добавлений и 22 удалений

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

@ -104,6 +104,19 @@ void CombinedStacks::RemoveStack(unsigned aIndex) {
}
}
void CombinedStacks::Swap(CombinedStacks& aOther) {
mModules.swap(aOther.mModules);
mStacks.swap(aOther.mStacks);
size_t nextIndex = aOther.mNextIndex;
aOther.mNextIndex = mNextIndex;
mNextIndex = nextIndex;
size_t maxStacksCount = aOther.mMaxStacksCount;
aOther.mMaxStacksCount = mMaxStacksCount;
mMaxStacksCount = maxStacksCount;
}
#if defined(MOZ_GECKO_PROFILER)
void CombinedStacks::Clear() {
mNextIndex = 0;

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

@ -25,6 +25,11 @@ class CombinedStacks {
explicit CombinedStacks();
explicit CombinedStacks(size_t aMaxStacksCount);
CombinedStacks(CombinedStacks&&) = default;
CombinedStacks& operator=(CombinedStacks&&) = default;
void Swap(CombinedStacks& aOther);
typedef std::vector<Telemetry::ProcessedStack::Frame> Stack;
const Telemetry::ProcessedStack::Module& GetModule(unsigned aIndex) const;
size_t GetModuleCount() const;

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

@ -76,25 +76,19 @@ BatchProcessedStackGenerator::BatchProcessedStackGenerator()
#endif
}
ProcessedStack BatchProcessedStackGenerator::GetStackAndModules(
const std::vector<uintptr_t>& aPCs) {
std::vector<StackFrame> rawStack;
auto stackEnd = aPCs.begin() + std::min(aPCs.size(), kMaxChromeStackDepth);
for (auto i = aPCs.begin(); i != stackEnd; ++i) {
uintptr_t aPC = *i;
StackFrame Frame = {aPC, static_cast<uint16_t>(rawStack.size()),
std::numeric_limits<uint16_t>::max()};
rawStack.push_back(Frame);
}
#ifdef MOZ_GECKO_PROFILER
SharedLibraryInfo rawModules(mSortedRawModules);
#ifndef MOZ_GECKO_PROFILER
static ProcessedStack GetStackAndModulesInternal(
std::vector<StackFrame>& aRawStack) {
#else
static ProcessedStack GetStackAndModulesInternal(
std::vector<StackFrame>& aRawStack, SharedLibraryInfo& aSortedRawModules) {
SharedLibraryInfo rawModules(aSortedRawModules);
// Remove all modules not referenced by a PC on the stack
std::sort(rawStack.begin(), rawStack.end(), CompareByPC);
std::sort(aRawStack.begin(), aRawStack.end(), CompareByPC);
size_t moduleIndex = 0;
size_t stackIndex = 0;
size_t stackSize = rawStack.size();
size_t stackSize = aRawStack.size();
while (moduleIndex < rawModules.GetSize()) {
const SharedLibrary& module = rawModules.GetEntry(moduleIndex);
@ -104,20 +98,20 @@ ProcessedStack BatchProcessedStackGenerator::GetStackAndModules(
bool moduleReferenced = false;
for (; stackIndex < stackSize; ++stackIndex) {
uintptr_t pc = rawStack[stackIndex].mPC;
uintptr_t pc = aRawStack[stackIndex].mPC;
if (pc >= moduleEnd) break;
if (pc >= moduleStart) {
// If the current PC is within the current module, mark
// module as used
moduleReferenced = true;
rawStack[stackIndex].mPC -= moduleStart;
rawStack[stackIndex].mModIndex = moduleIndex;
aRawStack[stackIndex].mPC -= moduleStart;
aRawStack[stackIndex].mModIndex = moduleIndex;
} else {
// PC does not belong to any module. It is probably from
// the JIT. Use a fixed mPC so that we don't get different
// stacks on different runs.
rawStack[stackIndex].mPC = std::numeric_limits<uintptr_t>::max();
aRawStack[stackIndex].mPC = std::numeric_limits<uintptr_t>::max();
}
}
@ -131,15 +125,15 @@ ProcessedStack BatchProcessedStackGenerator::GetStackAndModules(
for (; stackIndex < stackSize; ++stackIndex) {
// These PCs are past the last module.
rawStack[stackIndex].mPC = std::numeric_limits<uintptr_t>::max();
aRawStack[stackIndex].mPC = std::numeric_limits<uintptr_t>::max();
}
std::sort(rawStack.begin(), rawStack.end(), CompareByIndex);
std::sort(aRawStack.begin(), aRawStack.end(), CompareByIndex);
#endif
// Copy the information to the return value.
ProcessedStack Ret;
for (auto& rawFrame : rawStack) {
for (auto& rawFrame : aRawStack) {
mozilla::Telemetry::ProcessedStack::Frame frame = {rawFrame.mPC,
rawFrame.mModIndex};
Ret.AddFrame(frame);
@ -157,5 +151,40 @@ ProcessedStack BatchProcessedStackGenerator::GetStackAndModules(
return Ret;
}
ProcessedStack BatchProcessedStackGenerator::GetStackAndModules(
const std::vector<uintptr_t>& aPCs) {
std::vector<StackFrame> rawStack;
auto stackEnd = aPCs.begin() + std::min(aPCs.size(), kMaxChromeStackDepth);
for (auto i = aPCs.begin(); i != stackEnd; ++i) {
uintptr_t aPC = *i;
StackFrame Frame = {aPC, static_cast<uint16_t>(rawStack.size()),
std::numeric_limits<uint16_t>::max()};
rawStack.push_back(Frame);
}
#if defined(MOZ_GECKO_PROFILER)
return GetStackAndModulesInternal(rawStack, mSortedRawModules);
#else
return GetStackAndModulesInternal(rawStack);
#endif
}
ProcessedStack BatchProcessedStackGenerator::GetStackAndModules(
const uintptr_t* aBegin, const uintptr_t* aEnd) {
std::vector<StackFrame> rawStack;
for (auto i = aBegin; i != aEnd; ++i) {
uintptr_t aPC = *i;
StackFrame Frame = {aPC, static_cast<uint16_t>(rawStack.size()),
std::numeric_limits<uint16_t>::max()};
rawStack.push_back(Frame);
}
#if defined(MOZ_GECKO_PROFILER)
return GetStackAndModulesInternal(rawStack, mSortedRawModules);
#else
return GetStackAndModulesInternal(rawStack);
#endif
}
} // namespace Telemetry
} // namespace mozilla

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

@ -8,6 +8,8 @@
#include <string>
#include <vector>
#include "mozilla/Vector.h"
#include "nsString.h"
#if defined(MOZ_GECKO_PROFILER)
# include "shared-libraries.h"
@ -64,7 +66,16 @@ class BatchProcessedStackGenerator {
BatchProcessedStackGenerator();
ProcessedStack GetStackAndModules(const std::vector<uintptr_t>& aPCs);
template <typename AllocatorPolicy>
ProcessedStack GetStackAndModules(
const Vector<void*, 0, AllocatorPolicy>& aPCs) {
return GetStackAndModules(reinterpret_cast<const uintptr_t*>(aPCs.begin()),
reinterpret_cast<const uintptr_t*>(aPCs.end()));
}
private:
ProcessedStack GetStackAndModules(const uintptr_t* aBegin,
const uintptr_t* aEnd);
#if defined(MOZ_GECKO_PROFILER)
SharedLibraryInfo mSortedRawModules;
#endif