Hacker News

Понимание компилятора Go: компоновщик

Понимание компилятора Go: компоновщик Этот всесторонний анализ понимания предлагает детальное изучение его основной части — Mewayz Business OS.

1 минута чтения

Mewayz Team

Editorial Team

Hacker News

Понимание компилятора Go: компоновщик

Компоновщик Go — это заключительный этап цепочки инструментов компиляции Go, отвечающий за объединение скомпилированных объектных файлов в один исполняемый двоичный файл. Он разрешает ссылки на символы, назначает адреса памяти и создает автономную программу, которую операционная система может загружать и запускать без внешних зависимостей.

Для инженерных команд, создающих производственные системы, включая инфраструктуру, лежащую в основе таких платформ, как Mewayz и ее бизнес-операционную систему из 207 модулей, понимание того, что происходит на этапе связывания, имеет важное значение для написания производительного и развертываемого программного обеспечения.

Что на самом деле делает Go Linker?

В инструментальной цепочке Go компиляция происходит в два основных этапа. Сначала компилятор (gc) преобразует исходные файлы Go в объектные файлы, зависящие от архитектуры. Затем компоновщик (cmd/link) берет эти объектные файлы и объединяет их в готовый исполняемый файл. В то время как компилятор выполняет синтаксический анализ, проверку типов и генерацию кода, компоновщик выполняет пространственную и реляционную работу по сборке программы.

В ходе этого процесса компоновщик выполняет несколько важных операций. Он разрешает все ссылки на символы в пакетах, то есть каждый вызов функции или ссылка на переменную, пересекающая границу пакета, связывается с его фактической реализацией. Он назначает адреса виртуальной памяти каждой функции и глобальной переменной. Он также записывает окончательный двоичный файл в формате, ожидаемом целевой операционной системой — ELF для Linux, Mach-O для macOS или PE для Windows.

В отличие от компоновщиков C или C++, компоновщик Go полностью написан на Go. Это решение, принятое во время начальной загрузки Go 1.5, дает команде Go полный контроль над процессом связывания и устраняет зависимость от внешних цепочек инструментов для большинства сборок.

Чем компоновщик Go отличается от традиционных компоновщиков?

Традиционные компоновщики в экосистеме C/C++ — GNU ld, gold или lld LLVM — работают со стандартными форматами объектных файлов, такими как перемещаемые файлы ELF. Компоновщик Go использует собственный внутренний объектный формат, что придает ему гибкость, но также означает, что он существует в несколько изолированной экосистеме.

💡 ЗНАЕТЕ ЛИ ВЫ?

Mewayz заменяет 8+ бизнес-инструментов в одной платформе

CRM · Выставление счетов · HR · Проекты · Бронирование · eCommerce · POS · Аналитика. Бесплатный тариф доступен навсегда.

Начать бесплатно →

Статическое связывание по умолчанию: Go в большинстве случаев создает статически связанные двоичные файлы, встраивая всю среду выполнения и все зависимости в один файл. Это резко контрастирует с программами на языке C, которые обычно полагаются на динамические разделяемые библиотеки.

Никакого отдельного этапа предварительной обработки: компоновщик Go не требует отдельного прохода разрешения символов, как это делают традиционные двухпроходные компоновщики. Он обрабатывает пакеты в порядке зависимости, который уже определен компилятором.

Устранение мертвого кода: компоновщик агрессивно удаляет недоступные функции и переменные, что очень важно, поскольку стандартная библиотека Go велика. Без этого каждый двоичный файл будет нести вес неиспользуемых пакетов.

Интеграция среды выполнения: компоновщик Go должен встраивать среду выполнения Go, включая сборщик мусора, планировщик горутин и код управления стеком, в каждый двоичный файл. Эта ответственность не имеет прямого аналога в компоновке C.

Мост CGo: когда CGo включен, компоновщик Go должен координировать свои действия с системным компоновщиком C для обработки смешанных объектных файлов Go/C, что значительно усложняет процесс.

Ключевая идея: в философии дизайна компоновщика Go приоритет отдается простоте развертывания, а не скорости сборки. Создавая полностью статические двоичные файлы со встроенной средой выполнения, Go устраняет целую категорию производственных проблем — отсутствие общих библиотек, конфликты версий и разрешение зависимостей во время выполнения — за счет увеличения времени компоновки и увеличения размера двоичных файлов.

Почему производительность компоновщика была постоянной проблемой?

В течение многих лет компоновщик Go был одной из самых медленных частей процесса сборки. Поскольку он работает со всей программой сразу, а не с отдельными пакетами, его нельзя распараллелить так, как это делает компиляция. Команда Go вложила значительные средства в улучшения компоновщика, особенно в Go 1.15 и 1.16, в которых представлен новый формат объектных файлов и уменьшена память компоновщика.

Build Your Business OS Today

From freelancers to agencies, Mewayz powers 138,000+ businesses with 207 integrated modules. Start free, upgrade when you grow.

Create Free Account →

Попробуйте Mewayz бесплатно

Единая платформа для CRM, выставления счетов, проектов, HR и многого другого. Банковская карта не требуется.

Начните управлять своим бизнесом умнее уже сегодня.

Присоединяйтесь к 30,000+ компаниям. Бесплатный тариф навсегда · Без кредитной карты.

Нашли это полезным? Поделиться.

Готовы применить это на практике?

Присоединяйтесь к 30,000+ компаниям, использующим Mewayz. Бесплатный тариф навсегда — кредитная карта не требуется.

Начать бесплатный пробный период →

Готовы действовать?

Начните ваш бесплатный пробный период Mewayz сегодня

Бизнес-платформа все-в-одном. Кредитная карта не требуется.

Начать бесплатно →

14-дневный бесплатный пробный период · Без кредитной карты · Можно отменить в любой момент