我有一个磁盘图像,其中包含一个标准图像,使用保险。超级块包含以下,我有一个功能read_superblock(*buf)就返回以下原数据:

Bytes 0-3: Magic Number (0xC0000112)
      4-7: Block Size (1024)
     8-11: Total file system size (in blocks)
    12-15: FAT length (in blocks)
    16-19: Root Directory (block number)
  20-1023: NOT USED

我非常新来C让我开始关于这个项目我很好奇什么是一个简单的方法来阅读这一结构或一些变量和简单的打印出来的屏幕上使用printf调试。

我最初想做的事情如下思考我能看到的原始数据,但我认为这不是这种情况。也没有结构和我试图阅读它作为一串其中似乎也可怕的错误。我抓住数据。有没有一种方法,我指定的结构和定义的字节数中的每一个变量?

char *buf;
read_superblock(*buf);
printf("%s", buf);
有帮助吗?

解决方案

是的,我想你会更好读成一个结构这一点。含有有用数据的字段是所有32位整数,所以可以定义如下所示(使用标准头文件stdint.h定义的类型)的结构:

typedef struct SuperBlock_Struct {
  uint32_t magic_number;
  uint32_t block_size;
  uint32_t fs_size;
  uint32_t fat_length;
  uint32_t root_dir;
} SuperBlock_t;

调用char*时,可以投射的结构,以一个read_superblock,如下所示:

SuperBlock_t sb;
read_superblock((char*) &sb);

现在打印出你的数据,你可以像下面这样的电话:

printf("%d %d %d %d\n",
  sb.magic_number,
  sb.block_size,
  sb.fs_size,
  sb.fat_length,
  sb.root_dir);

请注意,您需要使用这样的技术时,因为你读整型数据(例如,您可能需要读取数据时转换字节)必须知道你的平台的字节序。你应该能够快速确定使用的第一场神奇的数字。

请注意,它是通常优选通过这样的结构,而没有浇铸;这允许您利用编译器的类型检查的优势,消除了潜在的问题,铸造可能隐藏。然而,这将需要改变你的read_superblock的执行将数据直接读入的结构。这并不困难,并且可以使用标准的C运行时功能fread来完成(假设你的数据是在一个文件中,如在您的问题暗示),像这样:

fread(&sb.magic_number, sizeof(sb.magic_number), 1, fp);
fread(&sb.block_size, sizeof(sb.block_size), 1, fp);
...

其他提示

两件事加在这里:

  1. 这是一个好主意,当拉原始数据变成一个结构,设置的结构以有零填充的,即使它是完全由无符号的32位整数。在海湾合作委员会你这样做 #pragma pack(0) 之前结构定义和 #pragma pack() 之后。
  2. 为处理潜在的字节序问题,两个电话看看是 ntohs()ntohl(), 对于16和32位数值分别为。注意,这些交换网络字节的以主机字节的顺序;如果这些都是相同的(这是他们是不是在x86平台),他们什么都不做。你从主要网络字节的顺序 htons()htonl().然而,由于这种数据,是来自你的文件系统和无网络,我不知道如果字节序是一个问题。这应该足够容易找出通过比较值你期望(例如这块大小)的价值,你得到的,在六角。

这不难打印你的数据成功复制到数据提出Emerick的结构之后。假设你用它来保存数据结构的实例被命名为SuperBlock_t_Instance。

然后就可以打印出它的领域是这样的:

printf("Magic Number:\t%u\nBlock Size:\t%u\n etc", 
SuperBlock_t_Instance.magic_number, 
SuperBlock_t_Instance.block_size);
许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top