"Правильно только это" - для меня это снисходительный тон
кафедрального лаборанта. Не пытайся быть таким и я тебе не скажу
куда идти. Если не понимаешь что-то - спроси, может договоримся о
терминах. Твоё "правило" - опять хоровод. Слово struct может быть после pack как при "голом" объявлении типа, то же с typedef, может быть при явном объявлении структуры некоего набранного тут же типа с именем. Ещё имеется неполное объявление типа, в т.ч. указателей. Мелкософт стесняется рассказывать явно перед которым из слов struct прагма будет работать, а перед которым нет.
В разных компиляторах даже синтаксис этих прагм разный. Ещё есть атрибуты, сними чуть проще, но тоже некоторая грусть. Самое же в прагмах упаковки поганое - они практически всегда действуют при выделении памяти. Потому и мурашки при вложенности, extern, передаче формальных параметров в функцию.
Ещё существуют и с самими struct неопределенности насчет выделения памяти, оптимизации, области видимости, и нюансы использования алиасов как отдельных типов (особенно интересно неполное объявление указателей типа структуры через typedef при разовом использовании - некоторые применяют для замены явного включения хедеров).
При этом в gcc ещё и ожидаемо разное поведение, например, в зависимости от флагов no-common и no-strict-aliasing. При "голом" объявлении типа память не должна выделяться, но тоже не всё однозначно.