bug-hurd
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[PATCH v2 1/2 gnumach] cpuboot: Fix percpu apboot_gdt for early gs


From: Damien Zammit
Subject: [PATCH v2 1/2 gnumach] cpuboot: Fix percpu apboot_gdt for early gs
Date: Tue, 17 Dec 2024 12:05:17 +0000

This allocates a constant space for percpu gdts
and copies the first entry to the nth entry on each cpu,
then patches its own copy of the gdt so it can function
independently.
---
 i386/i386/cpuboot.S | 63 ++++++++++++++++++++++++++++++++++++++-------
 1 file changed, 53 insertions(+), 10 deletions(-)

diff --git a/i386/i386/cpuboot.S b/i386/i386/cpuboot.S
index f93e0387..76ed907d 100644
--- a/i386/i386/cpuboot.S
+++ b/i386/i386/cpuboot.S
@@ -31,15 +31,19 @@
 #define BOOT_CS                0x8
 #define BOOT_DS                0x10
 
+#define GDT_DESCR_M32  4
+#define GDT_TABLE_M32  (14*2)
+
 .data
 
 .align 16
 apboot_idt_ptr:
        .long 0
 .align 16
+apboot_gdt_top:
        .word 0
 apboot_gdt_descr:
-       .word 14*8-1
+       .word (GDT_TABLE_M32 * 4) - 1
        .long apboot_gdt - KERNELBASE
 .align 16
 apboot_gdt:
@@ -101,6 +105,9 @@ apboot_percpu_med:
 apboot_percpu_high:
        .byte 0
 
+/* Empty space for per-cpu gdt descriptor and gdt */
+.space (NCPUS-1) * (GDT_DESCR_M32 + GDT_TABLE_M32) * 4, 0x0
+
 .globl apboot, apbootend, gdt_descr_tmp, apboot_jmp_offset
 .align 16
 .code16
@@ -159,28 +166,62 @@ apboot_jmp_offset:
        movw    %ax, %gs
        movw    %ax, %ss
 
-       /* Get CPU number */
+       /* Get CPU number into ebp */
        movl    $1, %eax
        cpuid
        shrl    $24, %ebx
-       movl    %cs:CX(cpu_id_lut, %ebx), %ecx
+       movl    %cs:CX(cpu_id_lut, %ebx), %ebp
+
+       /* Copy first gdt descriptor and gdt to cpu-th area */
+       movl    $(GDT_DESCR_M32 + GDT_TABLE_M32), %ecx
+       movl    $apboot_gdt_top, %esi
+       movl    %esi, %edi
+       movl    $((GDT_DESCR_M32 + GDT_TABLE_M32) * 4), %eax
+       mul     %ebp
+       addl    %eax, %edi
+       rep movsl
 
        /* Access per_cpu area */
-       movl    %ecx,%eax
+       movl    %ebp, %eax
        movl    $PC_SIZE,%ebx
        mul     %ebx
        addl    $percpu_array, %eax
 
        /* Record our cpu number */
-       movl    %ecx, (PERCPU_CPU_ID)(%eax)
+       movl    %ebp, (PERCPU_CPU_ID)(%eax)
 
        /* Set up temporary percpu descriptor */
        addl    $(-KERNELBASE), %eax
-       movw    %ax, apboot_percpu_low
-       shr     $16, %eax
-       movb    %al, apboot_percpu_med
-       shr     $8, %ax
-       movb    %al, apboot_percpu_high
+       movl    %eax, %ebx
+
+       /* Make eax hold offset to my cpus gdt */
+       movl    $((GDT_DESCR_M32 + GDT_TABLE_M32) * 4), %eax
+       mul     %ebp
+
+       /* Patch only our own copy of gdt */
+       movl    $apboot_percpu_low, %ecx
+       addl    %eax, %ecx
+       movw    %bx, (%ecx)
+       shr     $16, %ebx
+       addl    $2, %ecx
+       movb    %bl, (%ecx)
+       shr     $8, %bx
+       addl    $3, %ecx
+       movb    %bl, (%ecx)
+
+       /* Patch only our own copy of gdt descriptor */
+       movl    $apboot_gdt_descr, %ecx
+       addl    %eax, %ecx
+       movl    %ecx, %edx
+       addl    $2, %edx
+       movl    (%edx), %ebx
+       addl    %eax, %ebx
+       movl    %ebx, (%edx)
+
+       /* Reload our copy of gdt */
+       lgdtl   (%ecx)
+       ljmpl   $KERNEL_CS, $2f
+2:
 
        movw    $PERCPU_DS, %ax
        movw    %ax, %gs
@@ -213,8 +254,10 @@ apboot_jmp_offset:
        /* Finish the cpu configuration */
        call EXT(cpu_ap_main)
 
+3:
        /* NOT REACHED */
        hlt
+       jmp     3b
 
 .align 16
     .word 0
-- 
2.45.2





reply via email to

[Prev in Thread] Current Thread [Next in Thread]