1
Fork 0
mirror of https://github.com/RGBCube/serenity synced 2025-07-25 21:07:35 +00:00

UserspaceEmulator: Support dynamically loaded programs

When loading dynamic objects, the emulator loads the interpreter,
generates an auxiliary vector and starts executing the loader.

Additionally, this commits also makes the MallocTracer and backtrace
symbolication work for dynamically loaded programs.
This commit is contained in:
Itamar 2020-11-23 20:00:35 +02:00 committed by Andreas Kling
parent 28cda567c1
commit 72ca45e300
9 changed files with 247 additions and 64 deletions

View file

@ -58,6 +58,8 @@ inline void MallocTracer::for_each_mallocation(Callback callback) const
void MallocTracer::target_did_malloc(Badge<SoftCPU>, FlatPtr address, size_t size)
{
if (m_emulator.is_in_loader_code())
return;
auto* region = m_emulator.mmu().find_region({ 0x20, address });
ASSERT(region);
ASSERT(region->is_mmap());
@ -109,6 +111,7 @@ ALWAYS_INLINE size_t MallocRegionMetadata::chunk_index_for_address(FlatPtr addre
return 0;
}
auto chunk_offset = address - (this->address + sizeof(ChunkedBlock));
ASSERT(this->chunk_size);
return chunk_offset / this->chunk_size;
}
@ -116,6 +119,8 @@ void MallocTracer::target_did_free(Badge<SoftCPU>, FlatPtr address)
{
if (!address)
return;
if (m_emulator.is_in_loader_code())
return;
if (auto* mallocation = find_mallocation(address)) {
if (mallocation->freed) {
@ -136,6 +141,8 @@ void MallocTracer::target_did_free(Badge<SoftCPU>, FlatPtr address)
void MallocTracer::target_did_realloc(Badge<SoftCPU>, FlatPtr address, size_t size)
{
if (m_emulator.is_in_loader_code())
return;
auto* region = m_emulator.mmu().find_region({ 0x20, address });
ASSERT(region);
ASSERT(region->is_mmap());
@ -201,8 +208,13 @@ void MallocTracer::audit_read(const Region& region, FlatPtr address, size_t size
if (!m_auditing_enabled)
return;
if (m_emulator.is_in_malloc_or_free())
if (m_emulator.is_in_malloc_or_free()) {
return;
}
if (m_emulator.is_in_loader_code()) {
return;
}
auto* mallocation = find_mallocation(region, address);
@ -246,6 +258,10 @@ void MallocTracer::audit_write(const Region& region, FlatPtr address, size_t siz
if (m_emulator.is_in_malloc_or_free())
return;
if (m_emulator.is_in_loader_code()) {
return;
}
auto* mallocation = find_mallocation(region, address);
if (!mallocation) {
reportln("\n=={}== \033[31;1mHeap buffer overflow\033[0m, invalid {}-byte write at address {:p}", getpid(), size, address);
@ -315,6 +331,8 @@ bool MallocTracer::is_reachable(const Mallocation& mallocation) const
return IterationDecision::Continue;
if (region.is_text())
return IterationDecision::Continue;
if (!region.is_readable())
return IterationDecision::Continue;
// Skip malloc blocks
if (region.is_mmap() && static_cast<const MmapRegion&>(region).is_malloc_block())
return IterationDecision::Continue;