1

Ok so I'm building a simple dns client program (without the use of things like getaddrinfo) in C, but I'm getting a weird issue when I print out the response address. The following code correctly prints out addr = 130.127.69.75, however, when I comment out the memcpy call and uncomment the line after it, my output becomes addr = 4294967170.127.69.75

temp[0] = resp[j++];
temp[1] = resp[j++];
memcpy(&response.rdlength, temp, 2);

printf("resp.rdlength = %d\n", response.rdlength);
response.rdlength = ntohs(response.rdlength);
for(i = 0; i < response.rdlength; i++) {
    temp[i] = resp[j++];
}

memcpy(&response.Addr, temp, response.rdlength);
response.Addr = ntohl(response.Addr);
unsigned int *a = &response.Addr;
unsigned int *b = (unsigned int *)malloc(sizeof(unsigned int) * 4);
printf("addr = %x\n", *a);
printf("temp = %c\n", temp[0]);
for(i = 0; i < 4; i++) {
    b[i] = 0;
    memcpy(&b[i], &temp[i], 1);
    //b[i] = (unsigned int)temp[i];         
}
printf("addr = %u.%u.%u.%u\n", b[0], b[1], b[2], b[3]);
//      exit(2);        

I'm just really not sure why that commented out assignment statement gives such a bizarre output, and would appreciate some clarification on why I might be seeing that behavior, and how I can get around it (without memcpy). I can post more of the code if necessary, but I think anything above what I've shown is just a lot of parsing other parts of the response packet, so I haven't initially included it.

mch
  • 9,424
  • 2
  • 28
  • 42
Arveanor
  • 43
  • 4
  • 4
    Perchance, is your `char` `signed`? – Deduplicator Nov 27 '14 at 16:45
  • Or maybe https://stackoverflow.com/questions/7950032/why-the-result-is-2-of-unsigned-int-1-unsigned-int-0xffffffff – Deduplicator Nov 27 '14 at 17:05
  • All this time I had no idea why anyone would ever make a char signed, but I guess that makes sense, now. Thanks! – Arveanor Nov 27 '14 at 17:34
  • this is data dependent activity. the char is signed, so sign extension occurs in the assignment to a int value. When the the char is greater that 0x7f, the high order bit is '1' (the sign bit) and the 1 bit is sign extended into the result variable. Similarly when the char is less than/equal to 0x7f the high order bit is '0' and 0 bit is sign extended into the result variable. – user3629249 Nov 27 '14 at 18:04
  • 1
    @user3629249: **Don't** use sign-extension as an explanation model. It only works for 2s-complement, and is far lower-level than needed anyway. Do it the standard-way: The result of conversion to `unsigned` is the original value, modulo (max_value+1). – Deduplicator Nov 27 '14 at 18:27
  • Your `memcpy(&b[i], &temp[i], 1)` is wrong, the `b[i]`s are `unsigned int`s so their size is unlikely to be 1, and you are copying 1 byte only, it should be `memcpy(&b[i], &temp[i], sizeof(usngined int))`, so may be `temp[i]` is not what you think it is. By the way, why use `unsigned int` if you never need more than 1 byte? Sorry if my english is not good enough, if you cant understand what I mean pleas ask me. – Iharob Al Asimi Nov 28 '14 at 02:26

0 Answers0