Данные
Возьмем типичный фонт для графической библиотеки, например AdafruitGFX. Обычно это файл с расширением .h и содержащий внутри исходный код С/С++, описывающий нужные структуры данных (пример, FreeSerifItalic9pt7b.h
: )
const uint8_t FreeSerifItalic9pt7bBitmaps[] PROGMEM = {
0x11, 0x12, 0x22, 0x24, 0x40, 0x0C, 0xDE, 0xE5, 0x40, 0x04, 0x82, 0x20,
0x98, 0x24, 0x7F, 0xC4, 0x82, 0x23, 0xFC, 0x24, 0x11, 0x04, 0x83, 0x20,
0x1C, 0x1B, 0x99, 0x4D, 0x26, 0x81, 0xC0, 0x70, 0x1C, 0x13, 0x49, 0xA4,
...
0x28, 0x18, 0x08, 0x08, 0x08, 0x18, 0x00, 0x3F, 0x42, 0x04, 0x08, 0x10,
0x20, 0x40, 0x72, 0x0E, 0x08, 0x61, 0x04, 0x30, 0x86, 0x08, 0x61, 0x04,
0x30, 0xC3, 0x8F, 0x00, 0xFF, 0xF0, 0x1E, 0x0C, 0x10, 0x20, 0xC1, 0x82,
0x04, 0x1C, 0x30, 0x40, 0x83, 0x04, 0x08, 0x20, 0x60, 0x99, 0x8E };
const GFXglyph FreeSerifItalic9pt7bGlyphs[] PROGMEM = {
{ 0, 0, 0, 5, 0, 1 }, // 0x20 ' '
{ 0, 4, 12, 6, 1, -11 }, // 0x21 '!'
{ 6, 5, 4, 6, 3, -11 }, // 0x22 '"'
{ 9, 10, 12, 9, 0, -11 }, // 0x23 '#'
{ 24, 9, 15, 9, 1, -12 }, // 0x24 '$'
{ 41, 14, 12, 15, 1, -11 }, // 0x25 '%'
...
{ 1100, 9, 8, 8, -1, -7 }, // 0x78 'x'
{ 1109, 9, 12, 9, 0, -7 }, // 0x79 'y'
{ 1123, 8, 9, 7, 0, -7 }, // 0x7A 'z'
{ 1132, 6, 15, 7, 1, -11 }, // 0x7B '{'
{ 1144, 1, 12, 5, 2, -11 }, // 0x7C '|'
{ 1146, 7, 16, 7, 0, -12 }, // 0x7D '}'
{ 1160, 8, 3, 10, 1, -5 } }; // 0x7E '~'
const GFXfont FreeSerifItalic9pt7b PROGMEM = {
(uint8_t *)FreeSerifItalic9pt7bBitmaps,
(GFXglyph *)FreeSerifItalic9pt7bGlyphs,
0x20, 0x7E, 22 };
// Approx. 1835 bytes
Точное содержание и даже формат файла нам сейчас не важны.
Обычно такие файлы используют так - включают в проект строчку
#include "FreeSerifItalic9pt7b.h"
и далее обращаются к структурам и отдельным полям как переменным программы.
Проблема
Предположим мы хотим не использовать фонты в программе, а отредактировать их содержимое. Если файлов один или два, проще всего было бы написать С++ код, который подключает нужные фонты, меняет их данные и сохраняет отредактированные структуры в таком же формате. Но в результате нам придется компилировать код с каждым фонтом отдельно. А что делать если файлов 100? Или, для совсем абстрактного подхода - 10 тыс?
Другой вариант - написать парсер, который будет разбирать файл как текстовой, удалять комментарии, находить заголовки структур и вычитывать строчки шестнацатиричных чисел… Но это же гемор… и огромная опасность ошибок, если формат файла не очень жесткий.
И вроде бы, у нас под рукой есть компилятор, который как раз-таки написан для того, чтобы парсить исходные файлы.
Вопрос - есть какой-то простой и общепринятый способ решения подобной задачи? Я за два дня гугления не нашел.
Точнее, я нашел способ автоматизировать процесс сборки отдельного С-кода для каждого из набора файлов (через make) - и это работает. Но это же громоздко и неэффективно…