Estou escrevendo um aplicativo em c para um STM32F105, usando o gcc.
No passado (com projetos mais simples), eu sempre variáveis definidas como char
, int
, unsigned int
e assim por diante.
Eu vejo que é comum usar os tipos definidos no stdint.h, tais como int8_t
, uint8_t
, uint32_t
, etc. Isto é verdade em múltiplos API do que estou usando, e também na biblioteca ARM CMSIS de ST.
Eu acredito que entendo por que devemos fazê-lo; para permitir que o compilador otimize melhor o espaço na memória. Espero que possa haver razões adicionais.
No entanto, devido às regras de promoção de número inteiro de c, continuo correndo contra os avisos de conversão sempre que tento adicionar dois valores, fazer uma operação bit a bit etc. O aviso tem algo como conversion to 'uint16_t' from 'int' may alter its value [-Wconversion]
. A questão é discutida aqui e aqui .
Isso não acontece ao usar variáveis declaradas como int
ou unsigned int
.
Para dar alguns exemplos, é necessário:
uint16_t value16;
uint8_t value8;
Eu teria que mudar isso:
value16 <<= 8;
value8 += 2;
para isso:
value16 = (uint16_t)(value16 << 8);
value8 = (uint8_t)(value8 + 2);
É feio, mas posso fazê-lo, se necessário. Aqui estão as minhas perguntas:
Existe um caso em que a conversão de não assinado para assinado e de volta para não assinado tornará o resultado incorreto?
Existem outros grandes motivos a favor / contra o uso dos tipos inteiros stdint.h?
Com base nas respostas que estou recebendo, parece que os tipos stdint.h geralmente são os preferidos, mesmo que c seja convertido uint
para int
e para trás. Isso leva a uma pergunta maior:
- Eu posso evitar os avisos do compilador usando typecasting (por exemplo
value16 = (uint16_t)(value16 << 8);
). Estou apenas escondendo o problema? Existe uma maneira melhor de fazer isso?
value8 += 2u;
e value8 = value8 + 2u;
, mas recebo os mesmos avisos.
8u
e2u
.