The China Blue Lagoon said:
*p loads the first character, converts it to an integer, and makes the character
code available to the %x formatter.
Not exactly. *p is of type char, so it's *already* an integer.
Because it's passed as an argument to a variadic function, it's promote
from char to int (note the *very* important distinction between
"integer" and "int").
Digression: On some exotic systems it might be promoted to unsigned int.
Specifically, this happens if CHAR_MAX > INT_MAX. This can occur only
if plain char is unsigned and sizeof(int)==1; the latter can only occur
if CHAR_BIT >= 16. You're unlikely to run into this in practice, and
even if you do it's likely to be harmless.
Note that "%x" expects an unsigned int, not an int. There are rules
that make it very likely that this will work as expected, but I'd still
use an implicit conversion -- which also avoids problems on the "exotic
systems" I just mentioned.
printf("%x\n", (unsigned)*p);
It's much easier to ensure that the argument is of the right type
than to work through all the special cases to ensure that it doesn't
need to be. Note that arguments to variadic functions are one of
the few contexts where casts (explicit conversions) are actually
a good idea.
You have to make each character available to the formatter separately,
printf("%x%x%x%x\n",p[0],p[1],p[2],p[3]);
Note that that can give you ambiguous results in some cases.
For small values, "%x" gives you only one character of output.
If the above gives you "1234567", you can't tell which of the 4
values was only one hex digit wide. You can use "%02x" to avoid
this problem, giving, for example, "12345607". This assumes 8-bit
bytes (4 bits for each of 2 hex digits).
Other than %s, C doesn't have standard formatters to print arrays. You can
explicitly enumerate each element as above, or use a loop
for (k=0; *p; k++) printf("%x", p[k]);
This loop will continue to execute as long as *p is non-zero.
Since you don't modify p, that will be a very long time -- or until
your program crashes.
for (k = 0; p[k] != '\0'; k ++) {
printf("%x", p[k]);
}
Note that this is not addressed to Bill, but to anyone else who
might be interested. Bill, if you can learn something from it,
that's great, but I'm not holding my breath.