Форум программистов, компьютерный форум, киберфорум
Наши страницы
Assembler: MASM64, х64/long mode
Войти
Регистрация
Восстановить пароль
 
Рейтинг 4.50/6: Рейтинг темы: голосов - 6, средняя оценка - 4.50
mkostoevr
Незнайка
26 / 11 / 2
Регистрация: 14.10.2016
Сообщений: 373
Записей в блоге: 2
1

GCC сгенерировал ассемблерный листинг программы. Не пойму, что делают некоторые его части

29.10.2017, 21:42. Просмотров 1245. Ответов 7
Метки нет (Все метки)

Здравия всем!

Сгенерил листинг такого файла:

C
1
2
3
4
5
6
int main(int argc, char** argv)
{
    argc = 1;
    argv[0][0] = '*';
    return 0;
}
Получился такой ассемблерный код:

Assembler
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
main:
    pushq   %rbp            # сохранить RBP
    movq    %rsp, %rbp      # Сохранить стек в RBP, чтобы было легче с ним работать
 
    movl    %edi, -4(%rbp)  # ???
    movq    %rsi, -16(%rbp) # ???
    
    movl    $1, -4(%rbp)    # argc = 1;
    
    movq    -16(%rbp), %rax # поместить адрес переменной argc в стеке в RAX 
    movq    (%rax), %rax    # ???
    movb    $42, (%rax)     # argv[0][0] = '*';
    
    movl    $0, %eax        # return 0;
    
    popq    %rbp            # восстановить RBP
    ret                     # returnn 0;
Объясните, пожалуйста, неучу, что делают команды, обозначенные тремя вопросительными знаками? (зачем они нужны?)
0
Лучшие ответы (1)
QA
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
29.10.2017, 21:42
Ответы с готовыми решениями:

Ассемблерный листинг
Подскажите, пожалуйста, что в ассемблерных листингах такого типа (ниже) означают 1й и 2й столбцы?...

Ассемблерный листинг
Как мне посмотреть ассемблерный листинг программы на СИ? Подскажите, пожалуйста. Много чего...

нужно пояснение по части из курсовой связанной с записями и массивами, напротив вопросов дать пояснение что операторы делают или строчки программы
лучше если конечно дадите по строчное определение что делает программа тут program Cntrl; uses...

Получить ассемблерный листинг из кода на с++
Здравствуйте! Требуется написать программу на ассемблере, которая бы занималась неким...

Можно ли директивой #pragma получить ассемблерный листинг?
Собственно, сабж. Не могу найти соответствующую функцию у #pragma. Есть она? Ключи компиляции уж...

7
Jin X
6711 / 1499 / 174
Регистрация: 14.12.2014
Сообщений: 2,903
Записей в блоге: 11
Завершенные тесты: 3
29.10.2017, 23:57 2
movl %edi, -4(%rbp) - это mov [rbp-4],edi
movq %rsi, -16(%rbp) - это mov [rbp-16],rsi
movq (%rax), %rax - это mov rax,[rax]

Добавлено через 6 минут
Не знаю почему такие странные смещения ([rbp-4]), по идее должно быть [rbp+16] для первого параметра (argc).
0
mkostoevr
Незнайка
26 / 11 / 2
Регистрация: 14.10.2016
Сообщений: 373
Записей в блоге: 2
30.10.2017, 16:44  [ТС] 3
Jin X, в том и дело:

Зачем пихать в адрес первой переменной значение регистра edi?
Зачем пихать в адрес второй переменной (argv, я там при комментировании ошибся) значение регистра rsi?

А с movq (%rax), %rax я разобрался, там в rax пихается адрес указателя на массив первого аргумента, на который ссылается указатель на указатель char** argv.

Не по теме:

Цитата Сообщение от Jin X Посмотреть сообщение
Не знаю почему такие странные смещения ([rbp-4]), по идее должно быть [rbp+16] для первого параметра (argc).
Кстати, а это вопрос... Действительно, начиная с rbp и кончая [rbp+7] должен быть адрес, куда возвратит функцию команда ret.

Или нет... А шут его знает, я матан в школе прогуливал.

0
Jin X
6711 / 1499 / 174
Регистрация: 14.12.2014
Сообщений: 2,903
Записей в блоге: 11
Завершенные тесты: 3
30.10.2017, 22:49 4
Цитата Сообщение от mkostoevr Посмотреть сообщение
Зачем пихать в адрес первой переменной значение регистра edi?
Адрес первой переменной [rbp+16], а не [rbp-4]. Последнее – это локальная переменная, вот только почему-то sub rsp,... я не вижу.

[rbp] содержит сохранённое значение rbp (байты от [rbp+0] по [rbp+7], если можно так выразиться).
[rbp+8] – адрес возврата (байты от [rbp+8] по [rbp+15], если можно так выразиться).
[rbp+16] – первый параметр.
[rbp+24] – второй параметр.
1
30.10.2017, 22:49
Братец Кролик
28 / 35 / 8
Регистрация: 16.10.2017
Сообщений: 137
01.11.2017, 16:40 5
Лучший ответ Сообщение было отмечено mkostoevr как решение

Решение

Цитата Сообщение от Jin X Посмотреть сообщение
вот только почему-то sub rsp,... я не вижу.
Компилятор использует красную зону.
mkostoevr,
По поводу тех двух инструкций. Имя переменной внутри функции - это локальная копия переданного параметра. Поэтому:
Assembler
1
2
    movl    %edi, -4(%rbp)  # инициализация локальной копии argc переданным параметром #1
    movq    %rsi, -16(%rbp) # инициализация указателя argv, который - локальная копия переданного указателя.
Добавлено через 4 минуты
Цитата Сообщение от mkostoevr Посмотреть сообщение
Зачем пихать в адрес первой переменной значение регистра edi?
edi - это argc. argc внутри функции - это новая переменная внутри функции. Ее нужно инициализировать переданным значением. Что и можно наблюдать с отключенной оптимизацией.

Добавлено через 4 минуты
Цитата Сообщение от Jin X Посмотреть сообщение
[rbp+16] – первый параметр.
[rbp+24] – второй параметр.
В x64 первые параметры идут в регистрах, а не в стеке. Первый параметр в rdi, второй в rsi. Поэтому в самом начале функции из регистров, компилятор их раскладывает в локальные переменные в красной зоне.
2
Jin X
6711 / 1499 / 174
Регистрация: 14.12.2014
Сообщений: 2,903
Записей в блоге: 11
Завершенные тесты: 3
01.11.2017, 18:29 6
Цитата Сообщение от Братец Кролик Посмотреть сообщение
В x64 первые параметры идут в регистрах, а не в стеке.
Точно! Это ж 64 бита, да ещё и Linux...
Но "оптимизация" тут стрёмная. Ибо...
Цитата Сообщение от Братец Кролик Посмотреть сообщение
компилятор их раскладывает в локальные переменные в красной зоне
тут лишнее...

Цитата Сообщение от Братец Кролик Посмотреть сообщение
Компилятор использует красную зону.
А вот в винде такого понятия нет... интересно.
Хотя я сейчас потестил – в винде использование "красной зоны" тоже работает без проблем (до 64 Kb). Что в 98 или NT, что в 7-ке...
0
Вложения
Тип файла: zip RedZoneTest.zip (1.0 Кб, 1 просмотров)
Братец Кролик
28 / 35 / 8
Регистрация: 16.10.2017
Сообщений: 137
01.11.2017, 19:24 7
Цитата Сообщение от Jin X Посмотреть сообщение
Но "оптимизация" тут стрёмная.
Она не стремная, она просто отключена

Добавлено через 13 минут
Цитата Сообщение от Jin X Посмотреть сообщение
Хотя я сейчас потестил – в винде использование "красной зоны" тоже работает без проблем (до 64 Kb). Что в 98 или NT, что в 7-ке...
Это не красная зона, просто стек. Там нет никаких гарантий, что эта память не мутабельна. В отличие от линукса, где это сделано специально в целях оптимизации и теоретически гарантируется, что никакой обработчик прерывания эту область менять не будет. В винде есть другая особенность - это область под регистры (4 х 8), которая выделяется перед вызовом функции. Когда я о ней не знал, крешей наловил
1
Jin X
6711 / 1499 / 174
Регистрация: 14.12.2014
Сообщений: 2,903
Записей в блоге: 11
Завершенные тесты: 3
01.11.2017, 19:47 8
Цитата Сообщение от Братец Кролик Посмотреть сообщение
Она не стремная, она просто отключена
Тем не менее, красная зона используется. По сути, она для оптимизации и создана, так это можно назвать некоей минимальной оптимизацией

Цитата Сообщение от Братец Кролик Посмотреть сообщение
Это не красная зона, просто стек. Там нет никаких гарантий, что эта память не мутабельна.
Гарантий нет, just эксперимент показывает... но понятно, что в серьёзных приложениях лучше так не делать.

Цитата Сообщение от Братец Кролик Посмотреть сообщение
В винде есть другая особенность - это область под регистры (4 х 8)
Это только в 64 битах. Но удобно для функций типа printf
И всё же, красная зона была бы неплохим решением в некоторых случаях, даже несмотря на то, что у нас и так есть аж 7 регистров (rax, rcx, rdx, r8-r11), не считая 6 шт xmm/ymm/zmm (ну и st, конечно же), которые можно спокойно использовать для любых нужд без предохранения...
1
01.11.2017, 19:47
Answers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
01.11.2017, 19:47

Не понятны некоторые части часть программы
class Triangle { double area; int height; int length; public static void main(String args) {...

Объяснить что делают строчки программы
битый час ломаю голову, но не могу понять что делают эти строчки. кто знает ,поделитесь плз...

Подскажите, пожалуйста, что такое листинг программы?
Подскажите, пожалуйста, что такое листинг программы?


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
8
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2019, vBulletin Solutions, Inc.
Рейтинг@Mail.ru