Я пытаюсь переформатировать код, который использует структуру, выровненную по границе в 4096 байт. Структура по сути представляет собой 2d-массив, в каждой точке которого есть 2 разных uint16 с некоторым заполнением в каждой строке. Способ объявления структур следующий:
frame TemporaryFrame0 __attribute__ ((aligned(4096)));
frame TemporaryFrame1 __attribute__ ((aligned(4096)));
frame TemporaryFrame2 __attribute__ ((aligned(4096)));
Я хочу объявить это как
frame TemporaryFrame[3] __attribute__ ((aligned(4096)));
но когда я заявляю об этом, оно не сохраняется в памяти должным образом/то же самое. Структура такая
typedef struct frame frame;
struct frame {
u8 byte_offset[32];
row row[FRAME_ROW_SIZE];
};
Я также пытался объявить структуру следующим образом, но безрезультатно.
typedef struct frame frame;
struct frame {
u8 byte_offset[32];
row row[FRAME_ROW_SIZE];
}__attribute__ ((aligned(4096)));
Для чего нужны эти «рамки»? Почему они должны быть выровнены по границам 4K? Какую проблему это решает?
Отредактируйте вопрос, чтобы предоставить минимально воспроизводимый пример, особенно для утверждения: «Я также пытался объявить структуру следующим образом, но безрезультатно».
Что это за ОС/инструментарий? В некоторых случаях компоновщик может быть ограничен в отношении степени выравнивания, которую он может обеспечить, поэтому запрос на большое выравнивание может не быть удовлетворен.
__attribute__ ((aligned(4096)))
— это расширение GNU, возможно, распознаваемое и некоторыми другими компиляторами. Начиная с C11, вместо него можно использовать стандартный _Alignas(4096)
. Обратите внимание, что реализации, как правило, не обязаны поддерживать это конкретное требование выравнивания, но кажется разумным предположить, что любая реализация, поддерживающая его в форме __attribute__
, будет поддерживать его и в стандартной форме.
frame TemporaryFrame[3] __attribute__ ((aligned(4096)));
говорит, что нужно выровнять массив TemporaryFrame
. Его элементы имеют любой размер и обязательно располагаются в памяти подряд. Если размер frame
равен X, адрес TemporaryFrame[1]
на X байт превышает адрес TemporaryFrame[0]
, и он не выровнен по 4096 байт, если только X не кратен 4096.
Чтобы выровнять элементы, определите struct frame
для выравнивания:
struct frame {
u8 byte_offset[32];
row row[FRAME_ROW_SIZE];
} __attribute__ ((aligned(4096)));
Если вы не хотите менять определение struct frame
, вы можете использовать включающую структуру для обеспечения выравнивания, но вам придется добавить дополнительный код для ссылки на член структуры:
struct { struct frame f __attribute__ ((aligned(4096))); } TemporaryFrame[3];
…
// Later, where TemporaryFrame[i] would be used, use instead:
TemporaryFrame[i].f
когда я объявляю nuc_frame TemporaryNucFrame[3]; и структура как struct nuc_frame { u8 byte_offset[32]; nuc_row row[NUC_FRAME_ROW_SIZE]; }__attribute__ ((aligned(4096))); Структура все еще не выровнена должным образом в памяти?
@NickBright: Я проверил это, и у меня это работает. Отредактируйте вопрос, чтобы предоставить минимально воспроизводимый пример.
Выполнение атрибута struct { structframe f ((aligned(4096))); } TemporaryFrame[3]; работал у меня. Спасибо!
1. «Я заявляю, что он не хранится в памяти должным образом/одинаково» — уточните 2. Что такое строка