C# FileStream Seek/ReadByte似乎颠倒了文件的字节顺序
我不明白我从下面被黑客攻击的代码中得到的结果,有人能解释一下吗。仅在读取UNICODE编码的文本文件时发生C# FileStream Seek/ReadByte似乎颠倒了文件的字节顺序,c#,unicode,stream,unicode-string,C#,Unicode,Stream,Unicode String,我不明白我从下面被黑客攻击的代码中得到的结果,有人能解释一下吗。仅在读取UNICODE编码的文本文件时发生 fs = File.Open(fileName, FileMode.Open, FileAccess.Read, FileShare.ReadWrite); // read from start byte[] lne = new byte[100]; int actual = fs.Read(lne, 0, lne.Length); string line = Encoding.Unic
fs = File.Open(fileName, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
// read from start
byte[] lne = new byte[100];
int actual = fs.Read(lne, 0, lne.Length);
string line = Encoding.Unicode.GetString(lne, 0, actual); // ok readable stuff as expected
string line1 = Encoding.BigEndianUnicode.GetString(lne, 0, actual); // fail as expected
// move down into the file
fs.Seek(-150, SeekOrigin.End);
fs.ReadByte(); // take this out, works ok!
lne = new byte[100];
actual = fs.Read(lne, 0, lne.Length);
line = encoding.GetString(lne, 0, actual); // fail non readable stuff - NOT EXPECTED
line1 = Encoding.BigEndianUnicode.GetString(lne, 0, actual); // SUCCESS, readable - huh!
很明显,代码不是“真实世界”,它只是我的真实代码正在做什么的分解
在第一次Encoding.Unicode.GetString之后,我可以在变量“line”中看到可读性良好的数据,在“line1”中看到预期的糟糕数据
在第二次Encoding.Unicode.GetString之后,我看到了完整的垃圾(我不知道是日语还是汉语),但是第1行现在包含了来自该文件的可读数据
如果我取出ReadByte,一切正常
任何人都不知道为什么会这样
TIA。您将移动到流的末尾减去100字节。然后你读取一个字节(它将你带到流的末尾减去99个字节),然后你尝试读取100个字节。这将占用流外的一个字节。Unicode字符串为2个字节,ASCII字符串的
0x41, 0, 0x42, 0, 0x43, 0 ... // {ASCII code for A}, 0,...
因此,如果以相反的顺序读取字节(bigendianianunicode
),就会得到无意义的字符。上面的字符串读作0x4100、0x4200、0x4300…
而不是0x0041…
当您开始读取奇数偏移量(从文件代码末尾开始查找)时,也会发生类似情况-带有ASCII文本的字节如下所示:
0, 0x41, 0, 0x42, 0, 0x43 ...
读作0x4100、0x4200、0x4300…
ReadByte
取出第一个0,这样您就可以从字符的开头而不是中间读取,并且序列将变为仅限ASCII的有效Unicode字符串(最后一个字符可能无效:
0x41, 0, 0x42, 0, 0x43,...
考虑使用一个TA,但这并不能解释为什么第一行中有废话,第二行中有好的数据——在第二次读的时候,我已经编辑了代码以去除100/99的差异。是的,我认为这是问题,也不是真正的修复,我只是觉得奇怪的是第二个BIDENANNIONDEO.GETSHIPE产生了有效的可读数据。我想如果我读到“中间”的话对于未编码字符串,接下来的2个字节将显示为相反的。@请注意,第二个
bigendianucode.GetString
将显示非ASCII字符的混乱,因为它将开始从2个字符中选取一半:0x41、0x01、0x42、0x2
从第二个字节开始,将以0x0142
而不是0x0141结束e> 或0x0242
。