This commit is contained in:
yuyanqinghw 2024-03-28 11:30:45 +08:00
commit cd66ef8ffc
19 changed files with 190 additions and 83 deletions

View File

@ -557,9 +557,10 @@ size_t CallStack::DoExpandCallStack(std::vector<DfxFrame> &newCallFrames,
// in case1 newIt -> C
// in case2 newIt -> B
const auto newIt = newCallFrames.end() - expandLimit;
HLOGM("try find new call chain bottom %s for limit %zu", newIt->ToString().c_str(),
expandLimit);
if (newIt != newCallFrames.end()) {
HLOGM("try find new call chain bottom %s for limit %zu", newIt->ToString().c_str(),
expandLimit);
}
// first frame search, from called - > caller
// for case 2 it should found B
@ -682,6 +683,9 @@ bool CallStack::DoUnwind2(const VirtualThread &thread, std::vector<DfxFrame> &ca
static std::shared_ptr<DfxRegs> regs = std::make_shared<DfxRegsArm64>();
regs->SetRegsData((uintptr_t*)(regs_), regsNum_);
#endif
if (unwinder == nullptr) {
return false;
}
unwinder->SetRegs(regs);
unwinder->Unwind(&unwindInfo);
callStack = unwinder->GetFrames();
@ -690,7 +694,8 @@ bool CallStack::DoUnwind2(const VirtualThread &thread, std::vector<DfxFrame> &ca
HLOGD("pc 0x%" PRIx64 " sp 0x%" PRIx64 "", frame.pc, frame.sp);
}
auto lastIt = callStack.end() - 1;
if (lastIt->pc == (lastIt - 1)->pc && lastIt->sp == (lastIt - 1)->sp) {
auto preIt = lastIt - 1;
if (callStack.size() > 1 && lastIt->pc == preIt->pc && lastIt->sp == preIt->sp) {
callStack.erase(lastIt);
HLOGD("remove last callframe");
}
@ -712,6 +717,9 @@ int CallStack::FillUnwindTable(SymbolsFile *symbolsFile, std::shared_ptr<DfxMap>
uintptr_t pc, UnwindTableInfo& outTableInfo)
{
HLOGM("try search debug info at %s", symbolsFile->filePath_.c_str());
if (unwindInfoPtr == nullptr) {
return -1;
}
auto &tableInfoMap = unwindInfoPtr->callStack.unwindTableInfoMap_;
// all the thread in same process have same mmap and symbols
if (tableInfoMap.find(unwindInfoPtr->thread.pid_) == tableInfoMap.end()) {
@ -748,6 +756,9 @@ int CallStack::FillUnwindTable(SymbolsFile *symbolsFile, std::shared_ptr<DfxMap>
int CallStack::FindUnwindTable(uintptr_t pc, UnwindTableInfo& outTableInfo, void *arg)
{
UnwindInfo *unwindInfoPtr = static_cast<UnwindInfo *>(arg);
if (unwindInfoPtr == nullptr) {
return -1;
}
int64_t mapIndex = unwindInfoPtr->thread.FindMapIndexByAddr(pc);
if (mapIndex >= 0) {
auto map = unwindInfoPtr->thread.GetMaps()[mapIndex];
@ -775,8 +786,9 @@ int CallStack::AccessMem2(uintptr_t addr, uintptr_t *val, void *arg)
*val = 0;
/* Check overflow. */
if (addr + sizeof(uintptr_t) < addr) {
HLOGE("address overflow at 0x%" UNW_WORD_PFLAG " increase 0x%zu", addr, sizeof(uintptr_t));
if (unwindInfoPtr == nullptr || addr + sizeof(uintptr_t) < addr) {
HLOGE("unwindInfoPtr is null or address overflow at 0x%" UNW_WORD_PFLAG " increase 0x%zu",
addr, sizeof(uintptr_t));
return -1;
}

View File

@ -166,6 +166,9 @@ bool RegisterMainOption(const std::string &optionName, const std::string &help,
if (g_MainOptions.count(optionName) == 0) {
g_MainOptions[optionName] = std::make_unique<MainOption>();
if (g_MainOptions[optionName].get() == nullptr) {
return false;
}
g_MainOptions[optionName].get()->help = help;
g_MainOptions[optionName].get()->callBackFunction = std::move(callBackFunction);
return true;

View File

@ -597,21 +597,23 @@ PerfRecordMmap2::PerfRecordMmap2(bool inKernel, u32 pid, u32 tid, std::shared_pt
{
data_.pid = pid;
data_.tid = tid;
data_.addr = item->begin;
data_.len = item->end - item->begin;
data_.pgoff = item->offset;
data_.maj = item->major;
data_.min = item->minor;
data_.ino = item->inode;
data_.ino_generation = 0;
// r--p 00000000 103:3e 12307 /data/storage/el1/bundle/entry.hap
// why prot get from this is 7. rwxp
DfxMap::PermsToProts(item->perms, data_.prot, data_.flags);
if (strncpy_s(data_.filename, KILO, item->name.c_str(), item->name.size()) != 0) {
HLOGE("strncpy_s failed");
}
if (item != nullptr) {
data_.addr = item->begin;
data_.len = item->end - item->begin;
data_.pgoff = item->offset;
data_.maj = item->major;
data_.min = item->minor;
data_.ino = item->inode;
data_.ino_generation = 0;
// r--p 00000000 103:3e 12307 /data/storage/el1/bundle/entry.hap
// why prot get from this is 7. rwxp
DfxMap::PermsToProts(item->perms, data_.prot, data_.flags);
if (strncpy_s(data_.filename, KILO, item->name.c_str(), item->name.size()) != 0) {
HLOGE("strncpy_s failed");
}
header.size = sizeof(header) + sizeof(data_) - KILO + item->name.size() + 1;
header.size = sizeof(header) + sizeof(data_) - KILO + item->name.size() + 1;
}
}
bool PerfRecordMmap2::GetBinary(std::vector<uint8_t> &buf) const

View File

@ -705,7 +705,8 @@ void PerfEvents::LoadTracepointEventTypesFromSystem()
for (const auto &concreteEvent : GetSubDirs(eventPath)) {
std::string idPath = eventPath + "/" + concreteEvent + "/id";
{
std::ifstream ifs {idPath};
std::string resolvedPath = CanonicalizeSpecPath(idPath.c_str());
std::ifstream ifs {resolvedPath};
// clang-format off
const std::string idStr = {
std::istream_iterator<char>(ifs),

View File

@ -344,6 +344,9 @@ bool PerfFileSectionUniStackTable::GetBinary(char *buf, size_t size)
Write(uint32_t(processStackTable_->size()));
for (auto it = processStackTable_->begin(); it != processStackTable_->end(); ++it) {
const auto &table = it->second;
if (table == nullptr) {
continue;
}
Write(table->GetPid());
Write(table->GetTabelSize());
const auto &idxs = table->GetUsedIndexes();
@ -352,6 +355,9 @@ bool PerfFileSectionUniStackTable::GetBinary(char *buf, size_t size)
Node *node = nullptr;
for (const auto idx : idxs) {
node = head + idx;
if (node == nullptr) {
continue;
}
Write(idx);
Write(node->value);
}

View File

@ -199,7 +199,9 @@ bool PerfFileReader::ReadIdsForAttr(const perf_file_attr &attr, std::vector<uint
HLOGE("fseek() failed");
return false;
}
if (ids == nullptr) {
return false;
}
ids->resize(count);
if (!Read(ids->data(), attr.ids.size)) {
return false;
@ -270,7 +272,7 @@ bool PerfFileReader::ReadRecord(ProcessRecordCB &callback)
return false;
} else {
perf_event_header *header = reinterpret_cast<perf_event_header *>(buf);
if (header->size > sizeof(buf)) {
if (header == nullptr || header->size > sizeof(buf)) {
HLOGE("read record header size error %hu", header->size);
return false;
}

View File

@ -312,6 +312,9 @@ bool PerfFileWriter::WriteAttrAndId(const std::vector<AttrWithId> &attrIds)
static bool LeftLessRight(const std::unique_ptr<PerfFileSection> &l,
const std::unique_ptr<PerfFileSection> &r)
{
if (l == nullptr || r == nullptr) {
return false;
}
return l->featureId_ < r->featureId_;
}
// to write perf_file_header to file

View File

@ -69,17 +69,19 @@ void Report::AddReportItem(const PerfRecordSample &sample, bool includeCallStack
}
} else {
auto frameIt = sample.callFrames_.begin();
HLOG_ASSERT(frameIt->pc < PERF_CONTEXT_MAX);
// for arkjs frame, skip the stub.an frame
if (StringEndsWith(frameIt->mapName, "stub.an")) {
HLOGV("stub.an frame, go to next, mapname %s", frameIt->mapName.c_str());
frameIt++;
if (frameIt != sample.callFrames_.end()) {
HLOG_ASSERT(frameIt->pc < PERF_CONTEXT_MAX);
// for arkjs frame, skip the stub.an frame
if (StringEndsWith(frameIt->mapName, "stub.an")) {
HLOGV("stub.an frame, go to next, mapname %s", frameIt->mapName.c_str());
frameIt++;
}
ReportItem &item = configs_[configIndex].reportItems_.emplace_back(
sample.data_.pid, sample.data_.tid, thread.name_, frameIt->mapName,
frameIt->funcName, frameIt->funcOffset, sample.data_.period);
HLOGV("%s", item.ToDebugString().c_str());
HLOG_ASSERT(!item.func_.empty());
}
ReportItem &item = configs_[configIndex].reportItems_.emplace_back(
sample.data_.pid, sample.data_.tid, thread.name_, frameIt->mapName,
frameIt->funcName, frameIt->funcOffset, sample.data_.period);
HLOGV("%s", item.ToDebugString().c_str());
HLOG_ASSERT(!item.func_.empty());
}
}
configs_[configIndex].sampleCount_++;
@ -391,7 +393,7 @@ void Report::OutputStdHead(ReportEventConfigItem &config, bool diffMode)
if (remainingWidth == 0) {
key.maxLen_ = 0;
}
if (fprintf(output_, "%-*s ", (remainingWidth > 0) ? static_cast<int>(key.maxLen_) : 0,
if (fprintf(output_, "%-*s ", (remainingWidth > 0) ? static_cast<unsigned int>(key.maxLen_) : 0,
key.keyName_.c_str()) < 0) {
return;
}

View File

@ -104,6 +104,9 @@ uint8_t *RingBuffer::GetReadData()
}
// else |---readPos<---data--->writePos---|
perf_event_header *header = reinterpret_cast<perf_event_header *>(buf_.get() + readPos);
if (header == nullptr) {
return nullptr;
}
readSize_ += header->size;
return buf_.get() + readPos;
}

View File

@ -42,14 +42,19 @@ bool SubCommandHelp::OnHelp(std::vector<std::string> &args)
printf("options:\n");
for (const auto &commandOption : mainOptions) {
printf("\t%-20s\t%s\n", commandOption.first.c_str(),
commandOption.second->help.c_str());
if (commandOption.second != nullptr) {
printf("\t%-20s\t%s\n", commandOption.first.c_str(),
commandOption.second->help.c_str());
}
}
auto &commands = SubCommand::GetSubCommands();
HLOGD("%zu cmds found:", commands.size());
printf("command:\n");
for (const auto &command : commands) {
if (command.second == nullptr) {
continue;
}
printf("\t%s:\t%s\n", command.second->Name().c_str(), command.second->Brief().c_str());
}
printf("\nSee 'hiperf help [command]' for more information on a specific command.\n\n");

View File

@ -1614,6 +1614,9 @@ void SubCommandRecord::SymbolicHits()
bool SubCommandRecord::CollectionSymbol(std::unique_ptr<PerfEventRecord> record)
{
if (record == nullptr) {
return false;
}
if (record->GetType() == PERF_RECORD_SAMPLE) {
PerfRecordSample *sample = static_cast<PerfRecordSample *>(record.get());
#if USE_COLLECT_SYMBOLIC
@ -1629,6 +1632,9 @@ bool SubCommandRecord::CollectionSymbol(std::unique_ptr<PerfEventRecord> record)
void SubCommandRecord::CollectSymbol(PerfRecordSample *sample)
{
if (sample == nullptr) {
return;
}
perf_callchain_context context = sample->inKernel() ? PERF_CONTEXT_KERNEL
: PERF_CONTEXT_USER;
pid_t server_pid;

View File

@ -359,6 +359,9 @@ void SubCommandReport::LoadEventDesc()
{
const PerfFileSection *featureSection =
recordFileReader_->GetFeatureSection(FEATURE::EVENT_DESC);
if (featureSection == nullptr) {
return;
}
const PerfFileSectionEventDesc &sectionEventdesc =
*static_cast<const PerfFileSectionEventDesc *>(featureSection);
HLOGV("Event descriptions: %zu", sectionEventdesc.eventDesces_.size());

View File

@ -189,6 +189,9 @@ void SubCommandStat::PrintPerHead()
void SubCommandStat::PrintPerValue(const std::unique_ptr<PerfEvents::ReportSum> &reportSum, const float &ratio,
std::string &configName)
{
if (reportSum == nullptr) {
return;
}
// print value
std::string strEventCount = std::to_string(reportSum->eventCountSum);
for (size_t i = strEventCount.size() - 1, j = 1; i > 0; --i, ++j) {
@ -219,6 +222,9 @@ void SubCommandStat::PrintPerValue(const std::unique_ptr<PerfEvents::ReportSum>
void SubCommandStat::InitPerMap(const std::unique_ptr<PerfEvents::ReportSum> &newPerMap,
const PerfEvents::Summary &summary, VirtualRuntime& virtualInstance)
{
if (newPerMap == nullptr) {
return;
}
newPerMap->cpu = summary.cpu;
if (g_reportCpuFlag && !g_reportThreadFlag) {
return;
@ -251,7 +257,7 @@ void SubCommandStat::ReportDetailInfos(
std::string perKey = "";
std::map<std::string, std::unique_ptr<PerfEvents::ReportSum>> perMaps;
for (auto event = countEvents.begin(); event != countEvents.end(); ++event) {
if (event->second->eventCount == 0) {
if (event->second == nullptr || event->second->eventCount == 0) {
continue;
}
constexpr float ratio {100.0};
@ -264,6 +270,9 @@ void SubCommandStat::ReportDetailInfos(
InitPerMap(perMap, it, runtimeInstance_);
perMaps[perKey] = std::move(perMap);
}
if (perMaps[perKey] == nullptr) {
continue;
}
perMaps[perKey]->configName = GetDetailComments(event->second, perMaps[perKey]->commentSum,
it, configName);
perMaps[perKey]->eventCountSum += it.eventCount;
@ -351,7 +360,7 @@ std::string SubCommandStat::GetCommentConfigName(
void SubCommandStat::MakeComments(const std::unique_ptr<PerfEvents::ReportSum> &reportSum, std::string &commentStr)
{
if (reportSum->commentSum == 0) {
if (reportSum == nullptr || reportSum->commentSum == 0) {
return;
}
if (reportSum->configName == "sw-task-clock") {

View File

@ -256,6 +256,10 @@ protected:
if (StringEndsWith(elfPath, ".hap")) {
filePath_ = elfPath + "!" + elfFile_->GetElfName();
HLOGD("update path for so in hap %s.", filePath_.c_str());
if (map == nullptr) {
HLOGW("map should not be nullptr.");
return false;
}
map->name = filePath_;
map->elf = elfFile_;
map->prevMap->name = filePath_;
@ -344,6 +348,9 @@ private:
bool LoadEhFrameHDR(const unsigned char *buffer, size_t bufferSize, uint64_t shdrOffset)
{
eh_frame_hdr *ehFrameHdr = (eh_frame_hdr *)buffer;
if (ehFrameHdr == nullptr) {
return false;
}
const uint8_t *dataPtr = ehFrameHdr->encode_data;
DwarfEncoding dwEhFramePtr(ehFrameHdr->eh_frame_ptr_enc, dataPtr);
DwarfEncoding dwFdeCount(ehFrameHdr->fde_count_enc, dataPtr);
@ -922,10 +929,6 @@ public:
HLOGD("the symbol file is %s.", filePath_.c_str());
if (StringEndsWith(filePath_, ".hap") || StringEndsWith(filePath_, ".hsp")) {
dfxExtractor_ = std::make_unique<DfxExtractor>(filePath_);
if (dfxExtractor_ == nullptr) {
HLOGD("DfxExtractor create failed.");
return false;
}
if (!dfxExtractor_->GetHapAbcInfo(loadOffSet_, abcDataPtr_, abcDataSize_)) {
HLOGD("failed to call GetHapAbcInfo, the symbol file is:%s", filePath_.c_str());
return false;
@ -1150,6 +1153,9 @@ void SymbolsFile::SortMatchedSymbols()
return;
}
sort(matchedSymbols_.begin(), matchedSymbols_.end(), [](const DfxSymbol* a, const DfxSymbol* b) {
if (a == nullptr || b == nullptr) {
return true;
}
return a->funcVaddr_ < b->funcVaddr_;
});
}
@ -1198,14 +1204,16 @@ const DfxSymbol SymbolsFile::GetSymbolWithVaddr(uint64_t vaddrInFile)
*/
if (found != symbols_.begin()) {
found = std::prev(found);
if (found->Contain(vaddrInFile)) {
found->offsetToVaddr_ = vaddrInFile - found->funcVaddr_;
if (!found->matched_) {
found->matched_ = true;
matchedSymbols_.push_back(&(*found));
if (found != symbols_.end()) {
if (found->Contain(vaddrInFile)) {
found->offsetToVaddr_ = vaddrInFile - found->funcVaddr_;
if (!found->matched_) {
found->matched_ = true;
matchedSymbols_.push_back(&(*found));
}
symbol = *found; // copy
HLOGV("found '%s' for vaddr 0x%016" PRIx64 "", symbol.ToString().c_str(), vaddrInFile);
}
symbol = *found; // copy
HLOGV("found '%s' for vaddr 0x%016" PRIx64 "", symbol.ToString().c_str(), vaddrInFile);
}
}

View File

@ -90,7 +90,9 @@ uint64_t UniqueStackTable::PutIpInSlot(uint64_t thisIp, uint64_t prevIdx)
node.section.inKernel = !!(thisIp & IP_IN_KERNEL);
while (currentDeconflictTimes_--) {
Node* tableNode = reinterpret_cast<Node *>(tableHead_) + curIpIdx;
if (tableNode == nullptr) {
continue;
}
// empty case
if (tableNode->value == 0) {
tableNode->value = node.value;
@ -133,7 +135,9 @@ uint64_t UniqueStackTable::PutIpsInTable(StackId *stackId, u64 *ips, u64 nr)
return 0;
}
}
if (stackId == nullptr) {
return 0;
}
stackId->section.id = prev;
stackId->section.nr = nr;
return prev;

View File

@ -279,7 +279,8 @@ std::string PlatformPathConvert(const std::string &path)
std::string ReadFileToString(const std::string &fileName)
{
std::ifstream inputString(fileName, std::ios::in);
std::string resolvedPath = CanonicalizeSpecPath(fileName.c_str());
std::ifstream inputString(resolvedPath, std::ios::in);
if (!inputString or !inputString.is_open()) {
return EMPTY_STRING;
}
@ -314,7 +315,8 @@ bool ReadFileToString(const std::string &fileName, std::string &fileData, size_t
bool WriteStringToFile(const std::string &fileName, const std::string &value)
{
std::ofstream output(fileName, std::ios::out);
std::string resolvedPath = CanonicalizeSpecPath(fileName.c_str());
std::ofstream output(resolvedPath, std::ios::out);
if (!output) {
return false;
}

View File

@ -185,6 +185,9 @@ VirtualThread &VirtualRuntime::CreateThread(pid_t pid, pid_t tid, const std::str
bool VirtualRuntime::UpdateHapSymbols(std::shared_ptr<DfxMap> map)
{
if (map == nullptr) {
return false;
}
// found it by name
auto symbolsFile = SymbolsFile::CreateSymbolsFile(map->name);
if (symbolsFile == nullptr) {
@ -354,12 +357,14 @@ void VirtualRuntime::UpdatekernelMap(uint64_t begin, uint64_t end, uint64_t offs
void VirtualRuntime::DedupFromRecord(PerfRecordSample *recordSample)
{
if (recordSample == nullptr) {
return;
}
u64 nr = recordSample->data_.nr;
if (nr == 0) {
collectSymbolCallBack_(recordSample);
return;
}
u32 pid = recordSample->data_.pid;
u64 *ips = recordSample->data_.ips;
StackId stackId;
@ -372,7 +377,9 @@ void VirtualRuntime::DedupFromRecord(PerfRecordSample *recordSample)
table = std::make_shared<UniqueStackTable>(pid);
processStackMap_[pid] = table;
}
if (table == nullptr) {
return;
}
while (table->PutIpsInTable(&stackId, ips, nr) == 0) {
// try expand hashtable if collison can not resolved
if (!table->Resize()) {
@ -381,7 +388,6 @@ void VirtualRuntime::DedupFromRecord(PerfRecordSample *recordSample)
return;
}
}
// callstack dedup success
recordSample->stackId_.value = stackId.value;
recordSample->header.size -= (sizeof(u64) * nr - sizeof(stackId));
@ -398,11 +404,17 @@ void VirtualRuntime::CollectDedupSymbol(kSymbolsHits &kernelSymbolsHits,
u32 pid;
for (const auto &tableEntry : processStackMap_) {
const auto &table = tableEntry.second;
if (table == nullptr) {
continue;
}
pid = table->GetPid();
head = table->GetHeadNode();
const auto &idxes = table->GetUsedIndexes();
for (const auto idx : idxes) {
node = head + idx;
if (node == nullptr) {
continue;
}
if (node->value != 0) {
if (node->section.inKernel) {
uint64_t ip = node->section.ip | KERNEL_PREFIX;
@ -492,7 +504,9 @@ bool VirtualRuntime::RecoverCallStack(PerfRecordSample &recordSample)
return false;
}
recordSample.ips_.clear();
StackTable->second->GetIpsByStackId(recordSample.stackId_, recordSample.ips_);
if (StackTable->second != nullptr) {
StackTable->second->GetIpsByStackId(recordSample.stackId_, recordSample.ips_);
}
recordSample.RecoverCallStack();
return true;
}
@ -795,7 +809,7 @@ void VirtualRuntime::UpdateSymbols(std::shared_ptr<DfxMap> map, pid_t pid)
HLOGD("try to find symbols for file: %s", map->name.c_str());
for (size_t i = 0; i < symbolsFiles_.size(); ++i) {
if (symbolsFiles_[i]->filePath_ == map->name) {
map->symbolFileIndex = i;
map->symbolFileIndex = static_cast<int32_t>(i);
HLOGV("already have '%s'", map->name.c_str());
return;
}
@ -904,6 +918,9 @@ const DfxSymbol VirtualRuntime::GetKernelThreadSymbol(uint64_t ip, const Virtual
}
auto map = thread.GetMaps()[mapIndex];
if (map == nullptr) {
return vaddrSymbol;
}
HLOGM("found addr 0x%" PRIx64 " in kthread map 0x%" PRIx64 " - 0x%" PRIx64 " from %s",
ip, map->begin, map->end, map->name.c_str());
// found symbols by file name
@ -1069,6 +1086,9 @@ DfxSymbol VirtualRuntime::GetSymbol(uint64_t ip, pid_t pid, pid_t tid, const per
bool VirtualRuntime::SetSymbolsPaths(const std::vector<std::string> &symbolsPaths)
{
std::unique_ptr<SymbolsFile> symbolsFile = SymbolsFile::CreateSymbolsFile(SYMBOL_UNKNOW_FILE);
if (symbolsFile == nullptr) {
return false;
}
// we need check if the path is accessible
bool accessible = symbolsFile->setSymbolsFilePath(symbolsPaths);
if (accessible) {
@ -1094,7 +1114,9 @@ void VirtualRuntime::UpdateFromPerfData(const std::vector<SymbolFileStruct> &sym
// load from symbolFileStruct (perf.data)
std::unique_ptr<SymbolsFile> symbolsFile = SymbolsFile::LoadSymbolsFromSaved(symbolFileStruct);
if (symbolsFile == nullptr) {
continue;
}
// reaload from sybol path If it exists
if (symbolsPaths_.size() > 0) {
HLOGV("try again with symbolsPaths setup");
@ -1247,11 +1269,17 @@ void VirtualRuntime::UpdateDevhostSymbols()
koMaps[symbol.module_] =
SymbolsFile::CreateSymbolsFile(SYMBOL_KERNEL_THREAD_FILE, filename);
}
if (koMaps[symbol.module_] == nullptr) {
continue;
}
koMaps[symbol.module_]->AddSymbol(std::move(symbol));
}
HLOGD("devhost loaded %zu symbolfiles", koMaps.size());
for (auto &it : koMaps) {
if (it.second == nullptr) {
continue;
}
HLOGD("Load %zu symbols to %s", it.second->GetSymbols().size(),
it.second->filePath_.c_str());
symbolsFiles_.emplace_back(std::move(it.second));

View File

@ -142,8 +142,8 @@ std::shared_ptr<DfxMap> VirtualThread::FindMapByFileInfo(const std::string name,
std::shared_ptr<DfxMap> VirtualThread::FindFirstMapByFileInfo(const std::string name) const
{
for (auto &map : memMaps_) {
if (name != map->name) {
for (const auto &map : memMaps_) {
if (map == nullptr || name != map->name) {
continue;
}
return map;
@ -154,6 +154,9 @@ std::shared_ptr<DfxMap> VirtualThread::FindFirstMapByFileInfo(const std::string
SymbolsFile *VirtualThread::FindSymbolsFileByMap(std::shared_ptr<DfxMap> map) const
{
if (map == nullptr) {
return nullptr;
}
if (map->symbolFileIndex != -1) {
// no need further operation
if (symbolsFiles_[map->symbolFileIndex]->LoadDebugInfo(map)) {
@ -166,7 +169,7 @@ SymbolsFile *VirtualThread::FindSymbolsFileByMap(std::shared_ptr<DfxMap> map) co
HLOGD("found symbol for map '%s'", map->name.c_str());
if (symbolsFiles_[i]->LoadDebugInfo(map)) {
HLOGD("found symbol for map '%s'", map->name.c_str());
map->symbolFileIndex = i;
map->symbolFileIndex = static_cast<int32_t>(i);
return symbolsFiles_[i].get();
}
}
@ -196,6 +199,9 @@ void VirtualThread::ReportVaddrMapMiss(uint64_t vaddr) const
missedRuntimeVaddr_.insert(vaddr);
HLOGV("vaddr %" PRIx64 " not found in any map", vaddr);
for (auto &map : memMaps_) {
if (map == nullptr) {
return;
}
HLOGV("map %s ", map->ToString().c_str());
}
}
@ -222,23 +228,25 @@ bool VirtualThread::ReadRoMemory(uint64_t vaddr, uint8_t *data, size_t size) con
}
if (memMapIndex != illegal) {
auto map = memMaps_[memMapIndex];
if (map->elf == nullptr) {
SymbolsFile* symFile = FindSymbolsFileByMap(map);
if (symFile == nullptr) {
return false;
if (map != nullptr) {
if (map->elf == nullptr) {
SymbolsFile* symFile = FindSymbolsFileByMap(map);
if (symFile == nullptr) {
return false;
}
map->elf = symFile->GetElfFile();
}
map->elf = symFile->GetElfFile();
}
if (map->elf != nullptr) {
// default base offset is zero
uint64_t foff = vaddr - map->begin + map->offset - map->elf->GetBaseOffset();
if (map->elf->Read(foff, data, size)) {
return true;
if (map->elf != nullptr) {
// default base offset is zero
uint64_t foff = vaddr - map->begin + map->offset - map->elf->GetBaseOffset();
if (map->elf->Read(foff, data, size)) {
return true;
} else {
return false;
}
} else {
return false;
HLOGW("find addr %" PRIx64 "in map but not loaded symbole %s", vaddr, map->name.c_str());
}
} else {
HLOGW("find addr %" PRIx64 "in map but not loaded symbole %s", vaddr, map->name.c_str());
}
} else {
#ifdef HIPERF_DEBUG

View File

@ -96,12 +96,12 @@ UnwindStep:unwind:12: ip 0x457ffe sp 0xb6ca1d28
UnwindStep:unwind:13: ip 0xb6f01f73 sp 0xb6ca1d38
*/
static const std::vector<frame> TEST_DWARF_FRAMES = {
{0x4575BC, 0xB6CA1C18}, // base ip sp
{0x45765e, 0xb6ca1c68}, {0x45768a, 0xb6ca1c78}, {0x4576ce, 0xb6ca1c88},
{0x457712, 0xb6ca1c98}, {0x457756, 0xb6ca1ca8}, {0x45779a, 0xb6ca1cb8},
{0x4577de, 0xb6ca1cc8}, {0x457822, 0xb6ca1cd8}, {0x457866, 0xb6ca1ce8},
{0x4578aa, 0xb6ca1cf8}, {0x4578ee, 0xb6ca1d08}, {0x45793c, 0xb6ca1d18},
{0x457ffe, 0xb6ca1d28}, {0xb6f01f73, 0xb6ca1d38},
{0x4575bc, 0xb6ca1c18}, // base ip sp
{0x45765f, 0xb6ca1c68}, {0x45768b, 0xb6ca1c78}, {0x4576cf, 0xb6ca1c88},
{0x457713, 0xb6ca1c98}, {0x457757, 0xb6ca1ca8}, {0x45779b, 0xb6ca1cb8},
{0x4577df, 0xb6ca1cc8}, {0x457823, 0xb6ca1cd8}, {0x457867, 0xb6ca1ce8},
{0x4578ab, 0xb6ca1cf8}, {0x4578ef, 0xb6ca1d08}, {0x45793d, 0xb6ca1d18},
{0x457fff, 0xb6ca1d28},
};
#else
static const std::string TEST_DWARF_ELF = "hiperf_example_cmd_64";
@ -151,7 +151,7 @@ static const std::vector<frame> TEST_DWARF_FRAMES = {
{0x5591ef7b10, 0x7f9aec7860}, {0x5591ef7bd0, 0x7f9aec78a0}, {0x5591ef7c90, 0x7f9aec78e0},
{0x5591ef7d50, 0x7f9aec7920}, {0x5591ef7e10, 0x7f9aec7960}, {0x5591ef7ed0, 0x7f9aec79a0},
{0x5591ef7f90, 0x7f9aec79e0}, {0x5591ef8050, 0x7f9aec7a20}, {0x5591ef80e8, 0x7f9aec7a60},
{0x5591ef95dc, 0x7f9aec7a80}, {0x7f9b0fa59c, 0x7f9aec7aa0},
{0x5591ef95dc, 0x7f9aec7a80},
};
#endif