PatchworkOS
Loading...
Searching...
No Matches
Trampoline

Trampoline for CPU initialization. More...

Macros

#define TRAMPOLINE_BASE_ADDR   0x8000
 The physical address where the trampoline code will be copied to and executed from.
 
#define TRAMPOLINE_DATA_OFFSET   0x0F00
 The offset within the trampoline page where we can store data.
 
#define TRAMPOLINE_PML4_OFFSET   (TRAMPOLINE_DATA_OFFSET + 0x00)
 Offset within the trampoline page where the PML4 address is stored.
 
#define TRAMPOLINE_ENTRY_OFFSET   (TRAMPOLINE_DATA_OFFSET + 0x08)
 Offset within the trampoline page where the entry point to jump to is stored.
 
#define TRAMPOLINE_CPU_ID_OFFSET   (TRAMPOLINE_DATA_OFFSET + 0x10)
 Offset within the trampoline page where the CPU id is stored.
 
#define TRAMPOLINE_CPU_OFFSET   (TRAMPOLINE_DATA_OFFSET + 0x18)
 Offset within the trampoline page where the CPU structure pointer is stored.
 
#define TRAMPOLINE_STACK_OFFSET   (TRAMPOLINE_DATA_OFFSET + 0x20)
 Offset within the trampoline page where the stack pointer for the trampoline is stored.
 
#define TRAMPOLINE_ADDR(offset)   ((void*)(TRAMPOLINE_BASE_ADDR + (offset)))
 Macro to get a pointer to an address within the trampoline page.
 
#define TRAMPOLINE_SIZE   ((uintptr_t)trampoline_end - (uintptr_t)trampoline_start)
 The size of the trampoline code.
 

Functions

void trampoline_start (void)
 The start of the trampoline code, defined in trampoline.s.
 
void trampoline_end (void)
 The end of the trampoline code, defined in trampoline.s.
 
void trampoline_init (void)
 Initializes the trampoline by copying the trampoline code to its designated memory location.
 
void trampoline_deinit (void)
 Deinitializes the trampoline by restoring the original contents of the trampoline memory location.
 
void trampoline_send_startup_ipi (cpu_t *cpu, cpuid_t cpuId, lapic_id_t lapicId)
 Sends the startup IPI to a CPU to start it up.
 
uint64_t trampoline_wait_ready (clock_t timeout)
 Waits for the currently starting CPU to signal that it is ready.
 
_NORETURN void trampoline_c_entry (cpu_t *self, cpuid_t cpuId)
 After the trampoline is done with basic initialization, it calls this C entry point to continue CPU initialization.
 

Detailed Description

Trampoline for CPU initialization.

The trampoline is a small piece of code used during the initialization of other CPUs in a multiprocessor system.

The trampoline code must be position-independent and fit within a single memory page, this is why we do all the weird offset stuff.

Macro Definition Documentation

◆ TRAMPOLINE_ADDR

#define TRAMPOLINE_ADDR (   offset)    ((void*)(TRAMPOLINE_BASE_ADDR + (offset)))

Macro to get a pointer to an address within the trampoline page.

Definition at line 63 of file trampoline.h.

◆ TRAMPOLINE_BASE_ADDR

#define TRAMPOLINE_BASE_ADDR   0x8000

The physical address where the trampoline code will be copied to and executed from.

Definition at line 25 of file trampoline.h.

◆ TRAMPOLINE_CPU_ID_OFFSET

#define TRAMPOLINE_CPU_ID_OFFSET   (TRAMPOLINE_DATA_OFFSET + 0x10)

Offset within the trampoline page where the CPU id is stored.

Definition at line 48 of file trampoline.h.

◆ TRAMPOLINE_CPU_OFFSET

#define TRAMPOLINE_CPU_OFFSET   (TRAMPOLINE_DATA_OFFSET + 0x18)

Offset within the trampoline page where the CPU structure pointer is stored.

Definition at line 53 of file trampoline.h.

◆ TRAMPOLINE_DATA_OFFSET

#define TRAMPOLINE_DATA_OFFSET   0x0F00

The offset within the trampoline page where we can store data.

This is used to pass data to the trampoline code, such as the stack pointer to use and the entry point to jump to. As it cannot access virtual memory yet.

Definition at line 33 of file trampoline.h.

◆ TRAMPOLINE_ENTRY_OFFSET

#define TRAMPOLINE_ENTRY_OFFSET   (TRAMPOLINE_DATA_OFFSET + 0x08)

Offset within the trampoline page where the entry point to jump to is stored.

Definition at line 43 of file trampoline.h.

◆ TRAMPOLINE_PML4_OFFSET

#define TRAMPOLINE_PML4_OFFSET   (TRAMPOLINE_DATA_OFFSET + 0x00)

Offset within the trampoline page where the PML4 address is stored.

Definition at line 38 of file trampoline.h.

◆ TRAMPOLINE_SIZE

#define TRAMPOLINE_SIZE   ((uintptr_t)trampoline_end - (uintptr_t)trampoline_start)

The size of the trampoline code.

Definition at line 78 of file trampoline.h.

◆ TRAMPOLINE_STACK_OFFSET

#define TRAMPOLINE_STACK_OFFSET   (TRAMPOLINE_DATA_OFFSET + 0x20)

Offset within the trampoline page where the stack pointer for the trampoline is stored.

Definition at line 58 of file trampoline.h.

Function Documentation

◆ trampoline_c_entry()

_NORETURN void trampoline_c_entry ( cpu_t self,
cpuid_t  cpuId 
)

After the trampoline is done with basic initialization, it calls this C entry point to continue CPU initialization.

When this function is called the trampolines stack is still being used, after cpu initalization is done we perform a jump to the idle thread of the CPU.

Parameters
selfPointer to the CPU structure of the current CPU, will still be uninitialized.
cpuIdThe ID of the current CPU.

Definition at line 99 of file trampoline.c.

References assert, cpu_init(), interrupt_frame_t::cs, ERR, thread_t::frame, GDT_CS_RING0, GDT_SS_RING0, thread_t::kernelStack, NULL, panic(), interrupt_frame_t::rflags, RFLAGS_ALWAYS_SET, interrupt_frame_t::rip, interrupt_frame_t::rsp, sched_is_idle(), sched_thread_unsafe(), interrupt_frame_t::ss, thread_jump(), stack_pointer_t::top, and trampoline_after_jump().

Referenced by trampoline_init().

◆ trampoline_deinit()

void trampoline_deinit ( void  )

Deinitializes the trampoline by restoring the original contents of the trampoline memory location.

Definition at line 51 of file trampoline.c.

References backupBuffer, LOG_DEBUG, memcpy(), NULL, PAGE_SIZE, pmm_free(), TRAMPOLINE_BASE_ADDR, and trampolineStack.

Referenced by smp_others_init().

◆ trampoline_end()

void trampoline_end ( void  )
extern

The end of the trampoline code, defined in trampoline.s.

◆ trampoline_init()

void trampoline_init ( void  )

Initializes the trampoline by copying the trampoline code to its designated memory location.

Will also backup the original contents of the trampoline memory location and restore it when trampoline_deinit() is called.

Definition at line 23 of file trampoline.c.

References assert, atomic_init, backupBuffer, cpuReadyFlag, LOG_DEBUG, memcpy(), memset(), NULL, PAGE_SIZE, panic(), PML_ENSURE_LOWER_HALF, pmm_alloc(), TRAMPOLINE_ADDR, TRAMPOLINE_BASE_ADDR, trampoline_c_entry(), TRAMPOLINE_DATA_OFFSET, TRAMPOLINE_ENTRY_OFFSET, TRAMPOLINE_PML4_OFFSET, TRAMPOLINE_SIZE, trampoline_start(), trampolineStack, vmm_get_kernel_space(), and WRITE_64.

Referenced by smp_others_init().

◆ trampoline_send_startup_ipi()

void trampoline_send_startup_ipi ( cpu_t cpu,
cpuid_t  cpuId,
lapic_id_t  lapicId 
)

Sends the startup IPI to a CPU to start it up.

Parameters
cpuThe CPU structure to be initalized as the new CPU.
cpuIdThe ID to be assigned to the CPU to start.
lapicIdThe LAPIC ID of the CPU to start.

Definition at line 63 of file trampoline.c.

References atomic_store, CLOCKS_PER_SEC, cpuReadyFlag, hpet_wait(), lapic_send_init(), lapic_send_sipi(), PAGE_SIZE, TRAMPOLINE_ADDR, TRAMPOLINE_BASE_ADDR, TRAMPOLINE_CPU_ID_OFFSET, TRAMPOLINE_CPU_OFFSET, TRAMPOLINE_STACK_OFFSET, trampolineStack, and WRITE_64.

Referenced by smp_others_init().

◆ trampoline_start()

void trampoline_start ( void  )
extern

The start of the trampoline code, defined in trampoline.s.

Referenced by trampoline_init().

◆ trampoline_wait_ready()

uint64_t trampoline_wait_ready ( clock_t  timeout)

Waits for the currently starting CPU to signal that it is ready.

Parameters
timeoutThe maximum time to wait in clock ticks.
Returns
On success, 0. On timeout, ERR and errno is set.

Definition at line 75 of file trampoline.c.

References atomic_load, CLOCKS_PER_SEC, cpuReadyFlag, ERR, and hpet_wait().

Referenced by smp_others_init().