mirror of
https://github.com/genodelabs/genode.git
synced 2025-06-06 09:21:49 +00:00
parent
90bea1499e
commit
e61f6cfd38
62
repos/base/run/migrate.run
Normal file
62
repos/base/run/migrate.run
Normal file
@ -0,0 +1,62 @@
|
|||||||
|
build "core init test/migrate timer"
|
||||||
|
|
||||||
|
if {![have_include "power_on/qemu"]} {
|
||||||
|
puts "Run script is not supported on this platform"
|
||||||
|
exit 0
|
||||||
|
}
|
||||||
|
if {[have_spec foc] && ([have_spec pbxa9] || [have_spec rpi3])} {
|
||||||
|
# foc kernel does detect solely 1 CPU */
|
||||||
|
puts "Run script is not supported on this platform"
|
||||||
|
exit 0
|
||||||
|
}
|
||||||
|
if {![have_spec nova] && ![have_spec foc] && ![have_spec sel4]} {
|
||||||
|
puts "Run script is not supported on this platform"
|
||||||
|
exit 0
|
||||||
|
}
|
||||||
|
|
||||||
|
create_boot_directory
|
||||||
|
|
||||||
|
append config {
|
||||||
|
<config prio_levels="2">
|
||||||
|
<parent-provides>
|
||||||
|
<service name="LOG"/>
|
||||||
|
<service name="CPU"/>
|
||||||
|
<service name="ROM"/>
|
||||||
|
<service name="PD"/>
|
||||||
|
<service name="IO_PORT"/> <!-- on some kernels for timer -->
|
||||||
|
<service name="IRQ"/> <!-- on some kernels for timer -->
|
||||||
|
<service name="TRACE"/> <!-- used by migration test -->
|
||||||
|
</parent-provides>
|
||||||
|
<default-route>
|
||||||
|
<any-service> <parent/> <any-child/> </any-service>
|
||||||
|
</default-route>
|
||||||
|
|
||||||
|
<start name="timer" caps="100">
|
||||||
|
<resource name="RAM" quantum="1M"/>
|
||||||
|
<provides><service name="Timer"/></provides>
|
||||||
|
</start>
|
||||||
|
|
||||||
|
<start name="test-migrate" caps="100">
|
||||||
|
<resource name="RAM" quantum="10M"/>
|
||||||
|
<config />
|
||||||
|
</start>
|
||||||
|
</config>
|
||||||
|
}
|
||||||
|
|
||||||
|
install_config $config
|
||||||
|
|
||||||
|
build_boot_image "core ld.lib.so init test-migrate timer"
|
||||||
|
|
||||||
|
append qemu_args "-nographic "
|
||||||
|
append qemu_args "-smp 4,cores=4,threads=1"
|
||||||
|
|
||||||
|
run_genode_until {.*test completed successfully.*\n} 70
|
||||||
|
|
||||||
|
grep_output {^\[init -> test-migrate\] \[ep\] thread 'migrate' migrated, .*}
|
||||||
|
|
||||||
|
compare_output_to {
|
||||||
|
[init -> test-migrate] [ep] thread 'migrate' migrated, location=1x0
|
||||||
|
[init -> test-migrate] [ep] thread 'migrate' migrated, location=2x0
|
||||||
|
[init -> test-migrate] [ep] thread 'migrate' migrated, location=3x0
|
||||||
|
[init -> test-migrate] [ep] thread 'migrate' migrated, location=0x0
|
||||||
|
}
|
173
repos/base/src/test/migrate/main.cc
Normal file
173
repos/base/src/test/migrate/main.cc
Normal file
@ -0,0 +1,173 @@
|
|||||||
|
/*
|
||||||
|
* \brief Testing thread migration
|
||||||
|
* \author Alexander Boettcher
|
||||||
|
* \date 2020-08-13
|
||||||
|
*/
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Copyright (C) 2020 Genode Labs GmbH
|
||||||
|
*
|
||||||
|
* This file is part of the Genode OS framework, which is distributed
|
||||||
|
* under the terms of the GNU Affero General Public License version 3.
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* Genode includes */
|
||||||
|
#include <base/component.h>
|
||||||
|
#include <cpu_session/connection.h>
|
||||||
|
#include <cpu_thread/client.h>
|
||||||
|
#include <timer_session/connection.h>
|
||||||
|
#include <trace_session/connection.h>
|
||||||
|
|
||||||
|
using namespace Genode;
|
||||||
|
|
||||||
|
|
||||||
|
enum { STACK_SIZE = 0x3000 };
|
||||||
|
|
||||||
|
/************************************************
|
||||||
|
** Migrate thread over all available CPU test **
|
||||||
|
************************************************/
|
||||||
|
|
||||||
|
struct Migrate_thread : Thread
|
||||||
|
{
|
||||||
|
Blockade blockade { };
|
||||||
|
Env &env;
|
||||||
|
|
||||||
|
Migrate_thread(Env &env)
|
||||||
|
: Thread(env, "migrate", STACK_SIZE), env(env)
|
||||||
|
{ }
|
||||||
|
|
||||||
|
void entry() override
|
||||||
|
{
|
||||||
|
Cpu_thread_client thread_client(cap());
|
||||||
|
|
||||||
|
/* we are ready */
|
||||||
|
blockade.wakeup();
|
||||||
|
|
||||||
|
while (true) {
|
||||||
|
log("[migrate] going to sleep");
|
||||||
|
|
||||||
|
blockade.block();
|
||||||
|
|
||||||
|
log("[migrate] woke up - got migrated ?");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
struct Migrate
|
||||||
|
{
|
||||||
|
Env &env;
|
||||||
|
Timer::Connection timer { env };
|
||||||
|
Migrate_thread thread { env };
|
||||||
|
Trace::Connection trace { env, 15 * 4096 /* RAM quota */,
|
||||||
|
11 * 4096 /* ARG_BUFFER RAM quota */,
|
||||||
|
0 /* parent levels */ };
|
||||||
|
|
||||||
|
Signal_handler<Migrate> timer_handler { env.ep(), *this,
|
||||||
|
&Migrate::check_traces };
|
||||||
|
|
||||||
|
Trace::Subject_id trace_id { };
|
||||||
|
Affinity::Location location { };
|
||||||
|
unsigned loc_same { 0 };
|
||||||
|
unsigned loc_pos { 0 };
|
||||||
|
|
||||||
|
unsigned test_rounds { 0 };
|
||||||
|
|
||||||
|
enum State {
|
||||||
|
LOOKUP_TRACE_ID, CHECK_AFFINITY, MIGRATE
|
||||||
|
} state { LOOKUP_TRACE_ID };
|
||||||
|
|
||||||
|
Migrate(Env &env) : env(env)
|
||||||
|
{
|
||||||
|
Affinity::Space cpus = env.cpu().affinity_space();
|
||||||
|
log("Detected ", cpus.width(), "x", cpus.height(), " CPU",
|
||||||
|
cpus.total() > 1 ? "s." : ".");
|
||||||
|
|
||||||
|
timer.sigh(timer_handler);
|
||||||
|
|
||||||
|
thread.start();
|
||||||
|
thread.blockade.block();
|
||||||
|
|
||||||
|
timer.trigger_periodic( 500 * 1000 /* us */);
|
||||||
|
}
|
||||||
|
|
||||||
|
void check_traces()
|
||||||
|
{
|
||||||
|
switch (state) {
|
||||||
|
case LOOKUP_TRACE_ID:
|
||||||
|
{
|
||||||
|
auto count = trace.for_each_subject_info([&](Trace::Subject_id const &id,
|
||||||
|
Trace::Subject_info const &info)
|
||||||
|
{
|
||||||
|
if (info.thread_name() != "migrate")
|
||||||
|
return;
|
||||||
|
|
||||||
|
trace_id = id;
|
||||||
|
location = info.affinity();
|
||||||
|
state = CHECK_AFFINITY;
|
||||||
|
|
||||||
|
log("[ep] thread '", info.thread_name(), "' started,",
|
||||||
|
" location=", location.xpos(), "x", location.ypos());
|
||||||
|
});
|
||||||
|
|
||||||
|
if (count.count == count.limit && state == LOOKUP_TRACE_ID) {
|
||||||
|
error("trace argument buffer too small for the test");
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
case CHECK_AFFINITY:
|
||||||
|
{
|
||||||
|
Trace::Subject_info const info = trace.subject_info(trace_id);
|
||||||
|
|
||||||
|
loc_same ++;
|
||||||
|
|
||||||
|
if ((location.xpos() == info.affinity().xpos()) &&
|
||||||
|
(location.ypos() == info.affinity().ypos()) &&
|
||||||
|
(location.width() == info.affinity().width()) &&
|
||||||
|
(location.height() == info.affinity().height()))
|
||||||
|
{
|
||||||
|
if (loc_same >= 1) {
|
||||||
|
loc_same = 0;
|
||||||
|
state = MIGRATE;
|
||||||
|
}
|
||||||
|
log ("[ep] .");
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
loc_same = 0;
|
||||||
|
location = info.affinity();
|
||||||
|
|
||||||
|
log("[ep] thread '", info.thread_name(), "' migrated,",
|
||||||
|
" location=", location.xpos(), "x", location.ypos());
|
||||||
|
|
||||||
|
test_rounds ++;
|
||||||
|
if (test_rounds == 4)
|
||||||
|
log("--- test completed successfully ---");
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
case MIGRATE:
|
||||||
|
state = CHECK_AFFINITY;
|
||||||
|
|
||||||
|
loc_pos ++;
|
||||||
|
Affinity::Location const loc = env.cpu().affinity_space().location_of_index(loc_pos);
|
||||||
|
|
||||||
|
/* trigger migration */
|
||||||
|
Cpu_thread_client client(thread.cap());
|
||||||
|
client.affinity(loc);
|
||||||
|
|
||||||
|
log("[ep] thread 'migrate' scheduled to migrate to location=",
|
||||||
|
loc.xpos(), "x", loc.ypos());
|
||||||
|
|
||||||
|
thread.blockade.wakeup();
|
||||||
|
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
void Component::construct(Env &env)
|
||||||
|
{
|
||||||
|
log("--- migrate thread test started ---");
|
||||||
|
|
||||||
|
static Migrate migrate_test(env);
|
||||||
|
}
|
3
repos/base/src/test/migrate/target.mk
Normal file
3
repos/base/src/test/migrate/target.mk
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
TARGET = test-migrate
|
||||||
|
SRC_CC = main.cc
|
||||||
|
LIBS = base
|
@ -22,6 +22,7 @@ lx_hybrid_ctors
|
|||||||
lx_hybrid_exception
|
lx_hybrid_exception
|
||||||
lx_hybrid_pthread_ipc
|
lx_hybrid_pthread_ipc
|
||||||
microcode
|
microcode
|
||||||
|
migrate
|
||||||
moon
|
moon
|
||||||
netperf_lwip
|
netperf_lwip
|
||||||
netperf_lwip_bridge
|
netperf_lwip_bridge
|
||||||
|
Loading…
x
Reference in New Issue
Block a user