Перейти к основному содержимому

Несколько модулей и линковка

Разработчику

Контекст: NASM → объектный файл ELF → ld или gcc. Linux x86-64. См. Первая программа про цепочку сборки.

Несколько модулей - линковка объектников

Один огромный .asm трудно сопровождать. Разделение по смыслу:

  • main.asm — точка входа, системные вызовы;
  • math.asm — вычисления;
  • io.asm — вывод/ввод;
  • macros.inc — только макросы (%include), без объектного кода.

Каждый .asm с кодом собирается в отдельный .o. Линкер склеивает объектники и разрешает ссылки «вызвать символ из другого файла».


Экспорт и импорт символов

Экспорт — метка видна снаружи модуля:

; math.asm
section .text
global add_u64

add_u64:
mov rax, rdi
add rax, rsi
ret

Импорт — используем чужую метку:

; main.asm
section .text
global _start
extern add_u64

_start:
mov rdi, 100
mov rsi, 23
call add_u64 ; rax = 123
; ...

Правила имен:

  • global имя — в одном модуле определение (реализация).
  • extern имя — объявление «определено в другом .o».
  • Точка входа «голой» программы без libc: global _start и линковка с _start как entry (см. ниже).

Сборка и линковка

nasm -f elf64 math.asm -o math.o
nasm -f elf64 main.asm -o main.o
ld math.o main.o -o app

Или через GCC как драйвер линкера (удобно, если позже подключите C):

gcc -nostdlib math.o main.o -o app

-nostdlib — без crt0 и libc; для чистого _start + syscall.

Порядок .o для ld обычно не критичен, если все символы разрешены. Неопределённый символ — ошибка линкера «undefined reference».


Данные в разных модулях

Строку можно держать в io.asm:

; io.asm
section .data
global msg
msg db 'OK', 10
msg_len equ $ - msg

В main.asm:

extern msg
extern msg_len ; константа equ не экспортируется как символ — msg_len лучше
; передавать через отдельный global или вычислять в main

equ не создаёт символ в объектнике. Для экспорта длины используют global msg_len и msg_len: dq $ - msg или функцию get_msg_len.


%include и отдельный .o

МеханизмРезультат
%include "file.asm"один объектный файл, общая область меток
отдельный .asm + global/externнесколько .o, инкапсуляция, переиспользование

Макросы и константы — в .inc с %include. Подпрограммы с фиксированным ABI — в отдельных .asm.


Статические библиотеки (кратко)

ar rcs libmath.a math.o
gcc -nostdlib main.o -L. -lmath -o app

ar упаковывает .o в архив; линкер вытаскивает нужные объектники по неразрешённым символам.


Типичные ошибки линковки

ОшибкаПричина
duplicate symbolglobal на одно имя в двух .asm
undefined reference to _startнет global _start или не тот файл первым
Разные -f elf32 / elf64смешение 32- и 64-битных объектников
Вызов без совпадения ABIаргументы не в rdi/rsi/... — см. подпрограммы

Дальше

Стык с кодом на C — взаимодействие с C. Разбор готового бинарника — чтение листинга.


См. также

Другие статьи этого же раздела в боковом меню (как на странице «О разделе»).