オリジナルhexdump関数
メモリ領域を表示する関数です。
以下の3つの要素からなります。
- アドレス部
- ASCII部
- 文字列部
文字が表示文字でない場合は'.'に置き換えます。
コード
#include <stdint.h>
#include <unistd.h>
#define PRINTABLE(a) (' ' <= a && a <= '~')
void ft_print_nbr(uintmax_t n)
{
char buf[17];
char *p;
p = buf;
*p++ = '\0';
while (1)
{
*p = "0123456789abcdef"[(n % 16)];
n /= 16;
if (!n)
break ;
p++;
}
if (!*(p - 1))
*++p = '0';
if (*(p - 2))
for (int i = 0; i < 7; i++)
*++p = '0';
while(*p)
write(1, p--, 1);
}
void *ft_print_memory(void *addr)
{
unsigned char *s1;
unsigned char *s2;
if (!addr)
return NULL;
s1 = (unsigned char *)addr;
s2 = s1;
while (*s1)
{
ft_print_nbr((uintmax_t)s1);
write(1, ": ", 2);
for (int i = 0; i < 16; i++)
{
*s1 ? ft_print_nbr(*s1++) : write(1, " ", 2);
if (i % 2)
write(1, " ", 1);
}
for (int i = 0; i < 16; i++)
if (*s2)
{
write(1, (PRINTABLE(*s2) ? s2 : (unsigned char *)".") , 1);
s2++;
}
write(1, "\n", 1);
}
return addr;
}
int main()
{
char *s = "To find information use the search box on the top right corner of the screen, or categorically browse the wiki using the Documentation topic links provided below.";
ft_print_memory(s);
return 0;
}
出力結果
0000000100003f11: 546f 2066 696e 6420 696e 666f 726d 6174 To find informat
0000000100003f21: 696f 6e20 7573 6520 7468 6520 7365 6172 ion use the sear
0000000100003f31: 6368 2062 6f78 206f 6e20 7468 6520 746f ch box on the to
0000000100003f41: 7020 7269 6768 7420 636f 726e 6572 206f p right corner o
0000000100003f51: 6620 7468 6520 7363 7265 656e 2c20 6f72 f the screen, or
0000000100003f61: 2063 6174 6567 6f72 6963 616c 6c79 2062 categorically b
0000000100003f71: 726f 7773 6520 7468 6520 7769 6b69 2075 rowse the wiki u
0000000100003f81: 7369 6e67 2074 6865 2044 6f63 756d 656e sing the Documen
0000000100003f91: 7461 7469 6f6e 2074 6f70 6963 206c 696e tation topic lin
0000000100003fa1: 6b73 2070 726f 7669 6465 6420 6265 6c6f ks provided belo
0000000100003fb1: 772e w.
ポイント
- アドレスも数字なので、アドレス部とASCII部の出力を1つの関数にまとめました。
- unsigned charにキャストすることで、拡張ASCIIに対応できるようにしています。
- 文字を扱うときは、基本的にcharで渡されたとしても、unsigned charにキャストして使うのがおすすめです。