From dbd993eace86560c31d9bb1fbb5247ae46042797 Mon Sep 17 00:00:00 2001 From: Derek Bruening Date: Thu, 29 Aug 2024 12:32:01 -0400 Subject: [PATCH] i#6938 sched migrate: Add migration count to scheduler (#6950) Adds the migration count to the new scheduler stats. Adds checks of the count to various unit tests. Issue: #6938 --- clients/drcachesim/common/memtrace_stream.h | 5 ++++ clients/drcachesim/scheduler/scheduler.cpp | 10 +++++++ clients/drcachesim/scheduler/scheduler.h | 1 + .../drcachesim/tests/scheduler_unit_tests.cpp | 28 ++++++++++--------- 4 files changed, 31 insertions(+), 13 deletions(-) diff --git a/clients/drcachesim/common/memtrace_stream.h b/clients/drcachesim/common/memtrace_stream.h index e18f534ddb0..b763f616e7b 100644 --- a/clients/drcachesim/common/memtrace_stream.h +++ b/clients/drcachesim/common/memtrace_stream.h @@ -93,6 +93,11 @@ class memtrace_stream_t { SCHED_STAT_DIRECT_SWITCH_ATTEMPTS, /** Count of #TRACE_MARKER_TYPE_DIRECT_THREAD_SWITCH attempts that succeeded. */ SCHED_STAT_DIRECT_SWITCH_SUCCESSES, + /** + * Counts the number of times an input switches from another core to this core: + * i.e., the number of input migrations to this core. + */ + SCHED_STAT_MIGRATIONS, /** Count of statistic types. */ SCHED_STAT_TYPE_COUNT, }; diff --git a/clients/drcachesim/scheduler/scheduler.cpp b/clients/drcachesim/scheduler/scheduler.cpp index d4ed82bc204..87f72e73cf4 100644 --- a/clients/drcachesim/scheduler/scheduler.cpp +++ b/clients/drcachesim/scheduler/scheduler.cpp @@ -683,6 +683,8 @@ scheduler_tmpl_t::~scheduler_tmpl_t() outputs_[i].stats[memtrace_stream_t::SCHED_STAT_DIRECT_SWITCH_ATTEMPTS]); VPRINT(this, 1, " %-25s: %9" PRId64 "\n", "Direct switch successes", outputs_[i].stats[memtrace_stream_t::SCHED_STAT_DIRECT_SWITCH_SUCCESSES]); + VPRINT(this, 1, " %-25s: %9" PRId64 "\n", "Migrations", + outputs_[i].stats[memtrace_stream_t::SCHED_STAT_MIGRATIONS]); } } @@ -2621,6 +2623,14 @@ scheduler_tmpl_t::set_cur_input(output_ordinal_t output, std::lock_guard lock(*inputs_[input].lock); + if (inputs_[input].prev_output != INVALID_OUTPUT_ORDINAL && + inputs_[input].prev_output != output) { + VPRINT(this, 3, "output[%d] migrating input %d from output %d\n", output, input, + inputs_[input].prev_output); + ++outputs_[output].stats[memtrace_stream_t::SCHED_STAT_MIGRATIONS]; + } + inputs_[input].prev_output = output; + if (prev_input < 0 && outputs_[output].stream->version_ == 0) { // Set the version and filetype up front, to let the user query at init time // as documented. Also set the other fields in case we did a skip for ROI. diff --git a/clients/drcachesim/scheduler/scheduler.h b/clients/drcachesim/scheduler/scheduler.h index b5f4f2b23e9..ab380781675 100644 --- a/clients/drcachesim/scheduler/scheduler.h +++ b/clients/drcachesim/scheduler/scheduler.h @@ -1297,6 +1297,7 @@ template class scheduler_tmpl_t { bool needs_advance = false; bool needs_roi = true; bool at_eof = false; + output_ordinal_t prev_output = INVALID_OUTPUT_ORDINAL; uintptr_t next_timestamp = 0; uint64_t instrs_in_quantum = 0; int instrs_pre_read = 0; diff --git a/clients/drcachesim/tests/scheduler_unit_tests.cpp b/clients/drcachesim/tests/scheduler_unit_tests.cpp index bca345d4bc3..b7f6c9b67c5 100644 --- a/clients/drcachesim/tests/scheduler_unit_tests.cpp +++ b/clients/drcachesim/tests/scheduler_unit_tests.cpp @@ -134,7 +134,7 @@ static void verify_scheduler_stats(scheduler_t::stream_t *stream, int64_t switch_input_to_input, int64_t switch_input_to_idle, int64_t switch_idle_to_input, int64_t switch_nop, int64_t preempts, int64_t direct_attempts, - int64_t direct_successes) + int64_t direct_successes, int64_t migrations) { // We assume our counts fit in the get_schedule_statistic()'s double's 54-bit // mantissa and thus we can safely use "==". @@ -156,6 +156,8 @@ verify_scheduler_stats(scheduler_t::stream_t *stream, int64_t switch_input_to_in assert(stream->get_schedule_statistic( memtrace_stream_t::SCHED_STAT_DIRECT_SWITCH_SUCCESSES) == direct_successes); + assert(stream->get_schedule_statistic(memtrace_stream_t::SCHED_STAT_MIGRATIONS) == + migrations); } static void @@ -1111,11 +1113,11 @@ test_synthetic() verify_scheduler_stats(scheduler.get_stream(0), /*switch_input_to_input=*/10, /*switch_input_to_idle=*/0, /*switch_idle_to_input=*/0, /*switch_nop=*/0, /*preempts=*/6, /*direct_attempts=*/0, - /*direct_successes=*/0); + /*direct_successes=*/0, /*migrations=*/7); verify_scheduler_stats(scheduler.get_stream(1), /*switch_input_to_input=*/11, /*switch_input_to_idle=*/1, /*switch_idle_to_input=*/0, /*switch_nop=*/0, /*preempts=*/8, /*direct_attempts=*/0, - /*direct_successes=*/0); + /*direct_successes=*/0, /*migrations=*/7); #ifndef WIN32 // XXX: Windows microseconds on test VMs are very coarse and stay the same // for long periods. Instruction quanta use wall-clock idle times, so @@ -1300,11 +1302,11 @@ test_synthetic_time_quanta() verify_scheduler_stats(scheduler.get_stream(0), /*switch_input_to_input=*/1, /*switch_input_to_idle=*/1, /*switch_idle_to_input=*/0, /*switch_nop=*/1, /*preempts=*/2, /*direct_attempts=*/0, - /*direct_successes=*/0); + /*direct_successes=*/0, /*migrations=*/0); verify_scheduler_stats(scheduler.get_stream(1), /*switch_input_to_input=*/2, /*switch_input_to_idle=*/1, /*switch_idle_to_input=*/1, /*switch_nop=*/0, /*preempts=*/1, /*direct_attempts=*/0, - /*direct_successes=*/0); + /*direct_successes=*/0, /*migrations=*/1); } { replay_file_checker_t checker; @@ -1433,11 +1435,11 @@ test_synthetic_with_timestamps() verify_scheduler_stats(scheduler.get_stream(0), /*switch_input_to_input=*/14, /*switch_input_to_idle=*/1, /*switch_idle_to_input=*/0, /*switch_nop=*/0, /*preempts=*/11, /*direct_attempts=*/0, - /*direct_successes=*/0); + /*direct_successes=*/0, /*migrations=*/7); verify_scheduler_stats(scheduler.get_stream(1), /*switch_input_to_input=*/12, /*switch_input_to_idle=*/0, /*switch_idle_to_input=*/0, /*switch_nop=*/2, /*preempts=*/9, /*direct_attempts=*/0, - /*direct_successes=*/0); + /*direct_successes=*/0, /*migrations=*/8); } static void @@ -1529,11 +1531,11 @@ test_synthetic_with_priorities() verify_scheduler_stats(scheduler.get_stream(0), /*switch_input_to_input=*/12, /*switch_input_to_idle=*/1, /*switch_idle_to_input=*/0, /*switch_nop=*/2, /*preempts=*/9, /*direct_attempts=*/0, - /*direct_successes=*/0); + /*direct_successes=*/0, /*migrations=*/8); verify_scheduler_stats(scheduler.get_stream(1), /*switch_input_to_input=*/14, /*switch_input_to_idle=*/0, /*switch_idle_to_input=*/0, /*switch_nop=*/0, /*preempts=*/11, /*direct_attempts=*/0, - /*direct_successes=*/0); + /*direct_successes=*/0, /*migrations=*/7); } static void @@ -1861,11 +1863,11 @@ test_synthetic_with_syscalls_multiple() verify_scheduler_stats(scheduler.get_stream(0), /*switch_input_to_input=*/17, /*switch_input_to_idle=*/2, /*switch_idle_to_input=*/1, /*switch_nop=*/2, /*preempts=*/11, /*direct_attempts=*/0, - /*direct_successes=*/0); + /*direct_successes=*/0, /*migrations=*/9); verify_scheduler_stats(scheduler.get_stream(1), /*switch_input_to_input=*/16, /*switch_input_to_idle=*/1, /*switch_idle_to_input=*/1, /*switch_nop=*/0, /*preempts=*/10, /*direct_attempts=*/0, - /*direct_successes=*/0); + /*direct_successes=*/0, /*migrations=*/11); } static void @@ -4261,7 +4263,7 @@ test_direct_switch() verify_scheduler_stats(scheduler.get_stream(0), /*switch_input_to_input=*/3, /*switch_input_to_idle=*/1, /*switch_idle_to_input=*/1, /*switch_nop=*/0, /*preempts=*/0, /*direct_attempts=*/3, - /*direct_successes=*/2); + /*direct_successes=*/2, /*migrations=*/0); } { // Test disabling direct switches. @@ -4302,7 +4304,7 @@ test_direct_switch() verify_scheduler_stats(scheduler.get_stream(0), /*switch_input_to_input=*/2, /*switch_input_to_idle=*/2, /*switch_idle_to_input=*/2, /*switch_nop=*/0, /*preempts=*/0, /*direct_attempts=*/0, - /*direct_successes=*/0); + /*direct_successes=*/0, /*migrations=*/0); } }