реклама на сайте
подробности

 
 
> Приведение типа указателя на элемент структуры
ViKo
сообщение Oct 17 2012, 10:51
Сообщение #1


Универсальный солдатик
******

Группа: Модераторы
Сообщений: 8 634
Регистрация: 1-11-05
Из: Минск
Пользователь №: 10 362



Допустим, имеется структура из байтов. Хочу инициализировать сразу 2 байта 16-битовым числом, или сразу 4 байта 32-битовым числом. Привожу указатель к нужному типу.
Код
typedef struct {
  __IO uint8_t A;
  __IO uint8_t B;
  uint16_t RES;
} DEV_t;

  DEV_t Dev;
  DEV_t *pDev = &Dev;

  pDev->A = 0x55;
  pDev->B = 0xAA;
  (uint16_t)pDev->A = 0x3333;
  (uint32_t)pDev->A = 0x01234567;


Код работает. Но Keil выдает предупреждения:
source\Exercises.c(117): warning: #1441-D: nonstandard cast on lvalue
Есть ли способ написать так, чтобы Keil не возмущался?
Go to the top of the page
 
+Quote Post
6 страниц V  « < 4 5 6  
Start new topic
Ответов (75 - 78)
ViKo
сообщение Dec 20 2013, 11:44
Сообщение #76


Универсальный солдатик
******

Группа: Модераторы
Сообщений: 8 634
Регистрация: 1-11-05
Из: Минск
Пользователь №: 10 362



Цитата(PheeL @ Dec 20 2013, 14:14) *
Каждый из элементов enum - это int. Так что если машинное слово 32-х разрядное, то всё верно.

Да, верно. Просто я об этом не задумывался. Да оно и нашлось всего в одном месте. Там и не сам enum стоял, а производный тип - typedef enum {...} ... Заменю на uint16_t и сэкономлю 4 байта!

Что любопытно. Имею в структуре 2 байта, в первом - битовые поля, во втором - uint8_t (вообще, reserv, для выше сказанного выравнивания). Так вот, такую 2-байтовую структуру Keil размещает в суперструктуре, не выравнивая по 2-байтовой границе. Как и написано по вышеприведенной ссылке, структура выравнивается по границе ее наибольшего члена.
Go to the top of the page
 
+Quote Post
XVR
сообщение Dec 24 2013, 09:55
Сообщение #77


Гуру
******

Группа: Свой
Сообщений: 3 123
Регистрация: 7-04-07
Из: Химки
Пользователь №: 26 847



Цитата(ViKo @ Dec 20 2013, 13:45) *
1. Что гарантирует, что вся суперструктура разместится по выровненному до слова адресу?
Компилятор гарантирует, что любое поле структуры (в том числе и поля вложенных структур) будет выровнено на его размер. Так же гарантируется, что это будет так и для массива структур. Отсюда автоматически следует, что сама структура всегда будет выровнена по ее полю с максимальным размером, и размер структуры тоже будет кратен размеру этого поля.
Цитата
Что будет, если первый элемент - 8-битовый?
Не важно, какой первый. Главное, что бы внутри был хотя бы один int
Цитата
В конце суперструктуры задаю 32-битовую CRC, это гарантирует выравнивание по словам, и целое число слов?
Да
Go to the top of the page
 
+Quote Post
Сергей Борщ
сообщение Dec 24 2013, 16:06
Сообщение #78


Гуру
******

Группа: Модераторы
Сообщений: 8 455
Регистрация: 15-05-06
Из: Рига, Латвия
Пользователь №: 17 095



Цитата(ViKo @ Dec 20 2013, 11:45) *
В конце суперструктуры задаю 32-битовую CRC, это гарантирует выравнивание по словам, и целое число слов?
Как уже было сказано - да, гарантирует. Но все "дырки", оставшиеся от выравнивания полей, могут быть заполнены совершенно произвольным мусором. Учтите это при расчете CRC. Т.е. либо перед заполнением полей структуры обнуляйте выделенную под нее память при помощи memset, либо считайте CRC конкретных полей, а не всей памяти струткуры, либо размещайте поля так, чтобы не между ними не образовывалось "дырок".


--------------------
На любой вопрос даю любой ответ
"Write code that is guaranteed to work, not code that doesn’t seem to break" (C++ FAQ)
Go to the top of the page
 
+Quote Post
AHTOXA
сообщение Dec 24 2013, 18:52
Сообщение #79


фанат дивана
******

Группа: Свой
Сообщений: 3 387
Регистрация: 9-08-07
Из: Уфа
Пользователь №: 29 684



Цитата(Сергей Борщ @ Dec 24 2013, 22:06) *
Но все "дырки", оставшиеся от выравнивания полей, могут быть заполнены совершенно произвольным мусором. Учтите это при расчете CRC.

Да, как-то я напоролся на такое. Была структура, в конце структуры crc16. При инициализации проверялось crc, и, в случае несовпадения, значениям структуры присваивались значения по умолчанию.
Всё это прекрасно работало, до тех пор, пока я не поменял размер одного члена структуры с uint8_t на uint16_t. После этой замены моя программа стала дурить. Оказалось, что при смене размера члена общий размер структуры не изменился, crc16 тоже совпал. А вот значение этого члена получилось недопустимо большое (за счёт добавленного байта).


--------------------
Если бы я знал, что такое электричество...
Go to the top of the page
 
+Quote Post

6 страниц V  « < 4 5 6
Reply to this topicStart new topic
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 


RSS Текстовая версия Сейчас: 24th July 2025 - 08:07
Рейтинг@Mail.ru


Страница сгенерированна за 0.01555 секунд с 7
ELECTRONIX ©2004-2016