Skip to content

Commit

Permalink
Kernel/aarch64: Implement Thread Local Storage
Browse files Browse the repository at this point in the history
This commit adds Processor::set_thread_specific_data, and this function
is used to factor out architecture specific implementation of setting
the thread specific data. This function is implemented for
aarch64 and x86_64, and the callsites are changed to use this function
instead.
  • Loading branch information
FireFox317 authored and gmta committed Feb 15, 2023
1 parent 7d0917f commit cfd73e5
Show file tree
Hide file tree
Showing 6 changed files with 24 additions and 6 deletions.
5 changes: 5 additions & 0 deletions Kernel/Arch/aarch64/ASM_wrapper.h
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,11 @@ inline void set_sp_el1(FlatPtr sp_el1)
asm("msr sp_el1, %[value]" ::[value] "r"(sp_el1));
}

inline void set_tpidr_el0(FlatPtr tpidr_el0)
{
asm("msr tpidr_el0, %[value]" ::[value] "r"(tpidr_el0));
}

inline void flush()
{
asm("dsb ish");
Expand Down
7 changes: 7 additions & 0 deletions Kernel/Arch/aarch64/Processor.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -454,6 +454,8 @@ extern "C" void enter_thread_context(Thread* from_thread, Thread* to_thread)

to_thread->set_cpu(Processor::current().id());

Processor::set_thread_specific_data(to_thread->thread_specific_data());

auto in_critical = to_thread->saved_critical();
VERIFY(in_critical > 0);
Processor::restore_critical(in_critical);
Expand All @@ -466,4 +468,9 @@ StringView Processor::platform_string()
return "aarch64"sv;
}

void Processor::set_thread_specific_data(VirtualAddress thread_specific_data)
{
Aarch64::Asm::set_tpidr_el0(thread_specific_data.get());
}

}
2 changes: 2 additions & 0 deletions Kernel/Arch/aarch64/Processor.h
Original file line number Diff line number Diff line change
Expand Up @@ -279,6 +279,8 @@ class Processor {

static StringView platform_string();

static void set_thread_specific_data(VirtualAddress thread_specific_data);

private:
Processor(Processor const&) = delete;

Expand Down
9 changes: 7 additions & 2 deletions Kernel/Arch/x86_64/Processor.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1543,8 +1543,7 @@ extern "C" void enter_thread_context(Thread* from_thread, Thread* to_thread)
}

auto& processor = Processor::current();
MSR fs_base_msr(MSR_FS_BASE);
fs_base_msr.set(to_thread->thread_specific_data().get());
Processor::set_thread_specific_data(to_thread->thread_specific_data());

if (from_regs.cr3 != to_regs.cr3)
write_cr3(to_regs.cr3);
Expand Down Expand Up @@ -1887,4 +1886,10 @@ UNMAP_AFTER_INIT void Processor::initialize_context_switching(Thread& initial_th
VERIFY_NOT_REACHED();
}

void Processor::set_thread_specific_data(VirtualAddress thread_specific_data)
{
MSR fs_base_msr(MSR_FS_BASE);
fs_base_msr.set(thread_specific_data.get());
}

}
2 changes: 2 additions & 0 deletions Kernel/Arch/x86_64/Processor.h
Original file line number Diff line number Diff line change
Expand Up @@ -419,6 +419,8 @@ class Processor {
static ErrorOr<Vector<FlatPtr, 32>> capture_stack_trace(Thread& thread, size_t max_frames = 0);

static StringView platform_string();

static void set_thread_specific_data(VirtualAddress thread_specific_data);
};

}
5 changes: 1 addition & 4 deletions Kernel/Syscalls/mmap.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -566,10 +566,7 @@ ErrorOr<FlatPtr> Process::sys$allocate_tls(Userspace<char const*> initial_data,

TRY(main_thread->make_thread_specific_region({}));

#if ARCH(X86_64)
MSR fs_base_msr(MSR_FS_BASE);
fs_base_msr.set(main_thread->thread_specific_data().get());
#endif
Processor::set_thread_specific_data(main_thread->thread_specific_data());

return m_master_tls_region.unsafe_ptr()->vaddr().get();
});
Expand Down

0 comments on commit cfd73e5

Please sign in to comment.