汇编:增加2(或更大数字)而不破坏ADC循环中的CF?

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了汇编:增加2(或更大数字)而不破坏ADC循环中的CF?相关的知识,希望对你有一定的参考价值。

我试图在Windows中测试TDM-GCC 64位汇编中的附加功能。我在前一段时间搜索了资源,我遇到了类似的代码(我做了一些修改,在TDM-GCC中编译它)。

typedef struct
{
    int size;
    __uint64_t uints[130];
} BigInteger;

void add(BigInteger *X, BigInteger *Y);   // X += Y
    // %rcx holds address of X, and %rdx holds address of Y apparently.

    // calc.s - assembly file
    .globl add
add:
    movq    8(%rdx), %rax
    addq    %rax, 8(%rcx)
    movq    16(%rdx), %rax
    adcq    %rax, 16(%rcx)
    movq    24(%rdx), %rax
    adcq    %rax, 24(%rcx)
    ...     ...

第一个汇编代码有效。不利的是,只要计算最大尺寸就需要很小的数字。所以我改为检查X和Y的大小并设置一个大小条件的循环,这样如果X和Y不大,它就不会总是添加整个数组。

    ...
// %r13 holds X addr, %r14 holds Y addr.
    addq    $8, %r13   // I have tried  incq %r13
    addq    $8, %r14   // I have tried  incq %r14
    movq    (%r14), %rax
    addq    %rax, (%r13)
    decl    %ecx
    cmpl    $0, %ecx
    je      .add4
.add3:
    addq    $8, %r13   // I have tried  incq %r13
    addq    $8, %r14   // I have tried  incq %r14
    movq    (%r14), %rax
    adcq    %rax, (%r13)
    loop    .add3
.add4:
    ...

但是我太简单了,不能认为使用ADDQ运算符向X和Y的地址(%r13,%r14)添加8个字节可以迭代数组。这里的问题是,如果我像这样使用ADDQ运算符,它会将进位标志重置为0,因此使用进位(.add3)计算加法的整个循环会中断。我试过用

    incq %r13

思考incq的工作方式类似于在C ++中递增一个指针,它知道它应该移动多少字节。但这只是增加寄存器值1,而不是8我认为它会移动。

所以我的问题是:汇编中是否有一种方法可以将寄存器增加大于1的数字,或者在不触及进位标志的情况下进行加法? (不添加,adc,因为它们都在最后设置进位标志)

答案

使用带有寄存器+偏移的加载有效地址

        lea     rax,[rax+8]    ;add 8 to rax

以上是关于汇编:增加2(或更大数字)而不破坏ADC循环中的CF?的主要内容,如果未能解决你的问题,请参考以下文章

装配ADC(随附进位)到C ++

C 汇编循环

循环用户输入直到满足条件

汇编语言,检查数字是不是可被 2 整除并在循环中打印数字的程序

张量流条件:检查张量内的值是否为零或更大

viewcontroller 中的 tableview 将宽度扩展到 ipad(或更大的屏幕设备)