#include <stdio.h> void dump (void *p, int n) { unsigned char *p1 = p; while (n--) { printf("%p - %02x\n", p1, *p1); p1++; } } int main (void) { char c = 150; short s = -3; int i = -151; printf("dump de c: \n"); dump(&c, sizeof(c)); printf("dump de s: \n"); dump(&s, sizeof(s)); printf("dump de i: \n"); dump(&i, sizeof(i)); return 0; }
#include <stdio.h> void dump (void *p, int n) { unsigned char *p1 = p; while (n--) { printf("%p - %02x\n", p1, *p1); p1++; } } int main (void) { short l = -32765; unsigned short k = 32771; printf("l=%d, k=%u \n", l, k); printf("dump de l: \n"); dump(&l, sizeof(l)); printf("dump de k: \n"); dump(&k, sizeof(k)); return 0; }
Imagine que uma empresa quer utilizar uma estrutura de dados que empacota 4 bytes signed em um valor inteiro unsigned de 32 bits. Os bytes dentro de uma palavra são numerados de 0 (menos significativo) a 3 (mais significativo). Sua tarefa é implementar uma função com o protótipo abaixo:
typedef unsigned packed_t; /* extrai byte de palavra e retorna inteiro (32 bits) com sinal */ int xbyte (packed_t word, int bytenum);Use seus conhecimentos de aritmética de complemento a 2 e shifts à direita para implementar essa função. Teste-a com o programa abaixo (leia até o final da questão!):
#include <stdio.h> #include <stdlib.h> #include <ctype.h> typedef unsigned packed_t; int string2num (char *s, int base) { int a = 0; for (; *s; s++) { if(isdigit(*s)) a = a*base + (*s - '0'); else if((*s >= 'A') && (*s < (base-10+'A'))) a = a*base + ((*s - 'A') + 10); else if((*s >= 'a') && (*s < (base-10+'a'))) a = a*base + ((*s - 'a') + 10); else { printf("pane: numero invalido! \n"); exit(1); } } return a; } int xbyte (packed_t word, int bytenum) { /* implementar!!! */ return 1; } int main (int argc, char **argv) { int x; if (argc != 3) { printf ("uso: %s <word (em hexadecimal)> <bytenum>\n", argv[0]); exit(1); } x = xbyte(string2num(argv[1], 16), atoi(argv[2])); printf ("%08x %d\n", x, x); return 0; }Para entender como deve funcionar o programa depois que você implementar a função xbyte, veja os exemplos abaixo:
ana@sol:~/sb$ ./xbyte 01abcd02 0 00000002 2 ana@sol:~/sb$ ./xbyte 11a032b5 0 ffffffb5 -75 ana@sol:~/sb$ ./xbyte 11a032b5 1 00000032 50 ana@sol:~/sb$ ./xbyte 11a032b5 2 ffffffa0 -96 ana@sol:~/sb$ ./xbyte 11a032b5 3 00000011 17 ana@sol:~/sb$ ./xbyte abcd 3 00000000 0 ana@sol:~/sb$ ./xbyte abcd 1 ffffffab -85 ana@sol:~/sb$ ./xbyte zzzz 1 pane: numero invalido!
Execute o programa abaixo e explique seu resultado (pense na representação interna dos valores de x e y e na declaração de seus tipos).
#include <stdio.h> int main (void) { int x = -1; unsigned int y = 2; printf("x=%d, y=%d\n", x, y); printf("x é menor do que y? %s\n", (x<y)?"sim":"nao"); return 0; }
Em C, o programador pode atribuir um signed char
,
que ocupa 8 bits,
a um unsigned int
, que ocupa 32 bits:
signed char sc = -1; unsigned int ui = sc;Ao atribuir um valor a
ui
, o que o código gerado tem que
fazer?
Observe que há duas mudanças, de tamanho e de tipo (o tipo, nesse
caso, é importante para saber como fazer a mudança de tamanho).
Faça a conversão na mão e diga como ficará a representação
interna de ui
.
Em seguida, escreva um programa em C para conferir sua resposta.
(Escreva as linhas acima e depois chame dump para ui).