我正在执行两个函数来连接和分割TFileStream中的文件,代码如下:
加入
procedure TFormHome.btnJoinClick(Sender: TObject);
var
InStream, OutStream: TFileStream;
OutFileName, InFileName1, InFileName2: string;
begin
OutFileName := 'salida.out';
InFileName1 := 'image.jpg';
InFileName2 := 'test.exe';
OutStream := TFileStream.Create(OutFileName, fmCreate);
try
InStream := TFileStream.Create(InFileName1, fmOpenRead);
ShowMessage(IntToStr(InStream.Size));
try
OutStream.CopyFrom(InStream, InStream.Size);
finally
InStream.Free;
end;
InStream := TFileStream.Create(InFileName2, fmOpenRead);
ShowMessage(IntToStr(InStream.Size));
try
OutStream.CopyFrom(InStream, InStream.Size);
finally
InStream.Free;
end;
finally
OutStream.Free;
end;
end;除法
procedure TFormHome.btnUnJoinClick(Sender: TObject);
var
Source, Target: TStream;
Buffer: array of Byte;
i: Integer;
SourceName, TargetNames: string;
SizeTargets: Integer;
begin
SourceName := 'salida.out';
TargetNames := 'test.exe';
SizeTargets := 2232832;
Source := TFileStream.Create(SourceName, fmOpenRead);
Target := TFileStream.Create(TargetNames, fmCreate);
try
SetLength(Buffer, SizeTargets);
Source.ReadBuffer(Pointer(Buffer)^, Length(Buffer));
Target.WriteBuffer(Buffer[0], Length(Buffer));
finally
Target.Free;
end;
end;问题是,当我划分文件时,当我想显示如下错误时,可执行文件中断并运行:
Windows can not find the file "route ..." Make sure the name is spelled correctly and try again或
The version of this file is not compatible with the version of Windows you are running ... (and then talking about 32 or 64 bits)另外,检查第二个函数中可执行文件的大小是否正确。
问题是,在第二个代码中,所有的文件都被破坏了
我该如何解决这个问题?
发布于 2016-09-22 03:28:23
您正在将多个输入文件联接在一起,而没有在输出中指明一个文件的结束位置和下一个文件的开始位置。divide代码不知道哪些字节属于JPG,哪些字节属于EXE。
例如,您所显示的divide代码提取JPG字节并将它们保存到.exe文件中。所以.exe文件当然不会正确运行。
为了提取EXE,您必须首先提取/跳过JPG,这意味着您必须知道JPG中有多少字节。因此,您需要将输入文件大小存储在连接的输出中,而不仅仅是它们的数据,例如:
procedure TFormHome.btnJoinClick(Sender: TObject);
var
OutStream: TFileStream;
procedure AddFile(const FileName: sstring);
var
InStream: TStream;
Size: Int64;
begin
InStream := TFileStream.Create(FileName, fmOpenRead or fmShareDenyWrite);
try
Size := InStream.Size;
OutStream.WriteBuffer(Size, SizeOf(Size));
OutStream.CopyFrom(InStream, Size);
finally
InStream.Free;
end;
end;
begin
OutStream := TFileStream.Create('salida.out', fmCreate);
try
AddFile('image.jpg');
AddFile('test.exe');
finally
OutStream.Free;
end;
end;
procedure TFormHome.btnUnJoinClick(Sender: TObject);
var
Source: TStream;
procedure SkipFile;
var
Size: Int64;
begin
Source.ReadBuffer(Size, SizeOf(Size));
Source.Seek(Size, soCurrent);
end;
procedure ExtractFile(const FileName: string);
var
Target: TStream;
Size: Int64;
begin
Source.ReadBuffer(Size, SizeOf(Size));
Target := TFileStream.Create(FileName, fmCreate);
try
Target.CopyFrom(Source, Size);
finally
Target.Free;
end;
end;
begin
Source := TFileStream.Create('salida.out', fmOpenRead or fmShareDenyWrite);
try
SkipFile;
ExtractFile('test.exe');
finally
Source.Free;
end;
end;我建议您也考虑存储文件名:
procedure TFormHome.btnJoinClick(Sender: TObject);
var
OutStream: TFileStream;
procedure AddFile(const FileName: string);
var
InStream: TStream;
Name: UTF8String;
Len: Integer;
FileSize, TotalSize: Int64;
begin
InStream := TFileStream.Create(FileName, fmOpenRead or fmShareDenyWrite);
try
Name := UTF8String(ExtractFileName(FileName));
Len := Length(Name);
FileSize := InStream.Size;
TotalSize := SizeOf(Len) + Len + SizeOf(FileSize) + FileSize;
OutStream.WriteBuffer(TotalSize, SizeOf(TotalSize));
OutStream.WriteBuffer(Len, SizeOf(Len));
OutStream.WriteBuffer(PAnsiChar(Name)^, Len);
OutStream.WriteBuffer(FileSize, SizeOf(FileSize));
OutStream.CopyFrom(InStream, FileSize);
finally
InStream.Free;
end;
end;
begin
OutStream := TFileStream.Create('salida.out', fmCreate);
try
AddFile('image.jpg');
AddFile('test.exe');
finally
OutStream.Free;
end;
end;
procedure TFormHome.btnUnJoinClick(Sender: TObject);
var
Source: TStream;
procedure SkipFile;
var
TotalSize: Int64;
begin
Source.ReadBuffer(TotalSize, SizeOf(TotalSize));
Source.Seek(TotalSize, soCurrent);
end;
procedure ExtractFile;
var
Target: TStream;
TotalSize, FileSize: Int64;
Name: UTF8String;
Len: Integer;
Pos: Int64;
begin
Source.ReadBuffer(TotalSize, SizeOf(TotalSize));
Pos := Source.Position;
Source.ReadBuffer(Len, SizeOf(Len));
SetLength(Name, Len);
Source.ReadBuffer(PAnsiChar(Name)^, Len);
Source.ReadBuffer(FileSize, SizeOf(FileSize));
Target := TFileStream.Create(String(Name), fmCreate);
try
Target.CopyFrom(Source, FileSize);
finally
Target.Free;
end;
if (Source.Position - Pos) <> TotalSize then
raise Exception.Create('Extract failed. Bad position');
end;
begin
Source := TFileStream.Create('salida.out', fmOpenRead or fmShareDenyWrite);
try
SkipFile;
ExtractFile;
finally
Source.Free;
end;
end;https://stackoverflow.com/questions/39623278
复制相似问题