summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--lldb/tools/debugserver/source/DNB.cpp8
-rw-r--r--lldb/tools/debugserver/source/DNB.h4
-rw-r--r--lldb/tools/debugserver/source/DNBDefs.h17
-rw-r--r--lldb/tools/debugserver/source/MacOSX/MachProcess.cpp5
-rw-r--r--lldb/tools/debugserver/source/MacOSX/MachProcess.h6
-rw-r--r--lldb/tools/debugserver/source/MacOSX/MachTask.cpp177
-rw-r--r--lldb/tools/debugserver/source/MacOSX/MachTask.h3
-rw-r--r--lldb/tools/debugserver/source/MacOSX/MachVMMemory.cpp32
-rw-r--r--lldb/tools/debugserver/source/MacOSX/MachVMMemory.h2
-rw-r--r--lldb/tools/debugserver/source/RNBRemote.cpp42
10 files changed, 196 insertions, 100 deletions
diff --git a/lldb/tools/debugserver/source/DNB.cpp b/lldb/tools/debugserver/source/DNB.cpp
index 36508e986e7..ed19b097327 100644
--- a/lldb/tools/debugserver/source/DNB.cpp
+++ b/lldb/tools/debugserver/source/DNB.cpp
@@ -1220,22 +1220,22 @@ DNBProcessMemoryRegionInfo (nub_process_t pid, nub_addr_t addr, DNBRegionInfo *r
}
std::string
-DNBProcessGetProfileData (nub_process_t pid)
+DNBProcessGetProfileData (nub_process_t pid, DNBProfileDataScanType scanType)
{
MachProcessSP procSP;
if (GetProcessSP (pid, procSP))
- return procSP->Task().GetProfileData();
+ return procSP->Task().GetProfileData(scanType);
return std::string("");
}
nub_bool_t
-DNBProcessSetEnableAsyncProfiling (nub_process_t pid, nub_bool_t enable, uint64_t interval_usec)
+DNBProcessSetEnableAsyncProfiling (nub_process_t pid, nub_bool_t enable, uint64_t interval_usec, DNBProfileDataScanType scan_type)
{
MachProcessSP procSP;
if (GetProcessSP (pid, procSP))
{
- procSP->SetEnableAsyncProfiling(enable, interval_usec);
+ procSP->SetEnableAsyncProfiling(enable, interval_usec, scan_type);
return true;
}
diff --git a/lldb/tools/debugserver/source/DNB.h b/lldb/tools/debugserver/source/DNB.h
index 2e14387cbcc..83366dbf999 100644
--- a/lldb/tools/debugserver/source/DNB.h
+++ b/lldb/tools/debugserver/source/DNB.h
@@ -63,8 +63,8 @@ nub_size_t DNBProcessMemoryWrite (nub_process_t pid, nub_addr_t addr, nub
nub_addr_t DNBProcessMemoryAllocate (nub_process_t pid, nub_size_t size, uint32_t permissions) DNB_EXPORT;
nub_bool_t DNBProcessMemoryDeallocate (nub_process_t pid, nub_addr_t addr) DNB_EXPORT;
int DNBProcessMemoryRegionInfo (nub_process_t pid, nub_addr_t addr, DNBRegionInfo *region_info) DNB_EXPORT;
-std::string DNBProcessGetProfileData (nub_process_t pid) DNB_EXPORT;
-nub_bool_t DNBProcessSetEnableAsyncProfiling (nub_process_t pid, nub_bool_t enable, uint64_t interval_usec) DNB_EXPORT;
+std::string DNBProcessGetProfileData (nub_process_t pid, DNBProfileDataScanType scanType) DNB_EXPORT;
+nub_bool_t DNBProcessSetEnableAsyncProfiling (nub_process_t pid, nub_bool_t enable, uint64_t interval_usec, DNBProfileDataScanType scan_type) DNB_EXPORT;
//----------------------------------------------------------------------
// Process status
diff --git a/lldb/tools/debugserver/source/DNBDefs.h b/lldb/tools/debugserver/source/DNBDefs.h
index 47a2a866964..de8b99a2f04 100644
--- a/lldb/tools/debugserver/source/DNBDefs.h
+++ b/lldb/tools/debugserver/source/DNBDefs.h
@@ -358,6 +358,23 @@ struct DNBRegionInfo
uint32_t permissions;
};
+enum DNBProfileDataScanType
+{
+ eProfileHostCPU = (1 << 0),
+ eProfileCPU = (1 << 1),
+
+ eProfileThreadsCPU = (1 << 2), // By default excludes eProfileThreadName and eProfileQueueName.
+ eProfileThreadName = (1 << 3), // Assume eProfileThreadsCPU, get thread name as well.
+ eProfileQueueName = (1 << 4), // Assume eProfileThreadsCPU, get queue name as well.
+
+ eProfileHostMemory = (1 << 5),
+
+ eProfileMemory = (1 << 6), // By default, excludes eProfileMemoryDirtyPage.
+ eProfileMemoryDirtyPage = (1 << 7), // Assume eProfileMemory, get Dirty Page size as well.
+
+ eProfileAll = 0xffffffff
+};
+
typedef nub_bool_t (*DNBCallbackBreakpointHit)(nub_process_t pid, nub_thread_t tid, nub_break_t breakID, void *baton);
typedef nub_addr_t (*DNBCallbackNameToAddress)(nub_process_t pid, const char *name, const char *shlib_regex, void *baton);
typedef nub_size_t (*DNBCallbackCopyExecutableImageInfos)(nub_process_t pid, struct DNBExecutableImageInfo **image_infos, nub_bool_t only_changed, void *baton);
diff --git a/lldb/tools/debugserver/source/MacOSX/MachProcess.cpp b/lldb/tools/debugserver/source/MacOSX/MachProcess.cpp
index 33847ebec85..0f7250a8b8f 100644
--- a/lldb/tools/debugserver/source/MacOSX/MachProcess.cpp
+++ b/lldb/tools/debugserver/source/MacOSX/MachProcess.cpp
@@ -315,10 +315,11 @@ MachProcess::StartSTDIOThread()
}
void
-MachProcess::SetEnableAsyncProfiling(bool enable, uint64_t interval_usec)
+MachProcess::SetEnableAsyncProfiling(bool enable, uint64_t interval_usec, DNBProfileDataScanType scan_type)
{
m_profile_enabled = enable;
m_profile_interval_usec = interval_usec;
+ m_profile_scan_type = scan_type;
if (m_profile_enabled && (m_profile_thread == NULL))
{
@@ -1411,7 +1412,7 @@ MachProcess::ProfileThread(void *arg)
nub_state_t state = proc->GetState();
if (state == eStateRunning)
{
- std::string data = proc->Task().GetProfileData();
+ std::string data = proc->Task().GetProfileData(proc->GetProfileScanType());
if (!data.empty())
{
proc->SignalAsyncProfileData(data.c_str());
diff --git a/lldb/tools/debugserver/source/MacOSX/MachProcess.h b/lldb/tools/debugserver/source/MacOSX/MachProcess.h
index f4529364909..542c3dbc93a 100644
--- a/lldb/tools/debugserver/source/MacOSX/MachProcess.h
+++ b/lldb/tools/debugserver/source/MacOSX/MachProcess.h
@@ -148,7 +148,7 @@ public:
//----------------------------------------------------------------------
// Profile functions
//----------------------------------------------------------------------
- void SetEnableAsyncProfiling (bool enable, uint64_t internal_usec);
+ void SetEnableAsyncProfiling (bool enable, uint64_t internal_usec, DNBProfileDataScanType scan_type);
bool IsProfilingEnabled () { return m_profile_enabled; }
uint64_t ProfileInterval () { return m_profile_interval_usec; }
bool StartProfileThread ();
@@ -250,6 +250,9 @@ public:
}
bool ProcessUsingSpringBoard() const { return (m_flags & eMachProcessFlagsUsingSBS) != 0; }
+
+ DNBProfileDataScanType GetProfileScanType () { return m_profile_scan_type; }
+
private:
enum
{
@@ -282,6 +285,7 @@ private:
bool m_profile_enabled; // A flag to indicate if profiling is enabled
uint64_t m_profile_interval_usec; // If enable, the profiling interval in microseconds
+ DNBProfileDataScanType m_profile_scan_type; // Indicates what needs to be profiled
pthread_t m_profile_thread; // Thread ID for the thread that profiles the inferior
PThreadMutex m_profile_data_mutex; // Multithreaded protection for profile info data
std::vector<std::string> m_profile_data; // Profile data, must be protected by m_profile_data_mutex
diff --git a/lldb/tools/debugserver/source/MacOSX/MachTask.cpp b/lldb/tools/debugserver/source/MacOSX/MachTask.cpp
index 785f1e74b92..21c10dde077 100644
--- a/lldb/tools/debugserver/source/MacOSX/MachTask.cpp
+++ b/lldb/tools/debugserver/source/MacOSX/MachTask.cpp
@@ -233,7 +233,7 @@ MachTask::GetMemoryRegionInfo (nub_addr_t addr, DNBRegionInfo *region_info)
} while (0)
// We should consider moving this into each MacThread.
-static void get_threads_profile_data(task_t task, nub_process_t pid, std::vector<uint64_t> &threads_id, std::vector<std::string> &threads_name, std::vector<uint64_t> &threads_used_usec)
+static void get_threads_profile_data(DNBProfileDataScanType scanType, task_t task, nub_process_t pid, std::vector<uint64_t> &threads_id, std::vector<std::string> &threads_name, std::vector<uint64_t> &threads_used_usec)
{
kern_return_t kr;
thread_act_array_t threads;
@@ -243,7 +243,8 @@ static void get_threads_profile_data(task_t task, nub_process_t pid, std::vector
if (kr != KERN_SUCCESS)
return;
- for (int i = 0; i < tcnt; i++) {
+ for (int i = 0; i < tcnt; i++)
+ {
thread_identifier_info_data_t identifier_info;
mach_msg_type_number_t count = THREAD_IDENTIFIER_INFO_COUNT;
kr = ::thread_info(threads[i], THREAD_IDENTIFIER_INFO, (thread_info_t)&identifier_info, &count);
@@ -254,22 +255,26 @@ static void get_threads_profile_data(task_t task, nub_process_t pid, std::vector
kr = ::thread_info(threads[i], THREAD_BASIC_INFO, (thread_info_t)&basic_info, &count);
if (kr != KERN_SUCCESS) continue;
- if ((basic_info.flags & TH_FLAGS_IDLE) == 0) {
+ if ((basic_info.flags & TH_FLAGS_IDLE) == 0)
+ {
nub_thread_t tid = MachThread::GetGloballyUniqueThreadIDForMachPortID (threads[i]);
-
threads_id.push_back(tid);
- if (identifier_info.thread_handle != 0) {
+ if ((scanType & eProfileThreadName) && (identifier_info.thread_handle != 0))
+ {
struct proc_threadinfo proc_threadinfo;
int len = ::proc_pidinfo(pid, PROC_PIDTHREADINFO, identifier_info.thread_handle, &proc_threadinfo, PROC_PIDTHREADINFO_SIZE);
- if (len && proc_threadinfo.pth_name[0]) {
+ if (len && proc_threadinfo.pth_name[0])
+ {
threads_name.push_back(proc_threadinfo.pth_name);
}
- else {
+ else
+ {
threads_name.push_back("");
}
}
- else {
+ else
+ {
threads_name.push_back("");
}
struct timeval tv;
@@ -289,26 +294,29 @@ static void get_threads_profile_data(task_t task, nub_process_t pid, std::vector
#define RAW_HEXBASE std::setfill('0') << std::hex << std::right
#define DECIMAL std::dec << std::setfill(' ')
std::string
-MachTask::GetProfileData ()
+MachTask::GetProfileData (DNBProfileDataScanType scanType)
{
std::string result;
static int32_t numCPU = -1;
- int32_t mib[] = {CTL_HW, HW_AVAILCPU};
- size_t len = sizeof(numCPU);
- if (numCPU == -1)
+ struct host_cpu_load_info host_info;
+ if (scanType & eProfileHostCPU)
{
- if (sysctl(mib, sizeof(mib) / sizeof(int32_t), &numCPU, &len, NULL, 0) != 0)
+ int32_t mib[] = {CTL_HW, HW_AVAILCPU};
+ size_t len = sizeof(numCPU);
+ if (numCPU == -1)
+ {
+ if (sysctl(mib, sizeof(mib) / sizeof(int32_t), &numCPU, &len, NULL, 0) != 0)
+ return result;
+ }
+
+ mach_port_t localHost = mach_host_self();
+ mach_msg_type_number_t count = HOST_CPU_LOAD_INFO_COUNT;
+ kern_return_t kr = host_statistics(localHost, HOST_CPU_LOAD_INFO, (host_info_t)&host_info, &count);
+ if (kr != KERN_SUCCESS)
return result;
}
- mach_port_t localHost = mach_host_self();
- struct host_cpu_load_info host_info;
- mach_msg_type_number_t count = HOST_CPU_LOAD_INFO_COUNT;
- kern_return_t kr = host_statistics(localHost, HOST_CPU_LOAD_INFO, (host_info_t)&host_info, &count);
- if (kr != KERN_SUCCESS)
- return result;
-
task_t task = TaskPort();
if (task == TASK_NULL)
return result;
@@ -322,24 +330,31 @@ MachTask::GetProfileData ()
uint64_t elapsed_usec = 0;
uint64_t task_used_usec = 0;
+ if (scanType & eProfileCPU)
+ {
+ // Get current used time.
+ struct timeval current_used_time;
+ struct timeval tv;
+ TIME_VALUE_TO_TIMEVAL(&task_info.user_time, &current_used_time);
+ TIME_VALUE_TO_TIMEVAL(&task_info.system_time, &tv);
+ timeradd(&current_used_time, &tv, &current_used_time);
+ task_used_usec = current_used_time.tv_sec * 1000000ULL + current_used_time.tv_usec;
+
+ struct timeval current_elapsed_time;
+ int res = gettimeofday(&current_elapsed_time, NULL);
+ if (res == 0)
+ {
+ elapsed_usec = current_elapsed_time.tv_sec * 1000000ULL + current_elapsed_time.tv_usec;
+ }
+ }
+
std::vector<uint64_t> threads_id;
std::vector<std::string> threads_name;
std::vector<uint64_t> threads_used_usec;
-
- // Get current used time.
- struct timeval current_used_time;
- struct timeval tv;
- TIME_VALUE_TO_TIMEVAL(&task_info.user_time, &current_used_time);
- TIME_VALUE_TO_TIMEVAL(&task_info.system_time, &tv);
- timeradd(&current_used_time, &tv, &current_used_time);
- task_used_usec = current_used_time.tv_sec * 1000000ULL + current_used_time.tv_usec;
- get_threads_profile_data(task, m_process->ProcessID(), threads_id, threads_name, threads_used_usec);
-
- struct timeval current_elapsed_time;
- int res = gettimeofday(&current_elapsed_time, NULL);
- if (res == 0)
+
+ if (scanType & eProfileThreadsCPU)
{
- elapsed_usec = current_elapsed_time.tv_sec * 1000000ULL + current_elapsed_time.tv_usec;
+ get_threads_profile_data(scanType, task, m_process->ProcessID(), threads_id, threads_name, threads_used_usec);
}
struct vm_statistics vm_stats;
@@ -349,53 +364,75 @@ MachTask::GetProfileData ()
mach_vm_size_t vprvt = 0;
mach_vm_size_t vsize = 0;
mach_vm_size_t dirty_size = 0;
- if (m_vm_memory.GetMemoryProfile(task, task_info, m_process->GetCPUType(), m_process->ProcessID(), vm_stats, physical_memory, rprvt, rsize, vprvt, vsize, dirty_size))
+ if (m_vm_memory.GetMemoryProfile(scanType, task, task_info, m_process->GetCPUType(), m_process->ProcessID(), vm_stats, physical_memory, rprvt, rsize, vprvt, vsize, dirty_size))
{
std::ostringstream profile_data_stream;
- profile_data_stream << "num_cpu:" << numCPU << ';';
- profile_data_stream << "host_user_ticks:" << host_info.cpu_ticks[CPU_STATE_USER] << ';';
- profile_data_stream << "host_sys_ticks:" << host_info.cpu_ticks[CPU_STATE_SYSTEM] << ';';
- profile_data_stream << "host_idle_ticks:" << host_info.cpu_ticks[CPU_STATE_IDLE] << ';';
+ if (scanType & eProfileHostCPU)
+ {
+ profile_data_stream << "num_cpu:" << numCPU << ';';
+ profile_data_stream << "host_user_ticks:" << host_info.cpu_ticks[CPU_STATE_USER] << ';';
+ profile_data_stream << "host_sys_ticks:" << host_info.cpu_ticks[CPU_STATE_SYSTEM] << ';';
+ profile_data_stream << "host_idle_ticks:" << host_info.cpu_ticks[CPU_STATE_IDLE] << ';';
+ }
- profile_data_stream << "elapsed_usec:" << elapsed_usec << ';';
- profile_data_stream << "task_used_usec:" << task_used_usec << ';';
+ if (scanType & eProfileCPU)
+ {
+ profile_data_stream << "elapsed_usec:" << elapsed_usec << ';';
+ profile_data_stream << "task_used_usec:" << task_used_usec << ';';
+ }
- int num_threads = threads_id.size();
- for (int i=0; i<num_threads; i++) {
- profile_data_stream << "thread_used_id:" << std::hex << threads_id[i] << std::dec << ';';
- profile_data_stream << "thread_used_usec:" << threads_used_usec[i] << ';';
-
- profile_data_stream << "thread_used_name:";
- int len = threads_name[i].size();
- if (len) {
- const char *thread_name = threads_name[i].c_str();
- // Make sure that thread name doesn't interfere with our delimiter.
- profile_data_stream << RAW_HEXBASE << std::setw(2);
- const uint8_t *ubuf8 = (const uint8_t *)(thread_name);
- for (int j=0; j<len; j++)
+ if (scanType & eProfileThreadsCPU)
+ {
+ int num_threads = threads_id.size();
+ for (int i=0; i<num_threads; i++)
+ {
+ profile_data_stream << "thread_used_id:" << std::hex << threads_id[i] << std::dec << ';';
+ profile_data_stream << "thread_used_usec:" << threads_used_usec[i] << ';';
+
+ if (scanType & eProfileThreadName)
{
- profile_data_stream << (uint32_t)(ubuf8[j]);
+ profile_data_stream << "thread_used_name:";
+ int len = threads_name[i].size();
+ if (len)
+ {
+ const char *thread_name = threads_name[i].c_str();
+ // Make sure that thread name doesn't interfere with our delimiter.
+ profile_data_stream << RAW_HEXBASE << std::setw(2);
+ const uint8_t *ubuf8 = (const uint8_t *)(thread_name);
+ for (int j=0; j<len; j++)
+ {
+ profile_data_stream << (uint32_t)(ubuf8[j]);
+ }
+ // Reset back to DECIMAL.
+ profile_data_stream << DECIMAL;
+ }
+ profile_data_stream << ';';
}
- // Reset back to DECIMAL.
- profile_data_stream << DECIMAL;
}
- profile_data_stream << ';';
}
- profile_data_stream << "wired:" << vm_stats.wire_count * vm_page_size << ';';
- profile_data_stream << "active:" << vm_stats.active_count * vm_page_size << ';';
- profile_data_stream << "inactive:" << vm_stats.inactive_count * vm_page_size << ';';
- uint64_t total_used_count = vm_stats.wire_count + vm_stats.inactive_count + vm_stats.active_count;
- profile_data_stream << "used:" << total_used_count * vm_page_size << ';';
- profile_data_stream << "free:" << vm_stats.free_count * vm_page_size << ';';
- profile_data_stream << "total:" << physical_memory << ';';
+ if (scanType & eProfileHostMemory)
+ profile_data_stream << "total:" << physical_memory << ';';
+
+ if (scanType & eProfileMemory)
+ {
+ profile_data_stream << "wired:" << vm_stats.wire_count * vm_page_size << ';';
+ profile_data_stream << "active:" << vm_stats.active_count * vm_page_size << ';';
+ profile_data_stream << "inactive:" << vm_stats.inactive_count * vm_page_size << ';';
+ uint64_t total_used_count = vm_stats.wire_count + vm_stats.inactive_count + vm_stats.active_count;
+ profile_data_stream << "used:" << total_used_count * vm_page_size << ';';
+ profile_data_stream << "free:" << vm_stats.free_count * vm_page_size << ';';
+
+ profile_data_stream << "rprvt:" << rprvt << ';';
+ profile_data_stream << "rsize:" << rsize << ';';
+ profile_data_stream << "vprvt:" << vprvt << ';';
+ profile_data_stream << "vsize:" << vsize << ';';
+
+ if (scanType & eProfileMemoryDirtyPage)
+ profile_data_stream << "dirty:" << dirty_size << ';';
+ }
- profile_data_stream << "rprvt:" << rprvt << ';';
- profile_data_stream << "rsize:" << rsize << ';';
- profile_data_stream << "vprvt:" << vprvt << ';';
- profile_data_stream << "vsize:" << vsize << ';';
- profile_data_stream << "dirty:" << dirty_size << ';';
profile_data_stream << "--end--;";
result = profile_data_stream.str();
diff --git a/lldb/tools/debugserver/source/MacOSX/MachTask.h b/lldb/tools/debugserver/source/MacOSX/MachTask.h
index 52169715407..f3fb6fb80f0 100644
--- a/lldb/tools/debugserver/source/MacOSX/MachTask.h
+++ b/lldb/tools/debugserver/source/MacOSX/MachTask.h
@@ -26,6 +26,7 @@
#include <string>
// Other libraries and framework includes
// Project includes
+#include "DNBDefs.h"
#include "MachException.h"
#include "MachVMMemory.h"
#include "PThreadMutex.h"
@@ -66,7 +67,7 @@ public:
nub_size_t ReadMemory (nub_addr_t addr, nub_size_t size, void *buf);
nub_size_t WriteMemory (nub_addr_t addr, nub_size_t size, const void *buf);
int GetMemoryRegionInfo (nub_addr_t addr, DNBRegionInfo *region_info);
- std::string GetProfileData ();
+ std::string GetProfileData (DNBProfileDataScanType scanType);
nub_addr_t AllocateMemory (nub_size_t size, uint32_t permissions);
nub_bool_t DeallocateMemory (nub_addr_t addr);
diff --git a/lldb/tools/debugserver/source/MacOSX/MachVMMemory.cpp b/lldb/tools/debugserver/source/MacOSX/MachVMMemory.cpp
index d13cbfe0131..c0ce9c6ec93 100644
--- a/lldb/tools/debugserver/source/MacOSX/MachVMMemory.cpp
+++ b/lldb/tools/debugserver/source/MacOSX/MachVMMemory.cpp
@@ -397,21 +397,29 @@ static void GetMemorySizes(task_t task, cpu_type_t cputype, nub_process_t pid, m
}
nub_bool_t
-MachVMMemory::GetMemoryProfile(task_t task, struct task_basic_info ti, cpu_type_t cputype, nub_process_t pid, vm_statistics_data_t &vm_stats, uint64_t &physical_memory, mach_vm_size_t &rprvt, mach_vm_size_t &rsize, mach_vm_size_t &vprvt, mach_vm_size_t &vsize, mach_vm_size_t &dirty_size)
+MachVMMemory::GetMemoryProfile(DNBProfileDataScanType scanType, task_t task, struct task_basic_info ti, cpu_type_t cputype, nub_process_t pid, vm_statistics_data_t &vm_stats, uint64_t &physical_memory, mach_vm_size_t &rprvt, mach_vm_size_t &rsize, mach_vm_size_t &vprvt, mach_vm_size_t &vsize, mach_vm_size_t &dirty_size)
{
- static mach_port_t localHost = mach_host_self();
- mach_msg_type_number_t count = HOST_VM_INFO_COUNT;
- host_statistics(localHost, HOST_VM_INFO, (host_info_t)&vm_stats, &count);
- vm_stats.wire_count += GetStolenPages();
- physical_memory = GetPhysicalMemory();
-
- // This uses vmmap strategy. We don't use the returned rsize for now. We prefer to match top's version since that's what we do for the rest of the metrics.
- GetRegionSizes(task, rsize, dirty_size);
+ if (scanType & eProfileHostMemory)
+ physical_memory = GetPhysicalMemory();
- GetMemorySizes(task, cputype, pid, rprvt, vprvt);
+ if (scanType & eProfileMemory)
+ {
+ static mach_port_t localHost = mach_host_self();
+ mach_msg_type_number_t count = HOST_VM_INFO_COUNT;
+ host_statistics(localHost, HOST_VM_INFO, (host_info_t)&vm_stats, &count);
+ vm_stats.wire_count += GetStolenPages();
+
+ GetMemorySizes(task, cputype, pid, rprvt, vprvt);
+
+ rsize = ti.resident_size;
+ vsize = ti.virtual_size;
+ }
- rsize = ti.resident_size;
- vsize = ti.virtual_size;
+ if (scanType & eProfileMemoryDirtyPage)
+ {
+ // This uses vmmap strategy. We don't use the returned rsize for now. We prefer to match top's version since that's what we do for the rest of the metrics.
+ GetRegionSizes(task, rsize, dirty_size);
+ }
return true;
}
diff --git a/lldb/tools/debugserver/source/MacOSX/MachVMMemory.h b/lldb/tools/debugserver/source/MacOSX/MachVMMemory.h
index 2a8f3d13c84..0b782365d08 100644
--- a/lldb/tools/debugserver/source/MacOSX/MachVMMemory.h
+++ b/lldb/tools/debugserver/source/MacOSX/MachVMMemory.h
@@ -28,7 +28,7 @@ public:
nub_size_t Write(task_t task, nub_addr_t address, const void *data, nub_size_t data_count);
nub_size_t PageSize();
nub_bool_t GetMemoryRegionInfo(task_t task, nub_addr_t address, DNBRegionInfo *region_info);
- nub_bool_t GetMemoryProfile(task_t task, struct task_basic_info ti, cpu_type_t cputype, nub_process_t pid, vm_statistics_data_t &vm_stats, uint64_t &physical_memory, mach_vm_size_t &rprvt, mach_vm_size_t &rsize, mach_vm_size_t &vprvt, mach_vm_size_t &vsize, mach_vm_size_t &dirty_size);
+ nub_bool_t GetMemoryProfile(DNBProfileDataScanType scanType, task_t task, struct task_basic_info ti, cpu_type_t cputype, nub_process_t pid, vm_statistics_data_t &vm_stats, uint64_t &physical_memory, mach_vm_size_t &rprvt, mach_vm_size_t &rsize, mach_vm_size_t &vprvt, mach_vm_size_t &vsize, mach_vm_size_t &dirty_size);
protected:
nub_size_t MaxBytesLeftInPage(nub_addr_t addr, nub_size_t count);
diff --git a/lldb/tools/debugserver/source/RNBRemote.cpp b/lldb/tools/debugserver/source/RNBRemote.cpp
index 5177c0e7299..f3612e866c6 100644
--- a/lldb/tools/debugserver/source/RNBRemote.cpp
+++ b/lldb/tools/debugserver/source/RNBRemote.cpp
@@ -3645,14 +3645,32 @@ RNBRemote::HandlePacket_MemoryRegionInfo (const char *p)
return SendPacket (ostrm.str());
}
+// qGetProfileData;scan_type:0xYYYYYYY
rnb_err_t
RNBRemote::HandlePacket_GetProfileData (const char *p)
{
nub_process_t pid = m_ctx.ProcessID();
if (pid == INVALID_NUB_PROCESS)
return SendPacket ("OK");
-
- std::string data = DNBProcessGetProfileData(pid);
+
+ StringExtractor packet(p += sizeof ("qGetProfileData"));
+ DNBProfileDataScanType scan_type = eProfileAll;
+ std::string name;
+ std::string value;
+ while (packet.GetNameColonValue(name, value))
+ {
+ if (name.compare ("scan_type") == 0)
+ {
+ std::istringstream iss(value);
+ uint32_t int_value = 0;
+ if (iss >> std::hex >> int_value)
+ {
+ scan_type = (DNBProfileDataScanType)int_value;
+ }
+ }
+ }
+
+ std::string data = DNBProcessGetProfileData(pid, scan_type);
if (!data.empty())
{
return SendPacket (data.c_str());
@@ -3663,18 +3681,18 @@ RNBRemote::HandlePacket_GetProfileData (const char *p)
}
}
-
-// QSetEnableAsyncProfiling;enable:[0|1]:interval_usec:XXXXXX;
+// QSetEnableAsyncProfiling;enable:[0|1]:interval_usec:XXXXXX;scan_type:0xYYYYYYY
rnb_err_t
RNBRemote::HandlePacket_SetEnableAsyncProfiling (const char *p)
{
nub_process_t pid = m_ctx.ProcessID();
if (pid == INVALID_NUB_PROCESS)
- return SendPacket ("");
+ return SendPacket ("OK");
- StringExtractor packet(p += sizeof ("QSetEnableAsyncProfiling:") - 1);
+ StringExtractor packet(p += sizeof ("QSetEnableAsyncProfiling"));
bool enable = false;
uint64_t interval_usec = 0;
+ DNBProfileDataScanType scan_type = eProfileAll;
std::string name;
std::string value;
while (packet.GetNameColonValue(name, value))
@@ -3687,13 +3705,23 @@ RNBRemote::HandlePacket_SetEnableAsyncProfiling (const char *p)
{
interval_usec = strtoul(value.c_str(), NULL, 10);
}
+ else if (name.compare ("scan_type") == 0)
+ {
+ std::istringstream iss(value);
+ uint32_t int_value = 0;
+ if (iss >> std::hex >> int_value)
+ {
+ scan_type = (DNBProfileDataScanType)int_value;
+ }
+ }
}
if (interval_usec == 0)
{
enable = 0;
}
- DNBProcessSetEnableAsyncProfiling(pid, enable, interval_usec);
+
+ DNBProcessSetEnableAsyncProfiling(pid, enable, interval_usec, scan_type);
return SendPacket ("OK");
}
OpenPOWER on IntegriCloud