c - 二进制文件读取错误,是字节序问题还是文件读取问题?
问题描述
目前我正在启动一个简单的 c VM,它将二进制文件读入“内存”数组,然后将获取解码并评估给定的指令。目前我被困在如何正确地将这个二进制文件读入内存,以便能够读取以供以后在解码和基于 2 或 4 个字节分离时使用。我的输入与我在下面输入的输出不匹配,我不确定这是字节序问题还是我没有正确地将文件读入内存。
主要的.c
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#define MAXMEM 1024
unsigned memory[MAXMEM];
int loads(char *filename)
{
File *file = fopen(filename, "rb");
return fread(memory, sizeof *memory, MAXMEM, file);
}
int main(int argc, char **argv){
if(argc <= 1){
printf("No file Found\n");
return -1;
}
char *filename = argv[1];
loads(filename);
printf("%04x\n", *memory);
}
INPUT.BIN(运行中得到的数据od -x --endian=big input.bin | head -5
)
00000000 b10a b200 1123
电流输出
b20ab1
期望的输出
either b10a b200 1123
or b1 0a b2 00 11 23
解决方案
显示问题都在这个语句中:
printf("%04x\n", *memory);
首先使用表示您要显示的格式的格式字符串。也许:
"%02x %02x %02x $02x\n"
以下建议的代码:
- 干净地编译
- 执行所需的功能
- 正确处理 IO 错误
- 不包括头文件那些内容没有被使用
现在,建议的代码:
#include <stdio.h>
//#include <string.h>
#include <stdlib.h> // exit(), EXIT_FAILURE
#define MAXMEM 1024
char memory[MAXMEM];
size_t loads(char *filename)
{
FILE *file = fopen(filename, "rb");
if( !file )
{
perror( "fopen for read failed" );
exit( EXIT_FAILURE );
}
return fread(memory, sizeof *memory, MAXMEM, file);
}
int main(int argc, char **argv){
if( argc != 2 )
{
fprintf( stderr, "USAGE: %s inputFileName\n", argv[0] );
exit( EXIT_FAILURE );
}
char *filename = argv[1];
size_t fileSize = loads(filename);
printf( "File Size: %zu\n", fileSize );
printf("%02x %02x %02x %02x\n",
memory[0],
memory[1],
memory[2],
memory[3]);
}
当针对同一个源文件运行时,会导致:
File Size: 701
23 69 6e 63
注意:23 69 6e 63
是十六进制值#inc
我将内存修改为 type char
。如果要保留它unsigned
,请注意 32 位无符号包含 8 个半字节,因此调用的格式字符串printf()
应%08x
为每个无符号值显示
推荐阅读
- php - 如何在 PHP 中执行类型提示接口的合同
- reactjs - 更新子组件状态后如何调用父组件的setState方法?
- java - 有没有办法为 org.springframework.data.jpa.domain.Specification 返回父实体的规范?
- angularjs-ng-repeat - 角度js ng-repeat不起作用
- c# - 如何最好地将大量数据添加到 DataGridView
- python - 视觉模拟量表精神病
- reactjs - DropdownMenu 在每次点击时重新呈现所有下拉项
- html - flexbox 的媒体查询问题
- image - 检测图像中的重复图案
- python - Python 'pandas' 在 0.23.0 版上没有属性 'ewm' 但在 0.18.0 版上没问题