Встроенная сборка - Синтаксис AT & T - Как перейти к переменной - PullRequest
1 голос
/ 06 декабря 2011

Итак, я работаю над пещерой кода, где я в основном заменяю вызов _memcpy своим прыжком, а затем хочу сохранить то, что находится в исходном коде.Оригинальная сборка:

mov     [esp+8], edx    ; size
mov     [esp+4], eax    ; ptr to source
mov     eax, [ebp+arg_4]
mov     [esp], eax      ; ptr to destination
call    _memcpy

Я борюсь с синтаксисом этого для AT & T, в основном я хочу хранить [esp + 8], [esp + 4] и [esp] в моих собственных переменных.Я пытаюсь сделать это следующим образом:

void codecave_jump( void ) __attribute__ ( ( signal, naked ) );
void codecave_jump( void ){

    void *destination, *source;
    size_t size;

    // push all registers onto the stack
    __asm__("pushal\n\t");

    // get size
     __asm__ __volatile__(
            "movl 8(%ecx), %0\n\t" : "=g" (size)
            );

    // get source
    __asm__ __volatile__(
            "movl 4(%ecx), %0\n\t" : "=g" (source)
            );

    // get destination
    __asm__ __volatile__(
            "movl %%eax, %0\n\t" : "=g" (destination)
            );

    // restore all of our registers
    __asm__("popal\n\t");

    // call memcpy
    __asm__("call __memcpy\n\t");

    // do the copy
    memcpy(destination, source, size);
}

И я получаю следующую ошибку: ошибка: отсутствует номер операнда после% -letter error: отсутствует номер операнда после% -letter

В основном это кричит на меня: "movl 8 (% ecx),% 0 \ n \ t": "= g" (размер)

Кто-нибудь знает, как я должен делать это правильно вСинтаксис AT & T?Я очень скучаю по синтаксису Intel в OS X: /

1 Ответ

1 голос
/ 06 декабря 2011

Поскольку в результирующем коде AT & T используются знаки процента для имен регистров, необходимо использовать двойные знаки процента для имен регистров при наличии таких операндов, как size:

"movl 8(%%ecx), %0\n\t" : "=g" (size)

Это похоже на то, как иногда вам нужны двойные знаки процента для printf.Похоже, вы поняли это правильно для %%eax, я предполагаю, что строка компилируется нормально.


Для mov mem32, mem32 нет кода операции.Сначала вам нужно будет переместить данные в регистр, а затем переместить их в область памяти (как в версии Intel для destination)

// get size
__asm__ __volatile__(
    "movl 8(%ecx), %eax\n\t"
    );
__asm__ __volatile__(
    "movl %%eax, %0\n\t" : "=g" (size)
    );

Для записи: я также нахожуСинтаксис AT & T невероятно запутан.:)

...