Ошибка сегмента при вызове функции в asm

#linux #assembly #segmentation-fault #arm

#linux #сборка #ошибка сегментации #arm

Вопрос:

Я начал изучать вызов функции в ассемблере. Я следил за большим количеством руководств в Интернете и внес в него некоторые изменения.

Но на самом деле это работает не так, как ожидалось.

 .data
 hello:  .ascii "hello everyonen"
 len= . - hello
 .text

.global _start

exit:
       mov %r1,#0
       mov %r2,#0
       mov %r0, #0
       mov %r7, #1
       swi #0

println:
        mov %r7, #4
        swi #0
        mov %pc, %lr
        bx %r7
_start:
        ldr %r1, =hello
        ldr %r2, =len
        b println
        b exit
  

и вывод идет

 hello everyone
Segmentation fault
  

Я не знаю, где я был неправ.

Комментарии:

1. Для какой платформы предназначен этот код?

2. @ThomasJager: 32-разрядный ARM, с системными вызовами Linux, как вы можете видеть из тегов. Использование % декораторов для имен регистров необычно, но, по-видимому, поддерживается: arm-none-eabi-gcc -nostdlib arm.s собирает связывает его в двоичный файл.

Ответ №1:

Для вызовов функций используйте bl инструкцию (переход и ссылка). Это настраивает lr на то, чтобы содержать обратный адрес. Ваш код использует b (branch) вместо bl , поэтому lr он не настроен, и возврат из println происходит по непредсказуемому адресу, что, вероятно, приводит к сбою вашей программы.

Чтобы исправить это, используйте bl вместо b для вызовов функций:

     bl println
    bl exit