从二进制文件读取8字节数据 [英] 8 bytes data reading from binary file

查看:106
本文介绍了从二进制文件读取8字节数据的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

亲爱的所有人,

我认为这是简单的程序.但是我真的面临问题,并且厌倦了寻找解决方案的过程.所以,我真的需要您的帮助.

这是问题所在.
我将7E FF FF FF FF FF FF 7E(8字节)数据保存在二进制文件中.
我想以二进制文件的相反顺序来检索它.

以下是输出功能.

Dear all,

I think it is simple program. But I really face problem and tired out of finding solution. So, I really need your help.

Here is the problem.
I saved 7E FF FF FF FF FF FF 7E (8 bytes) data in binary file.
I would like to retrieve it as reverse order with binary file.

The following is output function.

void outputint64(int i) {
	__int64 app1 = (__int64)mem[i+3] << 48; //mem is short type array data read from binary file
	__int64 app2 = (__int64)mem[i+2] << 32;
	__int64 app3 = (__int64)mem[i+1] << 16;
	__int64 app4 = (__int64)mem[i];
	__int64 app = (__int64)app1 | (__int64)app2 | (__int64)app3 | (__int64)app4;
	printf("int64 value is : %I64x", app);
}



app1输出为0x 7E FF 00 00 00 00 00 00//输出与我期望的一样
app2输出为0x FF FF FF FF 00 00 00 00////实际上我只希望0x 00 00 FF FF 00 00 00 00
app3输出为0x FF FF FF FF FF FF 00 00//实际上我只期望0x 00 00 00 00 FF FF 00 00
app4的输出为0x FF FF FF FF FF FF FF 7E//实际上我只期望0x 00 00 00 00 00 00 FF 7E

因此,即使我期望为0x 7E FF FF FF FF FF FF FF 7E,应用程序的输出也变为0x FF FF FF FF FF FF FF 7E.

如何修改才能获得预期的结果?
如果您有任何想法,请帮助我.

预先感谢.



app1 output is 0x 7E FF 00 00 00 00 00 00 //the output is as I expect
app2 output is 0x FF FF FF FF 00 00 00 00 //actually I only expect 0x 00 00 FF FF 00 00 00 00
app3 output is 0x FF FF FF FF FF FF 00 00 //actually I only expect 0x 00 00 00 00 FF FF 00 00
app4 output is 0x FF FF FF FF FF FF FF 7E //actually I only expect 0x 00 00 00 00 00 00 FF 7E

So, app output becomes 0x FF FF FF FF FF FF FF 7E, even though I expect as 0x 7E FF FF FF FF FF FF 7E.

How should I modify to get the expected result?
If you have any idea, please help me.

Thanks in advance.

推荐答案

我认为您会发现问题是符号扩展之一,也就是说-如果您仅声明mem为4个短裤的数组,则它们为 SIGNED 短裤. App1正常运行,因为第一个短路为0x7E-或 0 111 1110

其他失败,因为它们都以MSB中的1位(最高有效位)开头.这意味着它们被解释为带符号的(实际上是-ve),因此在它们乘以0时保持负数是剩余的. shift是,它们插入了1位(在更高有效位中),而不是0位-仍添加在最低有效位中.

要解决此问题,请将mem声明为未签名短裤的数组. (此行为在ASM中不会发生-这是C编译器为您(对?)所做的)

以下代码产生输出:

I think you''ll find that the problem is one of sign-extension, that is to say - if you''ve only declared mem to be an array of 4 shorts, they are SIGNEDshorts. App1 works ok because the first short is 0x7E - or 0111 1110

The others fail, because they all begin with a 1 bit in the MSB (most significant bit) This means they are interpreted as signed (-ve, in fact), so to maintain that negativity when they are multiplied 0 which is what a left shift is, they have 1 bits inserted (in the more significat bits), rather than 0 bits - which are still added in the least significant bits.

To fix, declare mem as an array of UNsigned shorts. (This behaviour doesn''t happen in ASM - it''s the C compiler does it for (to?) you)

The following code produces the output:

int64 value is : 7effffffffffff7e







#include <stdio.h>
#include <stdlib.h>

unsigned short mem[4];

void outputint64(__int64 i)
{
    __int64 app1 = (__int64)mem[i+3] << 48; //mem is short type array data read from binary file
    __int64 app2 = (__int64)mem[i+2] << 32;
    __int64 app3 = (__int64)mem[i+1] << 16;
    __int64 app4 = (__int64)mem[i];
    __int64 app = (__int64)app1 | (__int64)app2 | (__int64)app3 | (__int64)app4;
    printf("int64 value is : %I64x", app);
}

int main()
{
    FILE *fp;
    fp = fopen("inputData.bin", "rb");
    fread(mem, 2, 4, fp);
    fclose(fp);
    int offset = 0;

    outputint64(offset);
}


short是带符号的类型.因此,当您从short转换为__int64时,它会根据符号位填充其他字节.在您的情况下为1(当高字节的值为FF时).因此,其他字节用FF''填充.

short is a signed type. So, when you cast from short to __int64, it fills the additional bytes according to the sign bit. In your case it''s 1 (when the value of the high byte is FF). So the additional bytes are filled with FF''s.

您可以通过为每个<<操作添加一个附加的&操作来解决此问题.像这样的东西:

You can fix that issue, by adding an additional & operation for each << operation. Something like:

__int64 app3 = ((__int64)mem[i+1] & (__int64)0xffff) << 16;

或者,通过向unsigned short添加其他强制转换.像这样的东西:

Or, by adding an additional cast to unsigned short. Something like:

__int64 app3 = (__int64)(unsigned short)mem[i+1] << 16;

顺便说一句,您可以仅在一行中设置app变量的值(在outputint64函数中):

By the way, you can set the value for the app variable (in the outputint64 function), in one line only:

__int64 app = *((__int64*)&mem[i]);


:)


尊敬的enhzflep,Jochen Arndt和Shmuel Zang,

非常感谢您的建议.
由于您的帮助,我可以完成我的工作.
如你所说,我用无符号的短.工作做得很好.

我还将练习_byteswap_uint64(),*((__ int64 *)&mem [i]来提高我的编程知识.

非常感谢您的帮助
Dear enhzflep, Jochen Arndt and Shmuel Zang,

Thank you very much for your advice.
Because of your help, I can finish my job.
I used unsigned short as you said. The work is done well.

I will also practice _byteswap_uint64(), *((__int64*)&mem[i] for improving my programming knowledge.

Thanks a lot for your helps


这篇关于从二进制文件读取8字节数据的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆