Kernel: Per processor information is now stored in class Processor
This allows us to allocate processor stacks, and other per processor structures dynamically in runtime. Giving processor stack to ap_trampoline feels super hacky, but it works for now.
This commit is contained in:
@@ -50,10 +50,10 @@ namespace Kernel
|
||||
|
||||
InterruptState lock()
|
||||
{
|
||||
auto id = get_processor_id();
|
||||
auto id = Processor::current_id();
|
||||
|
||||
auto state = get_interrupt_state();
|
||||
set_interrupt_state(InterruptState::Disabled);
|
||||
auto state = Processor::get_interrupt_state();
|
||||
Processor::set_interrupt_state(InterruptState::Disabled);
|
||||
|
||||
while (!m_locker.compare_exchange(PROCESSOR_NONE, id, BAN::MemoryOrder::memory_order_acquire))
|
||||
__builtin_ia32_pause();
|
||||
@@ -64,7 +64,7 @@ namespace Kernel
|
||||
void unlock(InterruptState state)
|
||||
{
|
||||
m_locker.store(PROCESSOR_NONE, BAN::MemoryOrder::memory_order_release);
|
||||
set_interrupt_state(state);
|
||||
Processor::set_interrupt_state(state);
|
||||
}
|
||||
|
||||
bool is_locked() const { return m_locker != PROCESSOR_NONE; }
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
#pragma once
|
||||
|
||||
#include <BAN/ForwardList.h>
|
||||
#include <kernel/Arch.h>
|
||||
|
||||
namespace Kernel
|
||||
@@ -11,36 +12,65 @@ namespace Kernel
|
||||
Enabled,
|
||||
};
|
||||
|
||||
#if ARCH(x86_64) || ARCH(i386)
|
||||
|
||||
inline void set_interrupt_state(InterruptState state)
|
||||
{
|
||||
if (state == InterruptState::Enabled)
|
||||
asm volatile("sti");
|
||||
else
|
||||
asm volatile("cli");
|
||||
}
|
||||
|
||||
inline InterruptState get_interrupt_state()
|
||||
{
|
||||
uintptr_t flags;
|
||||
asm volatile("pushf; pop %0" : "=rm"(flags));
|
||||
if (flags & (1 << 9))
|
||||
return InterruptState::Enabled;
|
||||
return InterruptState::Disabled;
|
||||
}
|
||||
|
||||
using ProcessorID = uint8_t;
|
||||
constexpr ProcessorID PROCESSOR_NONE = 0xFF;
|
||||
inline ProcessorID get_processor_id()
|
||||
{
|
||||
uint16_t id;
|
||||
asm volatile("movw %%gs, %0" : "=rm"(id));
|
||||
return id;
|
||||
}
|
||||
|
||||
#if ARCH(x86_64)
|
||||
class Processor
|
||||
{
|
||||
BAN_NON_COPYABLE(Processor);
|
||||
|
||||
public:
|
||||
static Processor& create(ProcessorID id);
|
||||
|
||||
static ProcessorID current_id()
|
||||
{
|
||||
uint16_t id;
|
||||
asm volatile("movw %%gs, %0" : "=rm"(id));
|
||||
return id;
|
||||
}
|
||||
|
||||
static Processor& get(ProcessorID);
|
||||
|
||||
static Processor& current() { return get(current_id()); }
|
||||
|
||||
static void set_interrupt_state(InterruptState state)
|
||||
{
|
||||
if (state == InterruptState::Enabled)
|
||||
asm volatile("sti");
|
||||
else
|
||||
asm volatile("cli");
|
||||
}
|
||||
|
||||
static InterruptState get_interrupt_state()
|
||||
{
|
||||
uintptr_t flags;
|
||||
asm volatile("pushf; pop %0" : "=rm"(flags));
|
||||
if (flags & (1 << 9))
|
||||
return InterruptState::Enabled;
|
||||
return InterruptState::Disabled;
|
||||
};
|
||||
|
||||
uintptr_t stack_bottom() const { return reinterpret_cast<uintptr_t>(m_stack); }
|
||||
uintptr_t stack_top() const { return stack_bottom() + m_stack_size; }
|
||||
|
||||
private:
|
||||
Processor() = default;
|
||||
Processor(Processor&& other)
|
||||
{
|
||||
m_stack = other.m_stack;
|
||||
other.m_stack = nullptr;
|
||||
}
|
||||
~Processor();
|
||||
|
||||
private:
|
||||
void* m_stack { nullptr };
|
||||
static constexpr size_t m_stack_size { 4096 };
|
||||
|
||||
friend class BAN::Vector<Processor>;
|
||||
};
|
||||
#else
|
||||
#error "Unknown architecure"
|
||||
#error
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user