gdb_monitor: hide exceptions during create_thread

This patch is a workaround for the missing implementation of
'Pd_session::transfer_quota' interface by the GDB monitor's PD service.
The missing implementation becomes problematic with the changes of #3750
that enabled the cap-quota accounting for core's CPU service.

In regular scenarios without the GDB monitor, the client of
'Cpu_session::create_thread' deals with Out_of_caps or Out_of_ram by
upgrading the CPU session's cap and RAM quotas. This, in turn, results
in a sequence of 'transfer_quota' operations at the parent.

Since GDB monitor implements a custom PD service, these 'transfer_quota'
calls try to transfer quota between sessions provided by core and those
provided by the GDB monitor. This does of course not work. To fix this
issue, the GDB monitor needs a major overhaul. This patch side-steps
the problem by handing Out_of_caps and Out_of_ram from the debuging
target.
This commit is contained in:
Norman Feske 2020-05-15 15:13:19 +02:00
parent 4002653334
commit 0de54cddaa
3 changed files with 32 additions and 3 deletions

View File

@ -119,7 +119,7 @@ append qemu_args " -serial stdio "
append qemu_args " -serial chardev:uart "
append qemu_args " -chardev socket,id=uart,port=$local_port,host=localhost,server,nowait,ipv4 "
run_genode_until {.*\[init -> gdb_monitor\].*} 30
run_genode_until {.*\[init -> gdb_monitor\] Remote debugging using /dev/terminal.*} 30
set genode_id [output_spawn_id]
puts "GDB monitor is up, starting GDB"

View File

@ -320,7 +320,7 @@ Cpu_session_component::Cpu_session_component(Env &env,
_ep(ep),
_md_alloc(md_alloc),
_core_pd(core_pd),
_parent_cpu_session(env.session<Cpu_session>(_id_space_element.id(), args, affinity)),
_parent_cpu_session(env.session<Cpu_session>(_id_space_element.id(), args, affinity), *this),
_signal_ep(signal_ep),
_new_thread_pipe_write_end(new_thread_pipe_write_end),
_breakpoint_len(breakpoint_len),

View File

@ -20,6 +20,7 @@
#include <base/rpc_server.h>
#include <base/service.h>
#include <base/thread.h>
#include <util/retry.h>
#include <cpu_session/client.h>
#include <parent/parent.h>
#include <pd_session/capability.h>
@ -57,7 +58,35 @@ class Gdb_monitor::Cpu_session_component : public Rpc_object<Cpu_session>
Pd_session_capability _core_pd;
Cpu_session_client _parent_cpu_session;
struct Expanding_parent_cpu_session : Cpu_session_client
{
Cpu_session_component &_component;
Expanding_parent_cpu_session(Cpu_session_capability cap,
Cpu_session_component &component)
:
Cpu_session_client(cap), _component(component) { }
Thread_capability create_thread(Capability<Pd_session> pd,
Cpu_session::Name const &name,
Affinity::Location affinity,
Weight weight,
addr_t utcb) override
{
enum { UPGRADE_ATTEMPTS = ~0U };
return Genode::retry<Out_of_ram>(
[&] () {
return Genode::retry<Out_of_caps>(
[&] () { return Cpu_session_client::create_thread(pd, name, affinity, weight, utcb); },
[&] () { _component._env.upgrade(_component._id_space_element.id(), "cap_quota=3"); },
UPGRADE_ATTEMPTS);
},
[&] () { _component._env.upgrade(_component._id_space_element.id(), "ram_quota=8K"); },
UPGRADE_ATTEMPTS);
}
};
Expanding_parent_cpu_session _parent_cpu_session;
Entrypoint &_signal_ep;
int const _new_thread_pipe_write_end;