Browse Source

Fixes bug #19986: Patch zipper.pp for create zip file output to TStream support

git-svn-id: trunk@19025 -
sekelsenmat 14 years ago
parent
commit
2ea96e08fa
1 changed files with 51 additions and 49 deletions
  1. 51 49
      packages/paszlib/src/zipper.pp

+ 51 - 49
packages/paszlib/src/zipper.pp

@@ -303,7 +303,7 @@ Type
     FFileName   :  String;         { Name of resulting Zip file                 }
     FFileName   :  String;         { Name of resulting Zip file                 }
     FFiles      : TStrings;
     FFiles      : TStrings;
     FInMemSize  : Integer;
     FInMemSize  : Integer;
-    FOutFile    : TFileStream;
+    FOutStream  : TStream;
     FInFile     : TStream;     { I/O file variables                         }
     FInFile     : TStream;     { I/O file variables                         }
     LocalHdr    : Local_File_Header_Type;
     LocalHdr    : Local_File_Header_Type;
     CentralHdr  : Central_File_Header_Type;
     CentralHdr  : Central_File_Header_Type;
@@ -315,8 +315,6 @@ Type
     function CheckEntries: Integer;
     function CheckEntries: Integer;
     procedure SetEntries(const AValue: TZipFileEntries);
     procedure SetEntries(const AValue: TZipFileEntries);
   Protected
   Protected
-    Procedure OpenOutput;
-    Procedure CloseOutput;
     Procedure CloseInput(Item : TZipFileEntry);
     Procedure CloseInput(Item : TZipFileEntry);
     Procedure StartZipFile(Item : TZipFileEntry);
     Procedure StartZipFile(Item : TZipFileEntry);
     Function  UpdateZipHeader(Item : TZipFileEntry; FZip : TStream; ACRC : LongWord;AMethod : Word) : Boolean;
     Function  UpdateZipHeader(Item : TZipFileEntry; FZip : TStream; ACRC : LongWord;AMethod : Word) : Boolean;
@@ -332,6 +330,8 @@ Type
     Constructor Create;
     Constructor Create;
     Destructor Destroy;override;
     Destructor Destroy;override;
     Procedure ZipAllFiles; virtual;
     Procedure ZipAllFiles; virtual;
+    Procedure SaveToFile(AFileName: string);
+    Procedure SaveToStream(AStream: TStream);
     Procedure ZipFiles(AFileName : String; FileList : TStrings);
     Procedure ZipFiles(AFileName : String; FileList : TStrings);
     Procedure ZipFiles(FileList : TStrings);
     Procedure ZipFiles(FileList : TStrings);
     Procedure ZipFiles(AFileName : String; Entries : TZipFileEntries);
     Procedure ZipFiles(AFileName : String; Entries : TZipFileEntries);
@@ -1202,13 +1202,6 @@ begin
   FEntries.Assign(AValue);
   FEntries.Assign(AValue);
 end;
 end;
 
 
-Procedure TZipper.OpenOutput;
-
-Begin
-  FOutFile:=TFileStream.Create(FFileName,fmCreate);
-End;
-
-
 Function TZipper.OpenInput(Item : TZipFileEntry) : Boolean;
 Function TZipper.OpenInput(Item : TZipFileEntry) : Boolean;
 
 
 Begin
 Begin
@@ -1225,13 +1218,6 @@ Begin
 End;
 End;
 
 
 
 
-Procedure TZipper.CloseOutput;
-
-Begin
-  FreeAndNil(FOutFile);
-end;
-
-
 Procedure TZipper.CloseInput(Item : TZipFileEntry);
 Procedure TZipper.CloseInput(Item : TZipFileEntry);
 
 
 Begin
 Begin
@@ -1280,8 +1266,8 @@ Begin
       Compressed_Size := Uncompressed_Size;  { ...update compressed size   }
       Compressed_Size := Uncompressed_Size;  { ...update compressed size   }
       end;
       end;
     end;
     end;
-  FOutFile.WriteBuffer({$IFDEF ENDIAN_BIG}SwapLFH{$ENDIF}(LocalHdr),SizeOf(LocalHdr));
-  FOutFile.WriteBuffer(ZFileName[1],Length(ZFileName));
+  FOutStream.WriteBuffer({$IFDEF ENDIAN_BIG}SwapLFH{$ENDIF}(LocalHdr),SizeOf(LocalHdr));
+  FOutStream.WriteBuffer(ZFileName[1],Length(ZFileName));
 End;
 End;
 
 
 
 
@@ -1296,17 +1282,17 @@ Var
 
 
 Begin
 Begin
    ACount := 0;
    ACount := 0;
-   CenDirPos := FOutFile.Position;
-   FOutFile.Seek(0,soFrombeginning);             { Rewind output file }
-   HdrPos := FOutFile.Position;
-   FOutFile.ReadBuffer(LocalHdr, SizeOf(LocalHdr));
+   CenDirPos := FOutStream.Position;
+   FOutStream.Seek(0,soFrombeginning);             { Rewind output file }
+   HdrPos := FOutStream.Position;
+   FOutStream.ReadBuffer(LocalHdr, SizeOf(LocalHdr));
 {$IFDEF FPC_BIG_ENDIAN}
 {$IFDEF FPC_BIG_ENDIAN}
    LocalHdr := SwapLFH(LocalHdr);
    LocalHdr := SwapLFH(LocalHdr);
 {$ENDIF}
 {$ENDIF}
    Repeat
    Repeat
      SetLength(ZFileName,LocalHdr.FileName_Length);
      SetLength(ZFileName,LocalHdr.FileName_Length);
-     FOutFile.ReadBuffer(ZFileName[1], LocalHdr.FileName_Length);
-     SavePos := FOutFile.Position;
+     FOutStream.ReadBuffer(ZFileName[1], LocalHdr.FileName_Length);
+     SavePos := FOutStream.Position;
      FillChar(CentralHdr,SizeOf(CentralHdr),0);
      FillChar(CentralHdr,SizeOf(CentralHdr),0);
      With CentralHdr do
      With CentralHdr do
        begin
        begin
@@ -1328,18 +1314,18 @@ Begin
      {$ENDIF}
      {$ENDIF}
        Local_Header_Offset := HdrPos;
        Local_Header_Offset := HdrPos;
        end;
        end;
-     FOutFile.Seek(0,soFromEnd);
-     FOutFile.WriteBuffer({$IFDEF FPC_BIG_ENDIAN}SwapCFH{$ENDIF}(CentralHdr),SizeOf(CentralHdr));
-     FOutFile.WriteBuffer(ZFileName[1],Length(ZFileName));
+     FOutStream.Seek(0,soFromEnd);
+     FOutStream.WriteBuffer({$IFDEF FPC_BIG_ENDIAN}SwapCFH{$ENDIF}(CentralHdr),SizeOf(CentralHdr));
+     FOutStream.WriteBuffer(ZFileName[1],Length(ZFileName));
      Inc(ACount);
      Inc(ACount);
-     FOutFile.Seek(SavePos + LocalHdr.Compressed_Size,soFromBeginning);
-     HdrPos:=FOutFile.Position;
-     FOutFile.ReadBuffer(LocalHdr, SizeOf(LocalHdr));
+     FOutStream.Seek(SavePos + LocalHdr.Compressed_Size,soFromBeginning);
+     HdrPos:=FOutStream.Position;
+     FOutStream.ReadBuffer(LocalHdr, SizeOf(LocalHdr));
 {$IFDEF FPC_BIG_ENDIAN}
 {$IFDEF FPC_BIG_ENDIAN}
      LocalHdr := SwapLFH(LocalHdr);
      LocalHdr := SwapLFH(LocalHdr);
 {$ENDIF}
 {$ENDIF}
    Until LocalHdr.Signature = CENTRAL_FILE_HEADER_SIGNATURE;
    Until LocalHdr.Signature = CENTRAL_FILE_HEADER_SIGNATURE;
-   FOutFile.Seek(0,soFromEnd);
+   FOutStream.Seek(0,soFromEnd);
    FillChar(EndHdr,SizeOf(EndHdr),0);
    FillChar(EndHdr,SizeOf(EndHdr),0);
    With EndHdr do
    With EndHdr do
      begin
      begin
@@ -1348,10 +1334,10 @@ Begin
      Central_Dir_Start_Disk := 0;
      Central_Dir_Start_Disk := 0;
      Entries_This_Disk := ACount;
      Entries_This_Disk := ACount;
      Total_Entries := ACount;
      Total_Entries := ACount;
-     Central_Dir_Size := FOutFile.Size-CenDirPos;
+     Central_Dir_Size := FOutStream.Size-CenDirPos;
      Start_Disk_Offset := CenDirPos;
      Start_Disk_Offset := CenDirPos;
      ZipFile_Comment_Length := 0;
      ZipFile_Comment_Length := 0;
-     FOutFile.WriteBuffer({$IFDEF FPC_BIG_ENDIAN}SwapECD{$ENDIF}(EndHdr), SizeOf(EndHdr));
+     FOutStream.WriteBuffer({$IFDEF FPC_BIG_ENDIAN}SwapECD{$ENDIF}(EndHdr), SizeOf(EndHdr));
      end;
      end;
 end;
 end;
 
 
@@ -1393,12 +1379,12 @@ Begin
         end;
         end;
       If UpdateZipHeader(Item,ZipStream,CRC,ZMethod) then
       If UpdateZipHeader(Item,ZipStream,CRC,ZMethod) then
         // Compressed file smaller than original file.
         // Compressed file smaller than original file.
-        FOutFile.CopyFrom(ZipStream,0)
+        FOutStream.CopyFrom(ZipStream,0)
       else
       else
         begin
         begin
         // Original file smaller than compressed file.
         // Original file smaller than compressed file.
         FInfile.Seek(0,soFromBeginning);
         FInfile.Seek(0,soFromBeginning);
-        FOutFile.CopyFrom(FInFile,0);
+        FOutStream.CopyFrom(FInFile,0);
         end;
         end;
     finally
     finally
       ZipStream.Free;
       ZipStream.Free;
@@ -1410,30 +1396,46 @@ Begin
   end;
   end;
 end;
 end;
 
 
+// Just like SaveToFile, but uses the FileName property
 Procedure TZipper.ZipAllFiles;
 Procedure TZipper.ZipAllFiles;
 
 
+Begin
+  SaveToFile(FileName);
+end;
+
+procedure TZipper.SaveToFile(AFileName: string);
+var
+  lStream: TFileStream;
+begin
+  lStream:=TFileStream.Create(FFileName,fmCreate);
+  try
+    SaveToStream(lStream);
+  finally
+    FreeAndNil(lStream);
+  end;
+end;
+
+procedure TZipper.SaveToStream(AStream: TStream);
 Var
 Var
    I : Integer;
    I : Integer;
    filecnt : integer;
    filecnt : integer;
-Begin
+begin
+  FOutStream := AStream;
+
   If CheckEntries=0 then
   If CheckEntries=0 then
     Exit;
     Exit;
   FZipping:=True;
   FZipping:=True;
   Try
   Try
     GetFileInfo;
     GetFileInfo;
-    OpenOutput;
-    Try
-      filecnt:=0;
-      For I:=0 to FEntries.Count-1 do
-        begin
-        ZipOneFile(FEntries[i]);
-        inc(filecnt);
-        end;
-      if filecnt>0 then
-        BuildZipDirectory;
-    finally
-      CloseOutput;
+
+    filecnt:=0;
+    for I:=0 to FEntries.Count-1 do
+    begin
+      ZipOneFile(FEntries[i]);
+      inc(filecnt);
     end;
     end;
+    if filecnt>0 then
+      BuildZipDirectory;
   finally
   finally
     FZipping:=False;
     FZipping:=False;
     // Remove entries that have been added by CheckEntries from Files.
     // Remove entries that have been added by CheckEntries from Files.