17a575b8a328489783cc230aa523bdda0bc62359
1 (* Copyright (C) DooM 2D:Forever Developers
2 *
3 * This program is free software: you can redistribute it and/or modify
4 * it under the terms of the GNU General Public License as published by
5 * the Free Software Foundation, either version 3 of the License, or
6 * (at your option) any later version.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 *
13 * You should have received a copy of the GNU General Public License
14 * along with this program. If not, see <http://www.gnu.org/licenses/>.
15 *)
16 // special stream classes
17 {$MODE DELPHI}
18 {$R+}
21 interface
23 uses
28 type
31 // read-only ïîòîê äëÿ èçâëå÷åíèÿ èç èñõîäíîãî òîëüêî êóñî÷êà
33 protected
44 public
45 // aSrc: ïîòîê-èñõîäíèê.
46 // aPos: íà÷àëüíàÿ ïîçèöèÿ â ïîòîêå. -1 -- ñ òåêóùåé.
47 // åñëè aPos < òåêóùåé ïîçèöèè, òî èñõîäíûé ïîòîê äîëæåí
48 // íîðìàëüíî ïîääåðæèâàòü Seek()!
49 // aSize: êîëè÷åñòâî áàéòèêîâ, êîòîðîå ìîæíî ïðî÷åñòü èç ïîòîêà.
50 // åñëè ìåíüøå íóëÿ -- òî äî êîíöà.
51 // aKillSrc: óáèâàòü ëè èñõîäíûé ïîòîê, êîãäà ñàìè óìèðàåì?
52 // òàêæå ìîæåò ïðèøïàíäîðèòü ê íà÷àëó ôàéëà áóôåð. bufSz áóäåò äîáàâëåíî ê
53 // äëèíå ôàéëà.
54 constructor Create (aSrc: TStream; aPos, aSize: Int64; aKillSrc: Boolean; preBuf: Pointer=nil; bufSz: Integer=0);
57 // íîðìàëèçóåò count è ÷èòàåò.
59 // Write() ïðîñòî ãðîìêî ïàäàåò.
61 // Seek() ðåàëèçîâàíî, ÷òîáû ìîãëà ðàáîòàòü ïðîïåðòÿ Size.
62 // âîîáùå-òî ìîæíî ïåðåêðûòü ìåòîä GetSize(), íî âäðóã êàêîé
63 // áîëüíîé íà ãîëîâó êîäåð áóäåò ïîëó÷àòü ðàçìåð ïðè ïîìîùè
64 // Seek()'à?
68 // this stream can kill both `proxied` and `guarded` streams on closing
70 protected
77 public
78 // aSrc: ïîòîê-èñõîäíèê (íà êîòîðûé çàìàïåíû îïåðàöèè ÷òåíèÿ/çàïèñè).
79 // aKillSrc: óáèâàòü ëè èñõîäíûé ïîòîê, êîãäà ñàìè óìèðàåì?
80 // aKillGuarded: óáèâàòü ëè îõðàíÿåìûé ïîòîê, êîãäà ñàìè óìèðàåì?
81 // aGuardedFirst: true: ïðè ñìåðòè ïåðâûì ïðèøèáàåì îõðàíÿåìîãî.
82 constructor Create (aSrc, aGuarded: TStream; aKillSrc, aKillGuarded: Boolean; aGuardedFirst: Boolean=true);
85 // íèæåñëåäóþùåå çàìàïëåíî íà fSource
92 private
96 public
104 protected
120 public
121 // `aSize` can be -1 if stream size is unknown
122 constructor create (asrc: TStream; aSize: Int64; aKillSrc: Boolean; aSkipHeader: boolean=false);
130 implementation
132 uses
133 zinflate;
136 { TSFSPartialStream }
137 constructor TSFSPartialStream.Create (aSrc: TStream; aPos, aSize: Int64; aKillSrc: Boolean; preBuf: Pointer=nil; bufSz: Integer=0);
138 begin
150 begin
154 end
155 else
156 begin
162 begin
168 begin
169 {
170 if fSource.Position <> fStartPos+fCurrentPos-Length(fPreBuf) then
171 begin
172 fSource.Position := fStartPos+fCurrentPos-Length(fPreBuf);
173 end;
174 }
176 begin
177 //writeln('seeking at ', fCurrentPos, ' (real: ', fStartPos+fCurrentPos-Length(fPreBuf), ')');
184 begin
187 // à íå õîäè, íåõîðîøèé, â íàø ñàäèê ãóëÿòü!
191 var
195 begin
201 begin
206 begin
220 begin
225 end
226 else
227 begin
233 begin
239 // äðóãèõ íå áûâàåò. à ó êîãî áûâàåò, òîìó ÿ íå äîêòîð.
247 { TSFSGuardStream }
248 constructor TSFSGuardStream.Create (aSrc, aGuarded: TStream; aKillSrc, aKillGuarded: Boolean; aGuardedFirst: Boolean=true);
249 begin
257 begin
265 begin
270 begin
275 begin
280 { TSFSMemoryStreamRO }
282 begin
291 begin
296 begin
299 // ñîâñåì ñáðåíäèë...
303 // ////////////////////////////////////////////////////////////////////////// //
304 { TUnZStream }
305 const ZBufSize = 32768; // size of the buffer used for temporarily storing data from the child stream
308 constructor TUnZStream.create (asrc: TStream; aSize: Int64; aKillSrc: Boolean; aSkipHeader: boolean=false);
309 var
311 begin
327 begin
336 var
339 begin
343 begin
348 begin
350 begin
351 // refill the buffer
367 var
370 begin
372 //writeln('fixing pos: fPos=', fPos, '; fSkipToPos=', fSkipToPos);
375 begin
377 //writeln(' reading ', rd, ' bytes...');
379 //writeln(' got ', rr, ' bytes; fPos=', fPos, '; fSkipToPos=', fSkipToPos);
382 //writeln(' pos: fPos=', fPos, '; fSkipToPos=', fSkipToPos);
388 var
392 begin
395 try
396 //writeln('determining unzstream size...');
398 begin
403 //writeln(' unzstream size is ', fSize);
404 finally
411 begin
418 begin
425 var
427 begin
428 //writeln('doing RESET');
439 var
441 begin
449 // äðóãèõ íå áûâàåò. à ó êîãî áûâàåò, òîìó ÿ íå äîêòîð.
453 //writeln('seek: ofs=', offset, '; origin=', origin, '; result=', result);