eddy_em: (Default)
eddy_em ([personal profile] eddy_em) wrote2018-05-29 11:32 pm

Перевод бинарных файлов в массив

Для этой операции, необходимой довольно-таки часто (особенно для микроконтроллеров: скажем, мелкую картинку во флеш записать или кусочек звукового файла), обычно пишутся велосипеды вроде такого:
hexdump -e '20/1 "0x%02x, " "\n"' testbin
0x0d, 0x19, 0x32, 0x44, 0xc9, 0xc9, 0xc9, 0x92, 0x24, 0x3b, 0x3b, 0x3b, 0x45, 0x46, 0x46, 0x6a, 0xc4, 0x88, 0x11, 0x84,
....

потом это ручками правится и все здорово.
Однако, наткнулся на SO на замечательный совет: использовать vim (точнее, утилиту, идущую с ним):
xxd -i testbin 
unsigned char testbin[] = {
  0x0d, 0x19, 0x32, 0x44, 0xc9, 0xc9, 0xc9, 0x92, 0x24, 0x3b, 0x3b, 0x3b,
....
};
unsigned int testbin_len = 100;

Очень удобно: практически без изменений (разве что const дописать) результат можно использовать!
Правда, с разрядностью выше 8 xxd не справится. И здесь уже велосипеды. 16 бит:
hexdump -e '16/2 "0x%04x, " "\n"' testbin 
0x190d, 0x4432, 0xc9c9, 0x92c9, 0x3b24, 0x3b3b, 0x4645, 0x6a46, 0x88c4, 0x8411, 0x0003, 0x0000, 0x0000, 0x0000, 0x7dc0, 0xc9c8,
...

32 бита:
hexdump -e '10/4 "0x%08x, " "\n"' testbin 
0x4432190d, 0x92c9c9c9, 0x3b3b3b24, 0x6a464645, 0x841188c4, 0x00000003, 0x00000000, 0xc9c87dc0, 0xa7a791c9, 0xf2f2f2a7,
...

Ну и видно, что все в little endian. Если возникнет нужда с big endian что-то делать, то придется городить еще какой-то велосипед. Либо писать универсальную утилиту, которая будет делать то же, что xxd, но с бóльшими возможностями.