First, download the package from:

http://biznetnetworks.dl.sourceforge.net/project/tboot/tboot/20090330/tboot-20090330.tar.gz

>From tboot/common/boot.S (noticed the begin_launch):


/* entry point post-launch, to verify memory layout */
/* (must all be w/in one page; since _start is page-aligned, it will be; */
/* which is why we can't call much other code (e.g. printk, TPM fns, etc.) */
ENTRY(_post_launch_entry)
    /* verify phys addr we were entered at is the one we expected
     * ebx contains the phys addr of the entry point
     */
    cmp $_post_launch_entry, %ebx
    jne layout_err

    /* verify last entry in MLE page table is the one we expected
     * this is sufficient because: 1) all addrs must be phys increasing
     * and 2) tboot is phys contig--therefore if any page were moved to
     * a different phys addr then the last page would have to be different
     * from tboot's last page
     */
    /* get addr of MLE page table from OsSinitData */
                              /* start of TXT heap (== BiosDataSize) */
    mov (TXT_PRIV_CONFIG_REGS_BASE + TXTCR_HEAP_BASE), %eax
    add (%eax), %eax                   /* skip BiosData */
    add (%eax), %eax                   /* skip OsMleData */
    mov (MLE_PGTBL_OFF+8)(%eax), %eax  /* addr of MLE page table */
    /* get to page table itself (there is only one for tboot) */
    mov (%eax), %eax          /* pgdir ptr -> pgdir */
    and $PAGE_MASK, %eax
    mov (%eax), %eax          /* pgdir -> pgtbl */
    and $PAGE_MASK, %eax
    /* find last page (pte) */
    mov $_mle_end, %ecx
    sub $_mle_start, %ecx     /* size of MLE */
    shr $PAGE_SHIFT-3, %ecx
    sub $8, %ecx              /* size/4k*8 is offset+1 of last pte */
    add %ecx, %eax
    mov (%eax), %eax          /* pte of last page */
    and $PAGE_MASK, %eax
    /* calc expected addr of last page */
    mov $(_mle_end - 1), %ebx /* addr of last byte of MLE... */
    and $PAGE_MASK, %ebx      /* ...rounded to page start */
    /* are they equal? */
    cmp %ebx, %eax
    je __start                /* yes, so continue with normal launch */
   
layout_err:       /* layout check failed so TXT RESET */
                     /* set a special error code */
    movl $LAYOUT_ERR, (TXT_PRIV_CONFIG_REGS_BASE + TXTCR_ERRORCODE)
                     /* unlock memory config (and serialize) */
    movl $1, (TXT_PRIV_CONFIG_REGS_BASE + TXTCR_CMD_UNLOCK_MEM_CONFIG)
    movl (TXT_PRIV_CONFIG_REGS_BASE + TXTCR_STS), %eax
                     /* TXT RESET */
    movl $1, (TXT_PRIV_CONFIG_REGS_BASE + TXTCR_CMD_RESET)
    mov $6, %eax
    mov $0xcf9, %edx
    out %al, (%dx)   /* for debug chipsets where TXT RESET may not work */
    ud2


ENTRY(__start)
        /* Set up a few descriptors: on entry only CS is guaranteed good. */
        lgdt    %cs:gdt_descr
        mov     $(ds_sel),%ecx
        mov     %ecx,%ds
        mov     %ecx,%es
        mov     %ecx,%fs
        mov     %ecx,%gs
        mov     %ecx,%ss
        ljmp    $(cs_sel),$(1f)
1:    leal    bsp_stack,%esp

        /* Reset EFLAGS (subsumes CLI and CLD). */
        pushl   $0
        popf

        /* Initialize BSS (no nasty surprises!) */
        mov     $__bss_start,%edi
        mov     $_end,%ecx
        sub     %edi,%ecx
        xor     %eax,%eax
        rep     stosb

        /* Load IDT */
        lidt    idt_descr

        /* enable MCE */
        mov     %cr4,%eax
        or      $X86_CR4_MCE,%eax
        mov     %eax,%cr4

        /* pass multiboot info struct and call measured launch code */
        push    %ebx
        call    begin_launch
        ud2

/*
 * vmexit handler
 */
ENTRY(vmx_asm_vmexit_handler)
        call vmx_vmexit_handler
    /* fall through to loop if callee returns (shouldn't happen) */

ENTRY(_mini_guest)
1:    pause
    cmp $0, (aps_exit_guest)
    je 1b
    /* VMCALL out of guest */
    .byte 0x0f,0x01,0xc1
    jmp 1b

#include "shutdown.S"

/*
 * entry point for GETSEC[WAKEUP]
 */
ENTRY(_txt_wakeup)
    # prepare this thread for C code
        /* Set up a few descriptors: on entry only CS is guaranteed good. */
        lgdt    %cs:gdt_descr
        mov     $0x10, %ecx
        mov     %ecx, %ds
        mov     %ecx, %es
        mov     %ecx, %fs
        mov     %ecx, %gs
        mov     %ecx, %ss
        ljmp    $(cs_sel), $(1f)

        /* Load IDT */
1:    lidt    idt_descr

        /* enable MCE */
        mov     %cr4,%eax
        or      $X86_CR4_MCE,%eax
        mov     %eax,%cr4

    # get initial APIC ID for this processor
    mov    $0x01, %eax
    xor    %ebx, %ebx
    cpuid
    shr    $24, %ebx

    # set stack as id-based offset from AP stack base
    # "truncate" if too big (txt_cpu_wakeup() will handle failure)
    # so that we at least have a stack (even if shared with another AP)
    cmp    $NR_CPUS, %ebx
    jl    2f
    mov    $NR_CPUS-1, %ebx
2:    mov    $AP_STACK_SIZE, %eax
    mul    %ebx
    sub    $AP_STACK_SIZE, %eax
    mov    $ap_stacks, %ecx
    sub    %eax, %ecx
    mov    %ecx, %esp

    call    txt_cpu_wakeup


/*
 * entry point for switch to real mode and jump
 * entry point in %ebx
 */
ENTRY(_prot_to_real)
    /* disable interrupts */
    cli
    mov     0x4(%esp), %ebx

    /* deal with parameter, real mode program entry point */
    mov     %ebx, %eax
    and     $0xffff0, %eax
    shr     $4, %eax
    mov     %ax, _real_mode_entry_point + 4
    and     $0xfff0000f, %ebx
    mov     %ebx, _real_mode_entry_point

    /* load proper segments for real mode */
    mov     $(ds16_sel), %ax
    mov     %ax, %ds
    mov     %ax, %es
    mov     %ax, %fs
    mov     %ax, %gs
    mov     %ax, %ss
    lidt    real_idt_desc
    xor     %eax, %eax
    ljmp    $(cs16_sel), $(1f)

    .code16
1:    mov     %eax, %cr0
    mov     $0x0, %ax
    mov     %ax, %ds
    mov     %ax, %es
    mov     %ax, %fs
    mov     %ax, %gs
    mov     %ax, %ss

    .code32

    DATA16
    ADDR16
    ljmp    *_real_mode_entry_point

/*
 * interrupt handler
 */

int_handler:
    call handle_exception
    ud2

/*
 * descriptors and descriptor tables
 */

    .align 8

/* GDT */
gdt_descr:
    .word    gdt_table_end - gdt_table - 1
    .long    gdt_table

        .align PAGE_SIZE, 0

ENTRY(gdt_table)
        /* unused */
        .quad    0x0000000000000000
cs_descr:    /* cs */
    .word    0xffff        /* limit = 4GB */
    .word    0x00        /* base = 0 */
    .word    0x9b00        /* read + exec + accessed */
    .word    0x00cf        /* granularity = 4096 */
ds_descr:    /* ds */
    .word    0xffff        /* limit = 4GB */
    .word    0x00        /* base = 0 */
    .word    0x9300        /* read + write + accessed */
    .word    0x00cf        /* granularity = 4096 */
tss_descr:    /* tss */
    .word    0xffff        /* limit = 4GB */
    .word    0x00        /* base = 0 */
    .word    0x8900        /* system segment, 32b available TSS */
    .word    0x008f        /* granularity = 4096 */
cs16_desc:    /* cs16 */
    .word    0xffff        /* limit = 4GB */
    .word   0x0000      /* base = 0 */
    .word   0x9b00      /* read + exec + accessed */
    .word    0x008f      /* granularity = 4096, D = 0 */
ds16_desc:  /* ds16 */
    .word   0xffff      /* limit = 4GB */
    .word   0x0000      /* base = 0 */
    .word   0x9300      /* read + exec + accessed */
    .word   0x008f      /* granularity = 4096, D = 0 */
        /* end (unused) */
    .quad   0x0000000000000000
ENTRY(gdt_table_end)

/* IDT */
idt_descr:
    .word    idt_table_end - idt_table - 1
    .long    idt_table

    .align    8

idt_table:
    .rept 18
        .word    int_handler - _start
        .word    cs_sel
        .word    0x8e00   /* present, DPL=0, 32b, interrupt */
        .word    (int_handler - _start + TBOOT_BASE_ADDR) >> 16
    .endr
    /* for machine-check exception */
        .word    int_handler - _start
        .word    cs_sel
        .word    0x8f00   /* present, DPL=0, 32b, trap */
        .word    (int_handler - _start + TBOOT_BASE_ADDR) >> 16
    .rept 237
        .word    int_handler - _start
        .word    cs_sel
        .word    0x8e00   /* present, DPL=0, 32b, interrupt */
        .word    (int_handler - _start + TBOOT_BASE_ADDR) >> 16
    .endr
idt_table_end:

/* Real Mode IDT */
real_idt_desc:
    .word   0x03ff
    .long   0

#include "wakeup.S"

Reply via email to