Переполнение при использовании uint32_t
#include <stdint.h>
#include <stdio.h>
#include <stdlib.h>
char* createMSG(uint8_t i,uint32_t port);
int strlen(char* tmp);
uint32_t user_port = 5000;
int main(int argc, char** argv) {
char *msg;
uint8_t i;
i = 1;
msg = createMSG(i,user_port);
printf("Port: %d",*(msg+2));
}
char* createMSG(uint8_t i,uint32_t port) {
char *buff;
buff = (char*) malloc(6);
uint8_t id;
id = 2;
memcpy(buff, &id, sizeof(uint8_t));
memcpy(buff+1, &i, sizeof(uint8_t));
memcpy(buff+2, &port, sizeof(uint32_t));
return buff;
}
Вывод: "Порт: -120". Кажется, что-то переполнено. Но uint32_t должно быть достаточно большим для 5000. При использовании 22 вместо 5000 все в порядке.
Зачем?
2 ответа
Решение
Эта линия
printf("Port: %d",*(msg+2));
печатает значение 'char' по адресу (msg+2), а не по uint32_t!
использование
uint32_t PortFromProc = *(uint32_t*)(msg+2);
printf("Port: %d", PortFromProc);
Чтобы "исправить" номера портов из функции recvfrom(), необходимо использовать функцию ntohl().
Так как *(msg+2)
имеет тип char
, Если вы действительно хотите сделать это, вы должны сделать
printf("Port: %d",*(uint32_t*)(msg+2));
Как отмечает @R.., msg + 2 почти наверняка не соответствует требованиям правильного выравнивания для типа uint32_t. Если код работает, это случайность, а не переносимость.