---
title: "🪵 Компиляция cтатических бинарников с помощью TinyCC"
date: 2023-07-30T13:52:57+03:00
draft: false
tags: [c, tips]
---

## Введение

Нерушимой истинной является факт,
что для cтатической компиляции компилятору необходимо добавить флаг `-static`
и указать необходимые библиотеки через параметр `-l`,
список которых отличается от динамической компиляции.

Однако для **tcc** это не работает.

## Компиляция cтатических исполныемых файлов

На примере библиотеки **SQLite3** покажу как компилировать статическую программу.

Для получения списка библиотек воспользуемся инструментом **pkg-config**.

```text
$ pkg-config --libs sqlite3
-lsqlite3
```

Для статической компиляции список библиотек будет немного больше.

```text
$ pkg-config --libs --static sqlite3
-lsqlite3 -lm -lz
```

В итоге получается, что для GCC/Clang команда компиляции будет выглядеть следующим образом.

```sh
gcc -static -Wall -O3 -o ${file%.*} $file `pkg-config --libs --static sqlite3`
```

Мне казалось очевидным, что для TCC дела обстоят таким же образом,
однако не тут то было.

## -static в TCC

На страницы документации к **TCC** (https://bellard.org/tcc/tcc-doc.html)
указана опция `-static`.

Цитата из документации:

```text
-static
    Generate a statically linked executable (default is a shared linked executable).
```

Запустив `tcc` с параметром `-hh`, который выводит расширенную справку,
можно заметить, что в описании к параметру `-static`
написано **не рекомендуется к использованию**.

Цитата из справки:

```text
-static    link to static libraries (not recommended)
```

В моём случае при компиляции прогаммы с параметром `-static` компилятор возвращает
ошибку сегментации.

## Статическая компилция в TCC

Чтобы скомпилировать в **tcc** программу статически,
необходимо напрямую передать компилятору `*.a` файлы.

```sh
tcc -Wall -O3 -o ${file%.*} -I$C_INCLUDE_PATH $file $LIBRARY_PATH/libname.a
```

## Дополнительно

Хочу упомянуть, что **tcc** не поддерживает переменные окружения
`C_INCLUDE_PATH` или `CPATH` и `LIBRARY_PATH`,
с помощью которых можно задать пути для заголовочных файлов и файлов библиотек.

Для **tcc** необходимо задавать каталоги стандартным способом, через параметры `-I` и `-L`.

## Ресурсы
* [Re: [Tinycc-devel] Is static linking functional?](https://mail.gnu.org/archive/html/tinycc-devel/2014-06/msg00028.html)
* [Tiny C Compiler Reference Documentation](https://bellard.org/tcc/tcc-doc.html)
