The following simple code produces strange output:
#include <stdio.h>
#include <string.h>
#include "/tmp/sha.h"
#define DIGEST 64
//taken from coreutils 8.5 - produces 64-byte sha digest and puts it into resblock
extern int sha512_stream(FILE *stream, void *resblock);
int main(int argc, char** argv) {
char sha[DIGEST];
memset(sha, 0, DIGEST);
FILE *stream;
stream = fopen("/bin/less", "r");
sha512_stream(stream, (void *) sha);
fclose(stream);
char buf[2] = {10, 32};
printf("%02x\n", sha[0]);
printf("%02x\n", buf[0]);
return 0;}
Gives the output:
ffffffa9
0a
The first byte of sha is A9, but where are the padding F’s coming from?
On Ubuntu Linux 10.10 with gcc 4.4.5.
(char)defaults to(signed char)on Linux x86, and becauseprintf()usesstdargthe(signed char)is being promoted implicitly to(int)resulting in sign extension. You’ll need to declare it(unsigned char)to get the expected behavior. (There is no way to pass type information throughstdarg, so default promotions are performed on arguments.)