]> git.saurik.com Git - wxWidgets.git/blame_incremental - tests/archive/archivetest.h
Check the return value of system() and pipe() in the test suite.
[wxWidgets.git] / tests / archive / archivetest.h
... / ...
CommitLineData
1///////////////////////////////////////////////////////////////////////////////
2// Name: tests/archive/archivetest.h
3// Purpose: Test the archive classes
4// Author: Mike Wetherell
5// RCS-ID: $Id$
6// Copyright: (c) 2004 Mike Wetherell
7// Licence: wxWindows licence
8///////////////////////////////////////////////////////////////////////////////
9
10#ifndef WX_ARCHIVETEST_INCLUDED
11#define WX_ARCHIVETEST_INCLUDED 1
12
13#define WX_TEST_ARCHIVE_ITERATOR
14
15#include "wx/archive.h"
16#include "wx/wfstream.h"
17
18
19///////////////////////////////////////////////////////////////////////////////
20// Bit flags for options for the tests
21
22enum Options
23{
24 PipeIn = 0x01, // input streams are non-seekable
25 PipeOut = 0x02, // output streams are non-seekable
26 Stub = 0x04, // the archive should be appended to a stub
27 AllOptions = 0x07
28};
29
30
31///////////////////////////////////////////////////////////////////////////////
32// TestOutputStream and TestInputStream are memory streams which can be
33// seekable or non-seekable.
34
35class TestOutputStream : public wxOutputStream
36{
37public:
38 TestOutputStream(int options);
39
40 ~TestOutputStream() { delete [] m_data; }
41
42 int GetOptions() const { return m_options; }
43 wxFileOffset GetLength() const { return m_size; }
44 bool IsSeekable() const { return (m_options & PipeOut) == 0; }
45
46 // gives away the data, this stream is then empty, and can be reused
47 void GetData(char*& data, size_t& size);
48
49private:
50 void Init();
51
52 wxFileOffset OnSysSeek(wxFileOffset pos, wxSeekMode mode);
53 wxFileOffset OnSysTell() const;
54 size_t OnSysWrite(const void *buffer, size_t size);
55
56 int m_options;
57 size_t m_pos;
58 size_t m_capacity;
59 size_t m_size;
60 char *m_data;
61};
62
63class TestInputStream : public wxInputStream
64{
65public:
66 // various streams have implemented eof differently, so check the archive
67 // stream works with all the possibilities (bit flags that can be ORed)
68 enum EofTypes {
69 AtLast = 0x01, // eof before an attempt to read past the last byte
70 WithError = 0x02 // give an error instead of eof
71 };
72
73 // ctor takes the data from the output stream, which is then empty
74 TestInputStream(TestOutputStream& out, int eoftype)
75 : m_data(NULL), m_eoftype(eoftype) { SetData(out); }
76 // this ctor 'dups'
77 TestInputStream(const TestInputStream& in);
78 ~TestInputStream() { delete [] m_data; }
79
80 void Rewind();
81 wxFileOffset GetLength() const { return m_size; }
82 bool IsSeekable() const { return (m_options & PipeIn) == 0; }
83 void SetData(TestOutputStream& out);
84
85 void Chop(size_t size) { m_size = size; }
86 char& operator [](size_t pos) { return m_data[pos]; }
87
88private:
89 wxFileOffset OnSysSeek(wxFileOffset pos, wxSeekMode mode);
90 wxFileOffset OnSysTell() const;
91 size_t OnSysRead(void *buffer, size_t size);
92
93 int m_options;
94 size_t m_pos;
95 size_t m_size;
96 char *m_data;
97 int m_eoftype;
98};
99
100
101///////////////////////////////////////////////////////////////////////////////
102// wxFFile streams for piping to/from an external program
103
104class PFileInputStream : public wxFFileInputStream
105{
106public:
107 PFileInputStream(const wxString& cmd);
108 ~PFileInputStream();
109};
110
111class PFileOutputStream : public wxFFileOutputStream
112{
113public:
114 PFileOutputStream(const wxString& cmd);
115 ~PFileOutputStream();
116};
117
118
119///////////////////////////////////////////////////////////////////////////////
120// A class to hold a test entry
121
122class TestEntry
123{
124public:
125 TestEntry(const wxDateTime& dt, int len, const char *data);
126 ~TestEntry() { delete [] m_data; }
127
128 wxDateTime GetDateTime() const { return m_dt; }
129 wxFileOffset GetLength() const { return m_len; }
130 size_t GetSize() const { return m_len; }
131 const char *GetData() const { return m_data; }
132 wxString GetComment() const { return m_comment; }
133 bool IsText() const { return m_isText; }
134
135 void SetComment(const wxString& comment) { m_comment = comment; }
136 void SetDateTime(const wxDateTime& dt) { m_dt = dt; }
137
138private:
139 wxDateTime m_dt;
140 size_t m_len;
141 char *m_data;
142 wxString m_comment;
143 bool m_isText;
144};
145
146
147///////////////////////////////////////////////////////////////////////////////
148// The test case
149
150template <class ClassFactoryT>
151class ArchiveTestCase : public CppUnit::TestCase
152{
153public:
154 ArchiveTestCase(std::string name,
155 ClassFactoryT *factory,
156 int options,
157 const wxString& archiver = wxEmptyString,
158 const wxString& unarchiver = wxEmptyString);
159
160 ~ArchiveTestCase();
161
162protected:
163 // the classes to test
164 typedef typename ClassFactoryT::entry_type EntryT;
165 typedef typename ClassFactoryT::instream_type InputStreamT;
166 typedef typename ClassFactoryT::outstream_type OutputStreamT;
167 typedef typename ClassFactoryT::notifier_type NotifierT;
168 typedef typename ClassFactoryT::iter_type IterT;
169 typedef typename ClassFactoryT::pairiter_type PairIterT;
170
171 // the entry point for the test
172 void runTest();
173
174 // create the test data
175 void CreateTestData();
176 TestEntry& Add(const char *name, const char *data, int len = -1);
177 TestEntry& Add(const char *name, int len = 0, int value = EOF);
178
179 // 'archive up' the test data
180 void CreateArchive(wxOutputStream& out);
181 void CreateArchive(wxOutputStream& out, const wxString& archiver);
182
183 // perform various modifications on the archive
184 void ModifyArchive(wxInputStream& in, wxOutputStream& out);
185
186 // extract the archive and verify its contents
187 void ExtractArchive(wxInputStream& in);
188 void ExtractArchive(wxInputStream& in, const wxString& unarchiver);
189 void VerifyDir(wxString& path, size_t rootlen = 0);
190
191 // tests for the iterators
192 void TestIterator(wxInputStream& in);
193 void TestPairIterator(wxInputStream& in);
194 void TestSmartIterator(wxInputStream& in);
195 void TestSmartPairIterator(wxInputStream& in);
196
197 // try reading two entries at the same time
198 void ReadSimultaneous(TestInputStream& in);
199
200 // overridables
201 virtual void OnCreateArchive(OutputStreamT& WXUNUSED(arc)) { }
202 virtual void OnSetNotifier(EntryT& entry);
203
204 virtual void OnArchiveExtracted(InputStreamT& WXUNUSED(arc),
205 int WXUNUSED(expectedTotal)) { }
206
207 virtual void OnCreateEntry( OutputStreamT& WXUNUSED(arc),
208 TestEntry& WXUNUSED(testEntry),
209 EntryT *entry = NULL) { (void)entry; }
210
211 virtual void OnEntryExtracted( EntryT& WXUNUSED(entry),
212 const TestEntry& WXUNUSED(testEntry),
213 InputStreamT *arc = NULL) { (void)arc; }
214
215 typedef std::map<wxString, TestEntry*> TestEntries;
216 TestEntries m_testEntries; // test data
217 std::auto_ptr<ClassFactoryT> m_factory; // factory to make classes
218 int m_options; // test options
219 wxDateTime m_timeStamp; // timestamp to give test entries
220 int m_id; // select between the possibilites
221 wxString m_archiver; // external archiver
222 wxString m_unarchiver; // external unarchiver
223};
224
225
226///////////////////////////////////////////////////////////////////////////////
227// Make ids
228
229class TestId
230{
231public:
232 // make a new id and return it as a string
233 static std::string MakeId();
234 // get the current id
235 static int GetId() { return m_seed; }
236private:
237 // seed for generating the ids
238 static int m_seed;
239};
240
241
242///////////////////////////////////////////////////////////////////////////////
243// Base class for the archive test suites
244
245class ArchiveTestSuite : public CppUnit::TestSuite
246{
247public:
248 ArchiveTestSuite(std::string name);
249
250protected:
251 virtual ArchiveTestSuite *makeSuite();
252
253 virtual CppUnit::Test *makeTest(std::string descr,
254 int options,
255 bool genericInterface,
256 const wxString& archiver,
257 const wxString& unarchiver);
258
259 void AddArchiver(const wxString& cmd) { AddCmd(m_archivers, cmd); }
260 void AddUnArchiver(const wxString &cmd) { AddCmd(m_unarchivers, cmd); }
261 bool IsInPath(const wxString& cmd);
262
263 std::string Description(const wxString& type,
264 int options,
265 bool genericInterface = false,
266 const wxString& archiver = wxEmptyString,
267 const wxString& unarchiver = wxEmptyString);
268
269private:
270 wxString m_name;
271 wxPathList m_path;
272 wxArrayString m_archivers;
273 wxArrayString m_unarchivers;
274
275 void AddCmd(wxArrayString& cmdlist, const wxString& cmd);
276};
277
278#endif