【问题标题】:Having trouble with hexdump program in CC 中的 hexdump 程序有问题
【发布时间】:2018-10-21 19:04:49
【问题描述】:

我似乎无法打印任何字符,事实上,程序似乎无法正确读取 any 文件,因为当我给它一个时,所有十六进制值都是零文件。

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <argp.h>
#include <sys/types.h>
#include <sys/stat.h>

static error_t parse_opt(int key, char *arg, struct argp_state *state);
static void dump_hex(char *f, size_t l);

static struct argp_option options[] = {
    {"filepath",    'f', "PATH",    0, "uses filepath provided by user" },
    { 0 }
};

struct arguments {
    char *path;
    /* int *column_size; */
};

static error_t parse_opt(int key, char *arg, struct argp_state *state) {

    struct arguments *arguments = state->input;

    switch(key) {
        case 'f':
            arguments->path = arg;
            break;

        default:
            return ARGP_ERR_UNKNOWN;
        }

    return 0;
}

static struct argp argp = { options, parse_opt, NULL, NULL };

static void dump_hex(char *f, size_t l) {

    FILE *fd;
    size_t i;
    unsigned char *b = (unsigned char *)malloc(16 * sizeof(unsigned char));

    memset(b, 0, 16 * sizeof(unsigned char));

    if((fd = fopen(f, "r"))) {
        for(i = 0; i <= l; i++) {
            if((i % 8) == 0) {
                if(i != 0) {
                    printf("| %s\n", b);
                }
                /* print the offset */
                printf("%05lx: ", i);
            }
            /* check if ASCII is printable */
            b[i % 16] = isprint(b[i]) ? b[i] : '.';

            /* print ASCII */
            printf("%02x ", b[i]);
        }

        /* print remaining ASCII */
        printf("| %s\n", b);
    }

    fclose(fd);
    free(b);
}

int main(int argc, char *argv[]) {

    struct arguments arguments;
    struct stat sb;
    off_t size;

    arguments.path = "-";

    argp_parse(&argp, argc, argv, 0, 0, &arguments);

    stat(arguments.path, &sb);
    size = sb.st_size;

    dump_hex(arguments.path, size);

    return 0;
}

这是我在将参数传递给二进制文件时收到的输出:

./hexdump --filepath=/tmp/a.out

212d0: 00 00 00 00 00 00 00 00 | ................
212d8: 00 00 00 00 00 00 00 00 | ................
212e0: 00 00 00 00 00 00 00 00 | ................
212e8: 00 00 00 00 00 00 00 00 | ................
212f0: 00 00 00 00 00 00 00 00 | ................
212f8: 00 00 00 00 00 00 00 00 | ................
Segmentation fault

此外,任何使代码更简洁的提示都会非常有益。

【问题讨论】:

  • 我推荐你使用fp作为文件指针(FILE *fp),保留fd作为文件描述符(int fd)。我建议您将文件打开和关闭与十六进制转储分开;将打开的文件流(文件指针)传递给 dex 转储函数。这避免了“如何将- 作为文件名处理”的问题——您只需将stdin 作为文件流传递。请注意,如果您打开文件失败,您仍然fclose()它;这是分段错误的秘诀。也要检查你的内存分配,尽管我承认它不太可能失败。 您在哪里读取文件?我看不到读取文件的代码?
  • @JonathanLeffler 我使用fd = fopen(f, "r") 打开文件并使用以下循环遍历它。
  • @redoes:此代码仅打开文件以进行读取访问。但你不是在阅读任何东西。为此,您必须使用fread()
  • @JonathanLeffler 当我遍历文件时我没有阅读它吗?
  • @redoes:您不是在代码中使用 for 循环来遍历文件。

标签: c hexdump


【解决方案1】:

您得到零的原因是您没有读取文件的内容并且b 被初始化为0x00。您只是打开和关闭文件。

另一个问题(这可能是分段错误的原因)是b 的大小为 16 字节。在某些地方您使用i % 16,但不是全部(在某些地方您直接使用i)。你一定要检查一下。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2018-10-23
    • 2016-10-02
    • 1970-01-01
    • 1970-01-01
    • 2017-11-27
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多