我正在尝试创建像 xxd 这样的 hexdump,但我正在尝试解决一些差异。目前,该程序每行处理 10 个字符,如最右列所示,而 xxd 中为 16 个。它也只显示每列 1 个八位字节,而不是成对的 2 个八位字节。
xxd
0000000: 2369 6e63 6c75 6465 203c 7374 6469 6f2e #include <stdio.
我的输出
0: 23 69 6E 63 6C 75 64 65 20 3C #include <
编辑:
为了添加一些说明,我试图实现两件事。1) 我希望这个程序能像xxd 一样输出。为此,它需要输出 32 个十六进制数字(8x 列,每列 4)。2)我还希望程序在 xxd 中列出行的 4 列中的十六进制数字。
我试图将下面源代码中的“10”编辑为“12”,但它会在输出中产生错误,这似乎是一个神奇的数字。
资源:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include <ctype.h>
#define BYTE_OFFSET_INIT 8
#define CHAR_OFFSET_INT 39
#define LINE_LENGTH 50
static void print_e(int e, char *program, char *file)
{
fprintf(stderr, "%s: %s: %s\n", program, file, strerror(e));
}
static void print_line(char *line)
{
int i;
/* sprintf leaves terminators mid-line, so clear them out so we can print the full line */
for (i = BYTE_OFFSET_INIT; i < CHAR_OFFSET_INT; i++)
if (line[i] == '\0')
line[i] = ' ';
printf("%s\n", line);
}
int main(int argc, char *argv[])
{
char line[LINE_LENGTH + 1];
int ch;
int character = 0;
int line_offset = 0;
int byte_offset = BYTE_OFFSET_INIT, char_offset = CHAR_OFFSET_INT;
if (argc != 2) {
fprintf(stderr, "Usage: %s [file]\n", argv[0]);
exit(EXIT_FAILURE);
}
FILE *fp = fopen(argv[1], "rb");
if (!fp) {
print_e(errno, argv[0], argv[1]);
exit(EXIT_FAILURE);
}
printf("Offset Bytes Characters\n");
printf("------ ----------------------------- ----------\n");
while ((ch = fgetc(fp)) != EOF) {
if (character == 0) {
sprintf(line, "%6d ", line_offset);
line_offset += 10;
}
sprintf(line + byte_offset, "%02X ", ch);
sprintf(line + char_offset, "%c", isprint(ch) ? ch : '.');
character++;
char_offset++;
byte_offset += 3;
if (character == 10) {
print_line(line);
character = 0;
char_offset = CHAR_OFFSET_INT;
byte_offset = BYTE_OFFSET_INIT;
}
}
if (ferror(fp)) {
print_e(errno, argv[0], argv[1]);
exit(EXIT_FAILURE);
}
if (character > 0)
print_line(line);
if (fclose(fp) == EOF) {
print_e(errno, argv[0], argv[1]);
exit(EXIT_FAILURE);
}
return 0;
}