mirror of
https://github.com/genodelabs/genode.git
synced 2025-04-12 05:41:36 +00:00
Fix: don't deference stale pager pointer in core
Reset pager pointer in platform_thread if pager object is removed. Fixes #532
This commit is contained in:
parent
1720e04fdc
commit
fa2cbdc7cb
@ -157,7 +157,10 @@ void Platform_thread::unbind()
|
||||
void Platform_thread::pager(Pager_object *pager_obj)
|
||||
{
|
||||
_pager_obj = pager_obj;
|
||||
_pager.local = pager_obj->cap();
|
||||
if (_pager_obj)
|
||||
_pager.local = pager_obj->cap();
|
||||
else
|
||||
_pager.local = Native_capability();
|
||||
}
|
||||
|
||||
|
||||
|
@ -20,14 +20,26 @@
|
||||
#include <base/signal.h>
|
||||
#include <pager/capability.h>
|
||||
#include <cap_session/cap_session.h>
|
||||
#include <thread/capability.h>
|
||||
|
||||
namespace Genode {
|
||||
|
||||
struct Pager_object
|
||||
{
|
||||
Thread_capability _thread_cap;
|
||||
|
||||
virtual ~Pager_object() { }
|
||||
|
||||
void exception_handler(Signal_context_capability) { }
|
||||
|
||||
public:
|
||||
|
||||
/**
|
||||
* Remember thread cap so that rm_session can tell thread that
|
||||
* rm_client is gone.
|
||||
*/
|
||||
Thread_capability thread_cap() { return _thread_cap; } const
|
||||
void thread_cap(Thread_capability cap) { _thread_cap = cap; }
|
||||
};
|
||||
|
||||
class Pager_activation_base { };
|
||||
|
@ -65,6 +65,8 @@ namespace Genode {
|
||||
bool singlestep;
|
||||
} _state;
|
||||
|
||||
Thread_capability _thread_cap;
|
||||
|
||||
void _copy_state(Nova::Utcb * utcb);
|
||||
|
||||
static void _page_fault_handler();
|
||||
@ -176,6 +178,13 @@ namespace Genode {
|
||||
void client_set_ec(addr_t ec) { _state.sel_client_ec = ec; }
|
||||
|
||||
void single_step(bool on) { _state.singlestep = on; }
|
||||
|
||||
/**
|
||||
* Remember thread cap so that rm_session can tell thread that
|
||||
* rm_client is gone.
|
||||
*/
|
||||
Thread_capability thread_cap() { return _thread_cap; } const
|
||||
void thread_cap(Thread_capability cap) { _thread_cap = cap; }
|
||||
};
|
||||
|
||||
|
||||
|
@ -34,6 +34,10 @@ void Ram_session_component::_revoke_ram_ds(Dataspace_component *ds)
|
||||
{
|
||||
size_t page_rounded_size = (ds->size() + get_page_size() - 1) & get_page_mask();
|
||||
|
||||
if (verbose_ram_ds)
|
||||
printf("-- revoke - ram ds size=0x%8zx phys 0x%8lx has core-local addr 0x%8lx - thread 0x%8p\n",
|
||||
page_rounded_size, ds->phys_addr(), ds->core_local_addr(), Thread_base::myself()->utcb());
|
||||
|
||||
unmap_local((Nova::Utcb *)Thread_base::myself()->utcb(),
|
||||
ds->core_local_addr(),
|
||||
page_rounded_size >> get_page_size_log2());
|
||||
@ -76,8 +80,8 @@ void Ram_session_component::_clear_ds(Dataspace_component *ds)
|
||||
}
|
||||
|
||||
if (verbose_ram_ds)
|
||||
printf("-- ram ds size=%zx phys %lx has core-local addr %p\n",
|
||||
page_rounded_size, ds->phys_addr(), virt_addr);
|
||||
printf("-- map - ram ds size=0x%8zx phys 0x%8lx has core-local addr 0x%8p - thread 0x%8p\n",
|
||||
page_rounded_size, ds->phys_addr(), virt_addr, Thread_base::myself()->utcb());
|
||||
|
||||
/* map the dataspace's physical pages to local addresses */
|
||||
const Nova::Rights rights(true, true, true);
|
||||
|
@ -43,6 +43,8 @@ namespace Genode {
|
||||
*/
|
||||
unsigned long _badge;
|
||||
|
||||
Thread_capability _thread_cap;
|
||||
|
||||
/**
|
||||
* User-level signal handler registered for this pager object via
|
||||
* 'Cpu_session::exception_handler()'.
|
||||
@ -97,6 +99,13 @@ namespace Genode {
|
||||
Signal_transmitter transmitter(_exception_sigh);
|
||||
transmitter.submit();
|
||||
}
|
||||
|
||||
/**
|
||||
* Remember thread cap so that rm_session can tell thread that
|
||||
* rm_client is gone.
|
||||
*/
|
||||
Thread_capability thread_cap() { return _thread_cap; } const
|
||||
void thread_cap(Thread_capability cap) { _thread_cap = cap; }
|
||||
};
|
||||
|
||||
/**
|
||||
|
@ -81,6 +81,8 @@ int Cpu_session_component::set_pager(Thread_capability thread_cap,
|
||||
if (!p) return -2;
|
||||
|
||||
thread->platform_thread()->pager(p);
|
||||
p->thread_cap(thread->cap());
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -756,6 +756,15 @@ Rm_session_component::~Rm_session_component()
|
||||
|
||||
/* remove all clients */
|
||||
while (Rm_client *cl = _client_slab.raw()->first_object()) {
|
||||
Thread_capability thread_cap = cl->thread_cap();
|
||||
if (thread_cap.valid()) {
|
||||
/* lookup thread and reset pager pointer */
|
||||
Cpu_thread_component *cpu_thread = dynamic_cast<Cpu_thread_component *>
|
||||
(_thread_ep->obj_by_cap(thread_cap));
|
||||
if (cpu_thread)
|
||||
cpu_thread->platform_thread()->pager(0);
|
||||
}
|
||||
|
||||
_lock.unlock();
|
||||
cl->dissolve_from_faulting_rm_session();
|
||||
this->dissolve(cl);
|
||||
|
Loading…
x
Reference in New Issue
Block a user