需要帮助理解Linux内核的BIOS中断调用

3
我正在研究Linux源代码,以找出它如何获得内存映射。我认为它从调用detect_memory()函数开始,该函数在这里定义。此函数调用同一文件中定义的detect_memory_e820()。第48行的detect_memory_e820()调用intcall,其定义如下:
    .code16gcc
    .text
    .globl  intcall
    .type   intcall, @function
intcall:
    /* Self-modify the INT instruction.  Ugly, but works. */
    cmpb    %al, 3f
    je  1f
    movb    %al, 3f
    jmp 1f      /* Synchronize pipeline */
1:
    /* Save state */
    pushfl
    pushw   %fs
    pushw   %gs
    pushal

    /* Copy input state to stack frame */
    subw    $44, %sp
    movw    %dx, %si
    movw    %sp, %di
    movw    $11, %cx
    rep; movsd

    /* Pop full state from the stack */
    popal
    popw    %gs
    popw    %fs
    popw    %es
    popw    %ds
    popfl

    /* Actual INT */
    .byte   0xcd        /* INT opcode */
3:  .byte   0

    /* Push full state to the stack */
    pushfl
    pushw   %ds
    pushw   %es
    pushw   %fs
    pushw   %gs
    pushal

    /* Re-establish C environment invariants */
    cld
    movzwl  %sp, %esp
    movw    %cs, %ax
    movw    %ax, %ds
    movw    %ax, %es

    /* Copy output state from stack frame */
    movw    68(%esp), %di   /* Original %cx == 3rd argument */
    andw    %di, %di
    jz  4f
    movw    %sp, %si
    movw    $11, %cx
    rep; movsd
4:  addw    $44, %sp

    /* Restore state and return */
    popal
    popw    %gs
    popw    %fs
    popfl
    retl
    .size   intcall, .-intcall

我的问题是我无法确定这个时刻dx寄存器的值是多少:movw %dx, %si,也不知道它从哪里来。

1个回答

4
请注意,makefile指定了-mregparm=3用于编译16位C代码。这指示编译器如果可能的话将前三个参数放入寄存器eax, edxecx。因此,dx的值将成为第二个参数,即&iregs。还要注意下面进一步确认的注释:/* Original %cx == 3rd argument */ 我觉得你开始时没有问题,关于如何使al获得中断号的值:)

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接