forked from OSchip/llvm-project
Added the ability for Target::ReadMemory to prefer to read from the file
cache even when a valid process exists. Previously, Target::ReadMemory would read from the process if there was a valid one and then fallback to the object file cache. llvm-svn: 122989
This commit is contained in:
parent
1c926b78fe
commit
db59823068
|
@ -400,13 +400,28 @@ public:
|
|||
bool
|
||||
GetTargetTriple (ConstString &target_triple);
|
||||
|
||||
size_t
|
||||
ReadMemoryFromFileCache (const Address& addr,
|
||||
void *dst,
|
||||
size_t dst_len,
|
||||
Error &error);
|
||||
|
||||
// Reading memory through the target allows us to skip going to the process
|
||||
// for reading memory if possible and it allows us to try and read from
|
||||
// any constant sections in our object files on disk. If you always want
|
||||
// live program memory, read straight from the process. If you possibly
|
||||
// want to read from const sections in object files, read from the target.
|
||||
// This version of ReadMemory will try and read memory from the process
|
||||
// if the process is alive. The order is:
|
||||
// 1 - if (prefer_file_cache == true) then read from object file cache
|
||||
// 2 - if there is a valid process, try and read from its memory
|
||||
// 3 - if (prefer_file_cache == false) then read from object file cache
|
||||
size_t
|
||||
ReadMemory (const Address& addr,
|
||||
bool prefer_file_cache,
|
||||
void *dst,
|
||||
size_t dst_len,
|
||||
Error &error);
|
||||
|
||||
|
||||
|
||||
SectionLoadList&
|
||||
GetSectionLoadList()
|
||||
|
|
|
@ -68,7 +68,8 @@ ReadBytes (ExecutionContextScope *exe_scope, const Address &address, void *dst,
|
|||
if (target)
|
||||
{
|
||||
Error error;
|
||||
return target->ReadMemory (address, dst, dst_len, error);
|
||||
bool prefer_file_cache = false;
|
||||
return target->ReadMemory (address, prefer_file_cache, dst, dst_len, error);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -422,7 +422,8 @@ Disassembler::ParseInstructions
|
|||
DataBufferSP data_sp(heap_buffer);
|
||||
|
||||
Error error;
|
||||
const size_t bytes_read = target->ReadMemory (range.GetBaseAddress(), heap_buffer->GetBytes(), heap_buffer->GetByteSize(), error);
|
||||
bool prefer_file_cache = true;
|
||||
const size_t bytes_read = target->ReadMemory (range.GetBaseAddress(), prefer_file_cache, heap_buffer->GetBytes(), heap_buffer->GetByteSize(), error);
|
||||
|
||||
if (bytes_read > 0)
|
||||
{
|
||||
|
|
|
@ -470,7 +470,8 @@ read_byte_for_edis (uint8_t *buf, uint64_t offset_address, void *arg)
|
|||
|
||||
uint8_t onebyte_buf[1];
|
||||
Error error;
|
||||
if (target->ReadMemory (read_addr, onebyte_buf, 1, error) != -1)
|
||||
const bool prefer_file_cache = true;
|
||||
if (target->ReadMemory (read_addr, prefer_file_cache, onebyte_buf, 1, error) != -1)
|
||||
{
|
||||
*buf = onebyte_buf[0];
|
||||
return 0;
|
||||
|
@ -550,6 +551,7 @@ AssemblyParse_x86::get_non_call_site_unwind_plan (UnwindPlan &unwind_plan)
|
|||
row.SetRegisterInfo (m_lldb_ip_regnum, initial_regloc);
|
||||
|
||||
unwind_plan.AppendRow (row);
|
||||
const bool prefer_file_cache = true;
|
||||
|
||||
while (m_func_bounds.ContainsFileAddress (m_cur_insn) && non_prologue_insn_count < 10)
|
||||
{
|
||||
|
@ -562,7 +564,7 @@ AssemblyParse_x86::get_non_call_site_unwind_plan (UnwindPlan &unwind_plan)
|
|||
// An unrecognized/junk instruction
|
||||
break;
|
||||
}
|
||||
if (m_target.ReadMemory (m_cur_insn, m_cur_insn_bytes, insn_len, error) == -1)
|
||||
if (m_target.ReadMemory (m_cur_insn, prefer_file_cache, m_cur_insn_bytes, insn_len, error) == -1)
|
||||
{
|
||||
// Error reading the instruction out of the file, stop scanning
|
||||
break;
|
||||
|
@ -672,7 +674,7 @@ loopnext:
|
|||
Address last_insn (m_func_bounds.GetBaseAddress());
|
||||
last_insn.SetOffset (last_insn.GetOffset() + m_func_bounds.GetByteSize() - 1);
|
||||
uint8_t bytebuf[1];
|
||||
if (m_target.ReadMemory (last_insn, bytebuf, 1, error) != -1)
|
||||
if (m_target.ReadMemory (last_insn, prefer_file_cache, bytebuf, 1, error) != -1)
|
||||
{
|
||||
if (bytebuf[0] == 0xc3) // ret aka retq
|
||||
{
|
||||
|
@ -723,7 +725,8 @@ AssemblyParse_x86::get_fast_unwind_plan (AddressRange& func, UnwindPlan &unwind_
|
|||
|
||||
uint8_t bytebuf[4];
|
||||
Error error;
|
||||
if (m_target.ReadMemory (func.GetBaseAddress(), bytebuf, sizeof (bytebuf), error) == -1)
|
||||
const bool prefer_file_cache = true;
|
||||
if (m_target.ReadMemory (func.GetBaseAddress(), prefer_file_cache, bytebuf, sizeof (bytebuf), error) == -1)
|
||||
return false;
|
||||
|
||||
uint8_t i386_prologue[] = {0x55, 0x89, 0xe5};
|
||||
|
@ -781,6 +784,7 @@ AssemblyParse_x86::find_first_non_prologue_insn (Address &address)
|
|||
return false;
|
||||
}
|
||||
|
||||
const bool prefer_file_cache = true;
|
||||
while (m_func_bounds.ContainsFileAddress (m_cur_insn))
|
||||
{
|
||||
Error error;
|
||||
|
@ -790,7 +794,7 @@ AssemblyParse_x86::find_first_non_prologue_insn (Address &address)
|
|||
// An error parsing the instruction, i.e. probably data/garbage - stop scanning
|
||||
break;
|
||||
}
|
||||
if (m_target.ReadMemory (m_cur_insn, m_cur_insn_bytes, insn_len, error) == -1)
|
||||
if (m_target.ReadMemory (m_cur_insn, prefer_file_cache, m_cur_insn_bytes, insn_len, error) == -1)
|
||||
{
|
||||
// Error reading the instruction out of the file, stop scanning
|
||||
break;
|
||||
|
|
|
@ -589,12 +589,43 @@ Target::ModulesDidUnload (ModuleList &module_list)
|
|||
}
|
||||
|
||||
size_t
|
||||
Target::ReadMemory (const Address& addr, void *dst, size_t dst_len, Error &error)
|
||||
Target::ReadMemoryFromFileCache (const Address& addr, void *dst, size_t dst_len, Error &error)
|
||||
{
|
||||
const Section *section = addr.GetSection();
|
||||
if (section && section->GetModule())
|
||||
{
|
||||
ObjectFile *objfile = section->GetModule()->GetObjectFile();
|
||||
if (objfile)
|
||||
{
|
||||
size_t bytes_read = section->ReadSectionDataFromObjectFile (objfile,
|
||||
addr.GetOffset(),
|
||||
dst,
|
||||
dst_len);
|
||||
if (bytes_read > 0)
|
||||
return bytes_read;
|
||||
else
|
||||
error.SetErrorStringWithFormat("error reading data from section %s", section->GetName().GetCString());
|
||||
}
|
||||
else
|
||||
{
|
||||
error.SetErrorString("address isn't from a object file");
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
error.SetErrorString("address doesn't contain a section that points to a section in a object file");
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
size_t
|
||||
Target::ReadMemory (const Address& addr, bool prefer_file_cache, void *dst, size_t dst_len, Error &error)
|
||||
{
|
||||
error.Clear();
|
||||
|
||||
|
||||
bool process_is_valid = m_process_sp && m_process_sp->IsAlive();
|
||||
|
||||
size_t bytes_read = 0;
|
||||
Address resolved_addr(addr);
|
||||
if (!resolved_addr.IsSectionOffset())
|
||||
{
|
||||
|
@ -608,6 +639,12 @@ Target::ReadMemory (const Address& addr, void *dst, size_t dst_len, Error &error
|
|||
}
|
||||
}
|
||||
|
||||
if (prefer_file_cache)
|
||||
{
|
||||
bytes_read = ReadMemoryFromFileCache (resolved_addr, dst, dst_len, error);
|
||||
if (bytes_read > 0)
|
||||
return bytes_read;
|
||||
}
|
||||
|
||||
if (process_is_valid)
|
||||
{
|
||||
|
@ -623,7 +660,7 @@ Target::ReadMemory (const Address& addr, void *dst, size_t dst_len, Error &error
|
|||
}
|
||||
else
|
||||
{
|
||||
size_t bytes_read = m_process_sp->ReadMemory(load_addr, dst, dst_len, error);
|
||||
bytes_read = m_process_sp->ReadMemory(load_addr, dst, dst_len, error);
|
||||
if (bytes_read != dst_len)
|
||||
{
|
||||
if (error.Success())
|
||||
|
@ -646,14 +683,11 @@ Target::ReadMemory (const Address& addr, void *dst, size_t dst_len, Error &error
|
|||
}
|
||||
}
|
||||
|
||||
const Section *section = resolved_addr.GetSection();
|
||||
if (section && section->GetModule())
|
||||
if (!prefer_file_cache)
|
||||
{
|
||||
ObjectFile *objfile = section->GetModule()->GetObjectFile();
|
||||
return section->ReadSectionDataFromObjectFile (objfile,
|
||||
resolved_addr.GetOffset(),
|
||||
dst,
|
||||
dst_len);
|
||||
// If we didn't already try and read from the object file cache, then
|
||||
// try it after failing to read from the process.
|
||||
return ReadMemoryFromFileCache (resolved_addr, dst, dst_len, error);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue