mirror of
https://github.com/Atmosphere-NX/Atmosphere.git
synced 2024-12-18 08:22:04 +00:00
kern: add tracing for irq/scheduling
This commit is contained in:
parent
8e5c0a9663
commit
f058536b59
6 changed files with 59 additions and 12 deletions
|
@ -32,10 +32,17 @@ namespace ams::kern {
|
||||||
class KTrace {
|
class KTrace {
|
||||||
public:
|
public:
|
||||||
enum Type {
|
enum Type {
|
||||||
|
Type_ThreadSwitch = 1,
|
||||||
|
|
||||||
Type_SvcEntry0 = 3,
|
Type_SvcEntry0 = 3,
|
||||||
Type_SvcEntry1 = 4,
|
Type_SvcEntry1 = 4,
|
||||||
Type_SvcExit0 = 5,
|
Type_SvcExit0 = 5,
|
||||||
Type_SvcExit1 = 6,
|
Type_SvcExit1 = 6,
|
||||||
|
Type_Interrupt = 7,
|
||||||
|
|
||||||
|
Type_ScheduleUpdate = 11,
|
||||||
|
|
||||||
|
Type_CoreMigration = 14,
|
||||||
};
|
};
|
||||||
private:
|
private:
|
||||||
static bool s_is_active;
|
static bool s_is_active;
|
||||||
|
@ -65,6 +72,18 @@ namespace ams::kern {
|
||||||
} \
|
} \
|
||||||
})
|
})
|
||||||
|
|
||||||
|
#define MESOSPHERE_KTRACE_PUSH_RECORD(TYPE, ...) \
|
||||||
|
({ \
|
||||||
|
if constexpr (::ams::kern::IsKTraceEnabled) { \
|
||||||
|
if (::ams::kern::KTrace::IsActive()) { \
|
||||||
|
::ams::kern::KTrace::PushRecord(TYPE, ## __VA_ARGS__); \
|
||||||
|
} \
|
||||||
|
} \
|
||||||
|
})
|
||||||
|
|
||||||
|
#define MESOSPHERE_KTRACE_THREAD_SWITCH(NEXT) \
|
||||||
|
MESOSPHERE_KTRACE_PUSH_RECORD(::ams::kern::KTrace::Type_ThreadSwitch, (NEXT)->GetId())
|
||||||
|
|
||||||
#define MESOSPHERE_KTRACE_SVC_ENTRY(SVC_ID, PARAM0, PARAM1, PARAM2, PARAM3, PARAM4, PARAM5, PARAM6, PARAM7) \
|
#define MESOSPHERE_KTRACE_SVC_ENTRY(SVC_ID, PARAM0, PARAM1, PARAM2, PARAM3, PARAM4, PARAM5, PARAM6, PARAM7) \
|
||||||
({ \
|
({ \
|
||||||
if constexpr (::ams::kern::IsKTraceEnabled) { \
|
if constexpr (::ams::kern::IsKTraceEnabled) { \
|
||||||
|
@ -84,3 +103,12 @@ namespace ams::kern {
|
||||||
} \
|
} \
|
||||||
} \
|
} \
|
||||||
})
|
})
|
||||||
|
|
||||||
|
#define MESOSPHERE_KTRACE_INTERRUPT(ID) \
|
||||||
|
MESOSPHERE_KTRACE_PUSH_RECORD(::ams::kern::KTrace::Type_Interrupt, ID)
|
||||||
|
|
||||||
|
#define MESOSPHERE_KTRACE_SCHEDULE_UPDATE(CORE, PREV, NEXT) \
|
||||||
|
MESOSPHERE_KTRACE_PUSH_RECORD(::ams::kern::KTrace::Type_ScheduleUpdate, CORE, (PREV)->GetId(), (NEXT)->GetId())
|
||||||
|
|
||||||
|
#define MESOSPHERE_KTRACE_CORE_MIGRATION(THREAD_ID, PREV, NEXT, REASON) \
|
||||||
|
MESOSPHERE_KTRACE_PUSH_RECORD(::ams::kern::KTrace::Type_CoreMigration, THREAD_ID, PREV, NEXT, REASON)
|
||||||
|
|
|
@ -111,6 +111,9 @@ namespace ams::kern::arch::arm64 {
|
||||||
const u32 raw_irq = this->interrupt_controller.GetIrq();
|
const u32 raw_irq = this->interrupt_controller.GetIrq();
|
||||||
const s32 irq = KInterruptController::ConvertRawIrq(raw_irq);
|
const s32 irq = KInterruptController::ConvertRawIrq(raw_irq);
|
||||||
|
|
||||||
|
/* Trace the interrupt. */
|
||||||
|
MESOSPHERE_KTRACE_INTERRUPT(irq);
|
||||||
|
|
||||||
/* If the IRQ is spurious, we don't need to reschedule. */
|
/* If the IRQ is spurious, we don't need to reschedule. */
|
||||||
if (irq < 0) {
|
if (irq < 0) {
|
||||||
return false;
|
return false;
|
||||||
|
|
|
@ -86,18 +86,20 @@ _ZN3ams4kern4arch5arm6412SvcHandler64Ev:
|
||||||
|
|
||||||
/* If we should, trace the svc entry. */
|
/* If we should, trace the svc entry. */
|
||||||
#if defined(MESOSPHERE_BUILD_FOR_TRACING)
|
#if defined(MESOSPHERE_BUILD_FOR_TRACING)
|
||||||
sub sp, sp, #0x40
|
sub sp, sp, #0x50
|
||||||
stp x0, x1, [sp, #(8 * 0)]
|
stp x0, x1, [sp, #(8 * 0)]
|
||||||
stp x2, x3, [sp, #(8 * 2)]
|
stp x2, x3, [sp, #(8 * 2)]
|
||||||
stp x4, x5, [sp, #(8 * 4)]
|
stp x4, x5, [sp, #(8 * 4)]
|
||||||
stp x6, x7, [sp, #(8 * 6)]
|
stp x6, x7, [sp, #(8 * 6)]
|
||||||
|
str x11, [sp, #(8 * 8)]
|
||||||
mov x0, sp
|
mov x0, sp
|
||||||
bl _ZN3ams4kern3svc13TraceSvcEntryEPKm
|
bl _ZN3ams4kern3svc13TraceSvcEntryEPKm
|
||||||
ldp x0, x1, [sp, #(8 * 0)]
|
ldp x0, x1, [sp, #(8 * 0)]
|
||||||
ldp x2, x3, [sp, #(8 * 2)]
|
ldp x2, x3, [sp, #(8 * 2)]
|
||||||
ldp x4, x5, [sp, #(8 * 4)]
|
ldp x4, x5, [sp, #(8 * 4)]
|
||||||
ldp x6, x7, [sp, #(8 * 6)]
|
ldp x6, x7, [sp, #(8 * 6)]
|
||||||
add sp, sp, #0x40
|
ldr x11, [sp, #(8 * 8)]
|
||||||
|
add sp, sp, #0x50
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* Invoke the SVC handler. */
|
/* Invoke the SVC handler. */
|
||||||
|
@ -294,18 +296,20 @@ _ZN3ams4kern4arch5arm6412SvcHandler32Ev:
|
||||||
|
|
||||||
/* If we should, trace the svc entry. */
|
/* If we should, trace the svc entry. */
|
||||||
#if defined(MESOSPHERE_BUILD_FOR_TRACING)
|
#if defined(MESOSPHERE_BUILD_FOR_TRACING)
|
||||||
sub sp, sp, #0x40
|
sub sp, sp, #0x50
|
||||||
stp x0, x1, [sp, #(8 * 0)]
|
stp x0, x1, [sp, #(8 * 0)]
|
||||||
stp x2, x3, [sp, #(8 * 2)]
|
stp x2, x3, [sp, #(8 * 2)]
|
||||||
stp x4, x5, [sp, #(8 * 4)]
|
stp x4, x5, [sp, #(8 * 4)]
|
||||||
stp x6, x7, [sp, #(8 * 6)]
|
stp x6, x7, [sp, #(8 * 6)]
|
||||||
|
str x19, [sp, #(8 * 8)]
|
||||||
mov x0, sp
|
mov x0, sp
|
||||||
bl _ZN3ams4kern3svc13TraceSvcEntryEPKm
|
bl _ZN3ams4kern3svc13TraceSvcEntryEPKm
|
||||||
ldp x0, x1, [sp, #(8 * 0)]
|
ldp x0, x1, [sp, #(8 * 0)]
|
||||||
ldp x2, x3, [sp, #(8 * 2)]
|
ldp x2, x3, [sp, #(8 * 2)]
|
||||||
ldp x4, x5, [sp, #(8 * 4)]
|
ldp x4, x5, [sp, #(8 * 4)]
|
||||||
ldp x6, x7, [sp, #(8 * 6)]
|
ldp x6, x7, [sp, #(8 * 6)]
|
||||||
add sp, sp, #0x40
|
ldr x19, [sp, #(8 * 8)]
|
||||||
|
add sp, sp, #0x50
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* Invoke the SVC handler. */
|
/* Invoke the SVC handler. */
|
||||||
|
|
|
@ -99,6 +99,8 @@ namespace ams::kern {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
MESOSPHERE_KTRACE_SCHEDULE_UPDATE(this->core_id, (prev_highest_thread != nullptr ? prev_highest_thread : this->idle_thread), (highest_thread != nullptr ? highest_thread : this->idle_thread));
|
||||||
|
|
||||||
this->state.highest_priority_thread = highest_thread;
|
this->state.highest_priority_thread = highest_thread;
|
||||||
this->state.needs_scheduling = true;
|
this->state.needs_scheduling = true;
|
||||||
return (1ul << this->core_id);
|
return (1ul << this->core_id);
|
||||||
|
@ -163,6 +165,7 @@ namespace ams::kern {
|
||||||
/* The suggested thread isn't bound to its core, so we can migrate it! */
|
/* The suggested thread isn't bound to its core, so we can migrate it! */
|
||||||
suggested->SetActiveCore(core_id);
|
suggested->SetActiveCore(core_id);
|
||||||
priority_queue.ChangeCore(suggested_core, suggested);
|
priority_queue.ChangeCore(suggested_core, suggested);
|
||||||
|
MESOSPHERE_KTRACE_CORE_MIGRATION(suggested->GetId(), suggested_core, core_id, 1);
|
||||||
top_threads[core_id] = suggested;
|
top_threads[core_id] = suggested;
|
||||||
cores_needing_scheduling |= Kernel::GetScheduler(core_id).UpdateHighestPriorityThread(top_threads[core_id]);
|
cores_needing_scheduling |= Kernel::GetScheduler(core_id).UpdateHighestPriorityThread(top_threads[core_id]);
|
||||||
break;
|
break;
|
||||||
|
@ -188,6 +191,7 @@ namespace ams::kern {
|
||||||
/* Perform the migration. */
|
/* Perform the migration. */
|
||||||
suggested->SetActiveCore(core_id);
|
suggested->SetActiveCore(core_id);
|
||||||
priority_queue.ChangeCore(candidate_core, suggested);
|
priority_queue.ChangeCore(candidate_core, suggested);
|
||||||
|
MESOSPHERE_KTRACE_CORE_MIGRATION(suggested->GetId(), candidate_core, core_id, 2);
|
||||||
top_threads[core_id] = suggested;
|
top_threads[core_id] = suggested;
|
||||||
cores_needing_scheduling |= Kernel::GetScheduler(core_id).UpdateHighestPriorityThread(top_threads[core_id]);
|
cores_needing_scheduling |= Kernel::GetScheduler(core_id).UpdateHighestPriorityThread(top_threads[core_id]);
|
||||||
break;
|
break;
|
||||||
|
@ -253,6 +257,8 @@ namespace ams::kern {
|
||||||
this->prev_thread = nullptr;
|
this->prev_thread = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
MESOSPHERE_KTRACE_THREAD_SWITCH(next_thread);
|
||||||
|
|
||||||
/* Switch the current process, if we're switching processes. */
|
/* Switch the current process, if we're switching processes. */
|
||||||
if (KProcess *next_process = next_thread->GetOwnerProcess(); next_process != cur_process) {
|
if (KProcess *next_process = next_thread->GetOwnerProcess(); next_process != cur_process) {
|
||||||
/* MESOSPHERE_LOG("!!! PROCESS SWITCH !!! %s -> %s\n", cur_process != nullptr ? cur_process->GetName() : nullptr, next_process != nullptr ? next_process->GetName() : nullptr); */
|
/* MESOSPHERE_LOG("!!! PROCESS SWITCH !!! %s -> %s\n", cur_process != nullptr ? cur_process->GetName() : nullptr, next_process != nullptr ? next_process->GetName() : nullptr); */
|
||||||
|
@ -496,6 +502,7 @@ namespace ams::kern {
|
||||||
if (running_on_suggested_core == nullptr || running_on_suggested_core->GetPriority() >= HighestCoreMigrationAllowedPriority) {
|
if (running_on_suggested_core == nullptr || running_on_suggested_core->GetPriority() >= HighestCoreMigrationAllowedPriority) {
|
||||||
suggested->SetActiveCore(core_id);
|
suggested->SetActiveCore(core_id);
|
||||||
priority_queue.ChangeCore(suggested_core, suggested, true);
|
priority_queue.ChangeCore(suggested_core, suggested, true);
|
||||||
|
MESOSPHERE_KTRACE_CORE_MIGRATION(suggested->GetId(), suggested_core, core_id, 3);
|
||||||
IncrementScheduledCount(suggested);
|
IncrementScheduledCount(suggested);
|
||||||
break;
|
break;
|
||||||
} else {
|
} else {
|
||||||
|
@ -549,6 +556,7 @@ namespace ams::kern {
|
||||||
/* Migrate the current thread to core -1. */
|
/* Migrate the current thread to core -1. */
|
||||||
cur_thread.SetActiveCore(-1);
|
cur_thread.SetActiveCore(-1);
|
||||||
priority_queue.ChangeCore(core_id, std::addressof(cur_thread));
|
priority_queue.ChangeCore(core_id, std::addressof(cur_thread));
|
||||||
|
MESOSPHERE_KTRACE_CORE_MIGRATION(cur_thread.GetId(), core_id, -1, 4);
|
||||||
IncrementScheduledCount(std::addressof(cur_thread));
|
IncrementScheduledCount(std::addressof(cur_thread));
|
||||||
|
|
||||||
/* If there's nothing scheduled, we can try to perform a migration. */
|
/* If there's nothing scheduled, we can try to perform a migration. */
|
||||||
|
@ -563,6 +571,7 @@ namespace ams::kern {
|
||||||
if (top_on_suggested_core == nullptr || top_on_suggested_core->GetPriority() >= HighestCoreMigrationAllowedPriority) {
|
if (top_on_suggested_core == nullptr || top_on_suggested_core->GetPriority() >= HighestCoreMigrationAllowedPriority) {
|
||||||
suggested->SetActiveCore(core_id);
|
suggested->SetActiveCore(core_id);
|
||||||
priority_queue.ChangeCore(suggested_core, suggested);
|
priority_queue.ChangeCore(suggested_core, suggested);
|
||||||
|
MESOSPHERE_KTRACE_CORE_MIGRATION(suggested->GetId(), suggested_core, core_id, 5);
|
||||||
IncrementScheduledCount(suggested);
|
IncrementScheduledCount(suggested);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -28,8 +28,11 @@ namespace ams::kern {
|
||||||
|
|
||||||
void KServerPort::CleanupSessions() {
|
void KServerPort::CleanupSessions() {
|
||||||
/* Ensure our preconditions are met. */
|
/* Ensure our preconditions are met. */
|
||||||
MESOSPHERE_ASSERT(this->IsLight() || this->session_list.empty());
|
if (this->IsLight()) {
|
||||||
MESOSPHERE_ASSERT(!this->IsLight() || this->light_session_list.empty());
|
MESOSPHERE_ASSERT(this->session_list.empty());
|
||||||
|
} else {
|
||||||
|
MESOSPHERE_ASSERT(this->light_session_list.empty());
|
||||||
|
}
|
||||||
|
|
||||||
/* Cleanup the session list. */
|
/* Cleanup the session list. */
|
||||||
while (true) {
|
while (true) {
|
||||||
|
|
Loading…
Reference in a new issue