计算31位数字/忽略最高有效位
本文关键字:有效位 31位 数字 计算 | 更新日期: 2023-09-27 17:50:59
我正在研究一个分析E01比特流图像的软件。基本上,这些是取证数据文件,允许用户将磁盘上的所有数据压缩到单个文件中。E01格式嵌入了关于原始数据的数据,包括源数据和结果数据的MD5哈希值等。如果您对一些轻松的阅读感兴趣,请参阅EWF/E01规范。关于我的问题:
e01文件包含一个"table"部分,它是一系列32位数字,这些数字是e01文件中实际数据块所在位置的偏移量。我已经成功地将这些数据解析成一个列表,执行以下操作:
this.ChunkLocations = new List<int>();
//hack:Will this overflow? We are adding to integers to a long?
long currentReadLocation = TableSectionDescriptorRef.OffsetFromFileStart + c_SECTION_DESCRIPTOR_LENGTH + c_TABLE_HEADER_LENGTH;
byte[] currReadBytes;
using (var fs = new FileStream(E01File.FullName, FileMode.Open))
{
fs.Seek(currentReadLocation, 0);
for (int i = 0; i < NumberOfEntries; i++)
{
currReadBytes = new byte[c_CHUNK_DATA_OFFSET_LENGTH];
fs.Read(currReadBytes,0, c_CHUNK_DATA_OFFSET_LENGTH);
this.ChunkLocations.Add(BitConverter.ToUInt32(currReadBytes, 0));
}
}
c_CHUNK_DATA_OFFSET_LENGTH为4字节/"32位"数。
根据ewf/e01规范,"块数据偏移量中的最高有效位表示块是压缩(1)还是未压缩(0)"。事实似乎证明了这一点,如果我将偏移量转换为整数,结果中会有很大的负数(对于没有压缩的块,毫无疑问),但大多数其他偏移量似乎都是正确递增的,但偶尔会出现疯狂的数据。ChunkLocations中的数据看起来像这样:
346256 379028 -2147071848 444556 477328 510100
在-2147071848中,MSB似乎被翻转以指示压缩/缺乏压缩。
问题:所以,如果MSB被用来标记压缩的存在,那么我真的在处理31位的数字,对吗?
1. 我如何忽略MSB/计算一个31位的数字在计算偏移值?
2. 这似乎是一个奇怪的标准,因为它似乎会大大限制你可以拥有的偏移量的大小,所以我在质疑我是否遗漏了什么?当我导航到e01文件中的这些位置时,这些偏移量看起来是正确的。
谢谢你的帮助!
这类事情在处理二进制格式时很典型。正如dtb所指出的,对于这个应用程序来说,31位可能已经足够大了,因为它可以处理高达2gb的偏移量。所以他们使用额外的位作为标志来节省空间。
你可以用一个按位AND来屏蔽掉这个位:
const UInt32 COMPRESSED = 0x80000000; // Only bit 31 on
UInt32 raw_value = 0x80004000; // test value
bool compressed = (raw_value & COMPRESSED) > 0;
UInt32 offset = raw_value & ~COMPRESSED;
Console.WriteLine("Compressed={0} Offset=0x{1:X}", compressed, offset);
输出:Compressed=True Offset=0x4000
如果您只想去掉前导位,则使用0x7FFFFFFF