]> git.saurik.com Git - wxWidgets.git/blame - include/wx/tarstrm.h
simpler implementation that also works over remote connections by Kevin O.
[wxWidgets.git] / include / wx / tarstrm.h
CommitLineData
dd1462c3 1/////////////////////////////////////////////////////////////////////////////
ce7208d4 2// Name: wx/tarstrm.h
dd1462c3
MW
3// Purpose: Streams for Tar files
4// Author: Mike Wetherell
5// RCS-ID: $Id$
6// Copyright: (c) 2004 Mike Wetherell
7// Licence: wxWindows licence
8/////////////////////////////////////////////////////////////////////////////
9
10#ifndef _WX_WXTARSTREAM_H__
11#define _WX_WXTARSTREAM_H__
12
13#include "wx/defs.h"
14
15#if wxUSE_TARSTREAM
16
17#include "wx/archive.h"
77b5dc95 18#include "wx/hashmap.h"
dd1462c3
MW
19
20
21/////////////////////////////////////////////////////////////////////////////
22// Constants
23
24// TypeFlag values
c6cf894a
FM
25enum wxTarType
26{
dd1462c3
MW
27 wxTAR_REGTYPE = '0', // regular file
28 wxTAR_LNKTYPE = '1', // hard link
29 wxTAR_SYMTYPE = '2', // symbolic link
30 wxTAR_CHRTYPE = '3', // character special
31 wxTAR_BLKTYPE = '4', // block special
32 wxTAR_DIRTYPE = '5', // directory
33 wxTAR_FIFOTYPE = '6', // named pipe
34 wxTAR_CONTTYPE = '7' // contiguous file
35};
36
37// Archive Formats (use wxTAR_PAX, it's backward compatible)
38enum wxTarFormat
39{
40 wxTAR_USTAR, // POSIX.1-1990 tar format
41 wxTAR_PAX // POSIX.1-2001 tar format
42};
43
44
45/////////////////////////////////////////////////////////////////////////////
46// wxTarNotifier
47
46b15bd5 48class WXDLLIMPEXP_BASE wxTarNotifier
dd1462c3
MW
49{
50public:
51 virtual ~wxTarNotifier() { }
52
53 virtual void OnEntryUpdated(class wxTarEntry& entry) = 0;
54};
55
56
57/////////////////////////////////////////////////////////////////////////////
58// Tar Entry - hold the meta data for a file in the tar
59
46b15bd5 60class WXDLLIMPEXP_BASE wxTarEntry : public wxArchiveEntry
dd1462c3
MW
61{
62public:
63 wxTarEntry(const wxString& name = wxEmptyString,
64 const wxDateTime& dt = wxDateTime::Now(),
65 wxFileOffset size = wxInvalidOffset);
66 virtual ~wxTarEntry();
67
68 wxTarEntry(const wxTarEntry& entry);
69 wxTarEntry& operator=(const wxTarEntry& entry);
70
71 // Get accessors
72 wxString GetName(wxPathFormat format = wxPATH_NATIVE) const;
73 wxString GetInternalName() const { return m_Name; }
74 wxPathFormat GetInternalFormat() const { return wxPATH_UNIX; }
75 int GetMode() const;
76 int GetUserId() const { return m_UserId; }
77 int GetGroupId() const { return m_GroupId; }
78 wxFileOffset GetSize() const { return m_Size; }
79 wxFileOffset GetOffset() const { return m_Offset; }
80 wxDateTime GetDateTime() const { return m_ModifyTime; }
81 wxDateTime GetAccessTime() const { return m_AccessTime; }
82 wxDateTime GetCreateTime() const { return m_CreateTime; }
83 int GetTypeFlag() const { return m_TypeFlag; }
84 wxString GetLinkName() const { return m_LinkName; }
85 wxString GetUserName() const { return m_UserName; }
86 wxString GetGroupName() const { return m_GroupName; }
87 int GetDevMajor() const { return m_DevMajor; }
88 int GetDevMinor() const { return m_DevMinor; }
89
90 // is accessors
91 bool IsDir() const;
92 bool IsReadOnly() const { return !(m_Mode & 0222); }
93
94 // set accessors
95 void SetName(const wxString& name, wxPathFormat format = wxPATH_NATIVE);
96 void SetUserId(int id) { m_UserId = id; }
97 void SetGroupId(int id) { m_GroupId = id; }
98 void SetMode(int mode);
99 void SetSize(wxFileOffset size) { m_Size = size; }
100 void SetDateTime(const wxDateTime& dt) { m_ModifyTime = dt; }
101 void SetAccessTime(const wxDateTime& dt) { m_AccessTime = dt; }
102 void SetCreateTime(const wxDateTime& dt) { m_CreateTime = dt; }
103 void SetTypeFlag(int type) { m_TypeFlag = type; }
104 void SetLinkName(const wxString& link) { m_LinkName = link; }
105 void SetUserName(const wxString& user) { m_UserName = user; }
106 void SetGroupName(const wxString& group) { m_GroupName = group; }
107 void SetDevMajor(int dev) { m_DevMajor = dev; }
108 void SetDevMinor(int dev) { m_DevMinor = dev; }
109
110 // set is accessors
111 void SetIsDir(bool isDir = true);
112 void SetIsReadOnly(bool isReadOnly = true);
113
114 static wxString GetInternalName(const wxString& name,
115 wxPathFormat format = wxPATH_NATIVE,
116 bool *pIsDir = NULL);
117
118 wxTarEntry *Clone() const { return new wxTarEntry(*this); }
119
120 void SetNotifier(wxTarNotifier& WXUNUSED(notifier)) { }
121
e3a10e0c 122private:
dd1462c3 123 void SetOffset(wxFileOffset offset) { m_Offset = offset; }
e3a10e0c 124
dd1462c3
MW
125 virtual wxArchiveEntry* DoClone() const { return Clone(); }
126
127 wxString m_Name;
128 int m_Mode;
129 bool m_IsModeSet;
130 int m_UserId;
131 int m_GroupId;
132 wxFileOffset m_Size;
133 wxFileOffset m_Offset;
134 wxDateTime m_ModifyTime;
135 wxDateTime m_AccessTime;
136 wxDateTime m_CreateTime;
5f77e766 137 int m_TypeFlag;
dd1462c3
MW
138 wxString m_LinkName;
139 wxString m_UserName;
140 wxString m_GroupName;
141 int m_DevMajor;
142 int m_DevMinor;
143
144 friend class wxTarInputStream;
145
146 DECLARE_DYNAMIC_CLASS(wxTarEntry)
147};
148
149
150/////////////////////////////////////////////////////////////////////////////
151// wxTarInputStream
152
45c64b28
MW
153WX_DECLARE_STRING_HASH_MAP(wxString, wxTarHeaderRecords);
154
46b15bd5 155class WXDLLIMPEXP_BASE wxTarInputStream : public wxArchiveInputStream
dd1462c3
MW
156{
157public:
158 typedef wxTarEntry entry_type;
159
160 wxTarInputStream(wxInputStream& stream, wxMBConv& conv = wxConvLocal);
161 wxTarInputStream(wxInputStream *stream, wxMBConv& conv = wxConvLocal);
162 virtual ~wxTarInputStream();
163
164 bool OpenEntry(wxTarEntry& entry);
165 bool CloseEntry();
166
167 wxTarEntry *GetNextEntry();
168
169 wxFileOffset GetLength() const { return m_size; }
170 bool IsSeekable() const { return m_parent_i_stream->IsSeekable(); }
171
172protected:
173 size_t OnSysRead(void *buffer, size_t size);
174 wxFileOffset OnSysTell() const { return m_pos; }
175 wxFileOffset OnSysSeek(wxFileOffset seek, wxSeekMode mode);
176
177private:
178 void Init();
179
e3a10e0c
MW
180 wxArchiveEntry *DoGetNextEntry() { return GetNextEntry(); }
181 bool OpenEntry(wxArchiveEntry& entry);
dd1462c3
MW
182 bool IsOpened() const { return m_pos != wxInvalidOffset; }
183
184 wxStreamError ReadHeaders();
45c64b28 185 bool ReadExtendedHeader(wxTarHeaderRecords*& recs);
dd1462c3
MW
186
187 wxString GetExtendedHeader(const wxString& key) const;
188 wxString GetHeaderPath() const;
189 wxFileOffset GetHeaderNumber(int id) const;
190 wxString GetHeaderString(int id) const;
191 wxDateTime GetHeaderDate(const wxString& key) const;
192
193 wxFileOffset m_pos; // position within the current entry
194 wxFileOffset m_offset; // offset to the start of the entry's data
195 wxFileOffset m_size; // size of the current entry's data
196
197 int m_sumType;
198 int m_tarType;
199 class wxTarHeaderBlock *m_hdr;
45c64b28
MW
200 wxTarHeaderRecords *m_HeaderRecs;
201 wxTarHeaderRecords *m_GlobalHeaderRecs;
dd1462c3 202
c0c133e1 203 wxDECLARE_NO_COPY_CLASS(wxTarInputStream);
dd1462c3
MW
204};
205
206
207/////////////////////////////////////////////////////////////////////////////
208// wxTarOutputStream
209
46b15bd5 210class WXDLLIMPEXP_BASE wxTarOutputStream : public wxArchiveOutputStream
dd1462c3
MW
211{
212public:
213 wxTarOutputStream(wxOutputStream& stream,
214 wxTarFormat format = wxTAR_PAX,
215 wxMBConv& conv = wxConvLocal);
216 wxTarOutputStream(wxOutputStream *stream,
217 wxTarFormat format = wxTAR_PAX,
218 wxMBConv& conv = wxConvLocal);
219 virtual ~wxTarOutputStream();
220
221 bool PutNextEntry(wxTarEntry *entry);
222
223 bool PutNextEntry(const wxString& name,
224 const wxDateTime& dt = wxDateTime::Now(),
225 wxFileOffset size = wxInvalidOffset);
226
227 bool PutNextDirEntry(const wxString& name,
228 const wxDateTime& dt = wxDateTime::Now());
229
230 bool CopyEntry(wxTarEntry *entry, wxTarInputStream& inputStream);
231 bool CopyArchiveMetaData(wxTarInputStream& WXUNUSED(s)) { return true; }
232
233 void Sync();
234 bool CloseEntry();
235 bool Close();
236
237 bool IsSeekable() const { return m_parent_o_stream->IsSeekable(); }
238
239 void SetBlockingFactor(int factor) { m_BlockingFactor = factor; }
240 int GetBlockingFactor() const { return m_BlockingFactor; }
241
242protected:
243 size_t OnSysWrite(const void *buffer, size_t size);
244 wxFileOffset OnSysTell() const { return m_pos; }
245 wxFileOffset OnSysSeek(wxFileOffset pos, wxSeekMode mode);
246
247private:
248 void Init(wxTarFormat format);
249
e3a10e0c
MW
250 bool PutNextEntry(wxArchiveEntry *entry);
251 bool CopyEntry(wxArchiveEntry *entry, wxArchiveInputStream& stream);
252 bool CopyArchiveMetaData(wxArchiveInputStream& WXUNUSED(s)) { return true; }
dd1462c3
MW
253 bool IsOpened() const { return m_pos != wxInvalidOffset; }
254
255 bool WriteHeaders(wxTarEntry& entry);
256 bool ModifyHeader();
257 wxString PaxHeaderPath(const wxString& format, const wxString& path);
258
259 void SetExtendedHeader(const wxString& key, const wxString& value);
260 void SetHeaderPath(const wxString& name);
261 bool SetHeaderNumber(int id, wxFileOffset n);
262 void SetHeaderString(int id, const wxString& str);
263 void SetHeaderDate(const wxString& key, const wxDateTime& datetime);
264
265 wxFileOffset m_pos; // position within the current entry
266 wxFileOffset m_maxpos; // max pos written
267 wxFileOffset m_size; // expected entry size
268
269 wxFileOffset m_headpos; // offset within the file to the entry's header
270 wxFileOffset m_datapos; // offset within the file to the entry's data
271
272 wxFileOffset m_tarstart;// offset within the file to the tar
273 wxFileOffset m_tarsize; // size of tar so far
274
275 bool m_pax;
276 int m_BlockingFactor;
277 wxUint32 m_chksum;
278 bool m_large;
279 class wxTarHeaderBlock *m_hdr;
280 class wxTarHeaderBlock *m_hdr2;
281 char *m_extendedHdr;
282 size_t m_extendedSize;
283 wxString m_badfit;
dd0af4bb 284 bool m_endrecWritten;
dd1462c3 285
c0c133e1 286 wxDECLARE_NO_COPY_CLASS(wxTarOutputStream);
dd1462c3
MW
287};
288
289
290/////////////////////////////////////////////////////////////////////////////
291// Iterators
292
293#if wxUSE_STL || defined WX_TEST_ARCHIVE_ITERATOR
294typedef wxArchiveIterator<wxTarInputStream> wxTarIter;
295typedef wxArchiveIterator<wxTarInputStream,
296 std::pair<wxString, wxTarEntry*> > wxTarPairIter;
297#endif
298
299
300/////////////////////////////////////////////////////////////////////////////
301// wxTarClassFactory
302
46b15bd5 303class WXDLLIMPEXP_BASE wxTarClassFactory : public wxArchiveClassFactory
dd1462c3
MW
304{
305public:
306 typedef wxTarEntry entry_type;
307 typedef wxTarInputStream instream_type;
308 typedef wxTarOutputStream outstream_type;
309 typedef wxTarNotifier notifier_type;
310#if wxUSE_STL || defined WX_TEST_ARCHIVE_ITERATOR
311 typedef wxTarIter iter_type;
312 typedef wxTarPairIter pairiter_type;
313#endif
314
315 wxTarClassFactory();
316
317 wxTarEntry *NewEntry() const
318 { return new wxTarEntry; }
319 wxTarInputStream *NewStream(wxInputStream& stream) const
320 { return new wxTarInputStream(stream, GetConv()); }
321 wxTarOutputStream *NewStream(wxOutputStream& stream) const
322 { return new wxTarOutputStream(stream, wxTAR_PAX, GetConv()); }
323 wxTarInputStream *NewStream(wxInputStream *stream) const
324 { return new wxTarInputStream(stream, GetConv()); }
325 wxTarOutputStream *NewStream(wxOutputStream *stream) const
326 { return new wxTarOutputStream(stream, wxTAR_PAX, GetConv()); }
327
328 wxString GetInternalName(const wxString& name,
329 wxPathFormat format = wxPATH_NATIVE) const
330 { return wxTarEntry::GetInternalName(name, format); }
331
332 const wxChar * const *GetProtocols(wxStreamProtocolType type
333 = wxSTREAM_PROTOCOL) const;
334
335protected:
336 wxArchiveEntry *DoNewEntry() const
337 { return NewEntry(); }
338 wxArchiveInputStream *DoNewStream(wxInputStream& stream) const
339 { return NewStream(stream); }
340 wxArchiveOutputStream *DoNewStream(wxOutputStream& stream) const
341 { return NewStream(stream); }
342 wxArchiveInputStream *DoNewStream(wxInputStream *stream) const
343 { return NewStream(stream); }
344 wxArchiveOutputStream *DoNewStream(wxOutputStream *stream) const
345 { return NewStream(stream); }
346
347private:
348 DECLARE_DYNAMIC_CLASS(wxTarClassFactory)
349};
350
351
352#endif // wxUSE_TARSTREAM
353
354#endif // _WX_WXTARSTREAM_H__