3

我正在 x86 上学习汇编,遇到了一个代码,它实际上将存储所有未初始化变量的 bss 部分归零

    ;Zero the bss
     movw    $__bss_start, %di
     movw    $_end+3, %cx
     xorl    %eax, %eax
     subw    %di, %cx
     shrw    $2, %cx
     rep; stosl

但不确定这段代码是如何工作的。谁能告诉我这里的情况如何,第一条指令将 bss 段的地址存储到 di 寄存器,但最后三条指令的目的是什么?

4

2 回答 2

9

Something like this;

 ;Zero the bss
 movw    $__bss_start, %di  ; Get start of BSS in %di register
 movw    $_end+3, %cx       ; Get end of BSS in %cx register
 xorl    %eax, %eax         ; Clear %eax 
 subw    %di, %cx           ; Calculate size of BSS (%cx-%di) to %cx
 shrw    $2, %cx            ; Divide %cx by 4
 rep stosl                  ; Repeat %cx times, store %eax (4 bytes of 0) at 
                            ; address %di and increase %di by 4.

On the rep stosl;

  • rep is a repeat prefix that will repeat the following instruction (out of a limited set) %cx times.
  • stosl stores the value of %eax at the address pointed to by %(e)di, and increases %e(di) by the size of %eax.

As an example, rep stosl with %eax set to 0, %edi set to 0x4000 and %cx set to 4, will set the memory from 0x4000 to %0x4010 to zero.

于 2013-07-08T12:27:44.017 回答
1

神奇的是rep; stoslstosl将 4 个字节eax存储到 指向的内存中edi并递增edi4。rep前缀导致该指令重复,直到 in 计数器ecx达到零,并且每次ecx递减 1。

所以我们需要做的就是将 .bss 段的地址放入edi(第一条指令),将 4 字节的字数放入.bss 中ecx。这只是(bss_start - bss_end) >> 2,由其余指令计算得出。

于 2013-07-09T12:51:15.393 回答