Это просто хорошая практика или это вызывает непредсказуемое поведение без нее?
Ни один из двух. Если данные, будучи упакованными или нет, используются только внутри программы, тогда хорошо, чтобы компилятор решил, как упорядочить эти данные и как их выровнять, - если вы действительно не хотите сохранять ram.
Если данные должны иметь определенный формат - и я думаю, что да, потому что ваша структура называется «radio_packet», то вы хотите быть уверены, что формат, который вы пишете, соблюдается. В этом случае вы хотите упаковать данные и вставить вручную прописку, если требуется формат.
В этом конкретном случае имя структуры заставляет меня думать, что пакет будет передан на другое оборудование, на котором будет запущено программное обеспечение, написанное, возможно, с помощью другого компилятора. Таким образом, вы не хотите, чтобы компилятор вмешивался в порядок и положение ваших полей. Другими словами, структура не используется только внутри программы.
Дальнейшее продление. Хорошая практика не использоватьупаковка и/или выравнивание, в нормальных ситуациях, потому что компилятор знает лучше, чем человек, что лучше. Вы используете упаковку/выравнивание, когда знаете, что делать лучше, чем компилятор, например, потому что вы должны уважать какой-то формат, о котором компилятор не знает. Обычно (но зависит от компилятора), он делает выбор, чтобы оптимизировать производительность, возможно, растрачивая некоторый баран. Для достижения максимальной производительности он может выровнять поля с предпочтительным выравниванием ЦП, вставить неиспользуемые/скрытые поля или даже переупорядочить их. Это не очень хорошо, если вы затем принимаете этот пакет и отправляете его на какое-то оборудование или программное обеспечение, которое не использует одно и то же дополнение/выравнивание: 32-битный процессор предпочитает 32-разрядные согласованные данные, но 8-битный ЦП не заботится.
С точки зрения вашей программы/ЦП в любом случае никогда не будет непредсказуемого поведения. Компилятор прекрасно знает, что он делает, даже если вы навязываете ему некоторые ограничения. Неправильное или [вероятно, не так] непредсказуемое поведение происходит, когда данные, неправильно отредактированные, входят/выходят из вашей программы.
Ну, если вы хотите избежать добавления, добавленного компилятором (между 'tag' и' id'), тогда вам нужно «упаковать» эту структуру. –
Вообще говоря, эти атрибуты не используются; они предназначены для специализированных ситуаций. Но в этих особых ситуациях они совершенно необходимы, и похоже, что вы используете этот тип в одной такой ситуации. – Hurkyl
'__attribute __ ((упакованный))' достаточно, 'aligned (1)' избыточно. Однако, чтобы уменьшить выравнивание по отношению к чему-то еще, чем к 1, оба они необходимы. Например, с учетом структуры с естественным выравниванием 4, '__attribute __ ((упакованный, выровненный (2)))' уменьшается выравнивание до 2. «упакованный» необходим в этом случае, потому что выравнивание в противном случае не может быть уменьшено. (Это относится к GCC.) –