Полное объявление типа структуры выглядит так:
Код
typedef struct { здесь список членов } имя_типа;
В плюсах есть более короткая запись
Код
struct имя_типа { здесь список членов };
После такого объявления компилятор знает имена, размеры и взаимное расположение членов и вы можете использовать offsetof:
Код
n = offsetof(имя_типа, имя_члена);
Просто объявление struct имя_типа; - неполное (incomplete) объявление типа. После такого объявления компилятор знает, что где-то будет объявлен такой тип и что этот тип будет структурой. Что будет в этой структуре он не знает, максимум, что он может вам позволить после такого объявления - объявить указатель на эту структуру и присваивания с этим указателем. Ни содержания этой структуры, ни размера ее он не знает, поэтому даже инкремента или декремента такого указателя он сделать не может, не говоря уже о доступе к членам этой структуры.
объявление struct { список членов } имя; объявляет структуру безымянного типа и
переменную "имя" этого типа. Поэтому вы не можете использовать "имя" в offsetof, ибо это имя переменной, а не типа.
В обычных Сях возможно объявление struct имя_типа { здесь список членов } имя_переменой; Здесь имя_типа - тоже неполное объявление типа, оно позволяет вставить в структуру указатель на нее же (используется для организации связанных списков), но не более того.
В первом сообщении темы нужно было объявить тип структуры и переменную этого типа:
Код
typedef struct
{
uint16_t data0;
uint16_t data1;
uint16_t data2;
uint16_t data3;
uint16_t data4;
uint16_t data5;
}data_test;
data_test Data_test;
struct data_test Data_test1; //можно и так, но тут ключевое слово struct избыточно
И вот после этого можно было использовать offsetof():
Код
number = offsetof(data_test, data0); // тут используется имя типа "data_test", а не имя переменной!