]> git.saurik.com Git - wxWidgets.git/blame - samples/console/console.cpp
wxFileSelector should have file name only, not path, passed to 3rd arg
[wxWidgets.git] / samples / console / console.cpp
CommitLineData
37667812
VZ
1/////////////////////////////////////////////////////////////////////////////
2// Name: samples/console/console.cpp
3// Purpose: a sample console (as opposed to GUI) progam using wxWindows
4// Author: Vadim Zeitlin
5// Modified by:
6// Created: 04.10.99
7// RCS-ID: $Id$
8// Copyright: (c) 1999 Vadim Zeitlin <zeitlin@dptmaths.ens-cachan.fr>
9// Licence: wxWindows license
10/////////////////////////////////////////////////////////////////////////////
11
e87271f3
VZ
12// ============================================================================
13// declarations
14// ============================================================================
15
16// ----------------------------------------------------------------------------
17// headers
18// ----------------------------------------------------------------------------
19
37667812
VZ
20#include <stdio.h>
21
22#include <wx/string.h>
bbfa0322 23#include <wx/file.h>
37667812 24#include <wx/app.h>
e87271f3 25
d31b7b68
VZ
26// without this pragma, the stupid compiler precompiles #defines below so that
27// changing them doesn't "take place" later!
28#ifdef __VISUALC__
29 #pragma hdrstop
30#endif
31
e87271f3
VZ
32// ----------------------------------------------------------------------------
33// conditional compilation
34// ----------------------------------------------------------------------------
35
d31b7b68 36// what to test (in alphabetic order)?
378b05f7 37
a1f79c1e 38//#define TEST_ARRAYS
bbf8fc53 39//#define TEST_CMDLINE
42b1f941 40//#define TEST_DATETIME
bbf8fc53 41//#define TEST_DIR
f6bcfd97 42//#define TEST_DLLLOADER
c7ce8392 43//#define TEST_ENVIRON
8fd0d89b 44//#define TEST_EXECUTE
844f90fb 45//#define TEST_FILE
2c8e4738 46//#define TEST_FILECONF
a6c65e88 47//#define TEST_FILENAME
24f25c8a 48//#define TEST_FTP
2c8e4738 49//#define TEST_HASH
f6bcfd97 50//#define TEST_LIST
bbf8fc53
VZ
51//#define TEST_LOG
52//#define TEST_LONGLONG
b92fd37c 53//#define TEST_MIME
f6bcfd97 54//#define TEST_INFO_FUNCTIONS
a1f79c1e 55//#define TEST_REGISTRY
89e60357 56//#define TEST_SOCKETS
24f25c8a 57#define TEST_STREAMS
ee6e1b1d 58//#define TEST_STRINGS
bbf8fc53 59//#define TEST_THREADS
8e907a13 60//#define TEST_TIMER
3ca6a5f0 61//#define TEST_VCARD -- don't enable this (VZ)
f6bcfd97
BP
62//#define TEST_WCHAR
63//#define TEST_ZIP
3ca6a5f0 64//#define TEST_ZLIB
f6bcfd97
BP
65
66// ----------------------------------------------------------------------------
67// test class for container objects
68// ----------------------------------------------------------------------------
69
70#if defined(TEST_ARRAYS) || defined(TEST_LIST)
71
72class Bar // Foo is already taken in the hash test
73{
74public:
75 Bar(const wxString& name) : m_name(name) { ms_bars++; }
76 ~Bar() { ms_bars--; }
77
78 static size_t GetNumber() { return ms_bars; }
79
80 const char *GetName() const { return m_name; }
81
82private:
83 wxString m_name;
84
85 static size_t ms_bars;
86};
87
88size_t Bar::ms_bars = 0;
89
90#endif // defined(TEST_ARRAYS) || defined(TEST_LIST)
e87271f3
VZ
91
92// ============================================================================
93// implementation
94// ============================================================================
95
8e907a13
VZ
96// ----------------------------------------------------------------------------
97// helper functions
98// ----------------------------------------------------------------------------
99
100#if defined(TEST_STRINGS) || defined(TEST_SOCKETS)
101
102// replace TABs with \t and CRs with \n
103static wxString MakePrintable(const wxChar *s)
104{
105 wxString str(s);
106 (void)str.Replace(_T("\t"), _T("\\t"));
107 (void)str.Replace(_T("\n"), _T("\\n"));
108 (void)str.Replace(_T("\r"), _T("\\r"));
109
110 return str;
111}
112
113#endif // MakePrintable() is used
114
d34bce84
VZ
115// ----------------------------------------------------------------------------
116// wxCmdLineParser
117// ----------------------------------------------------------------------------
118
d31b7b68
VZ
119#ifdef TEST_CMDLINE
120
d34bce84
VZ
121#include <wx/cmdline.h>
122#include <wx/datetime.h>
123
124static void ShowCmdLine(const wxCmdLineParser& parser)
125{
126 wxString s = "Input files: ";
127
128 size_t count = parser.GetParamCount();
129 for ( size_t param = 0; param < count; param++ )
130 {
131 s << parser.GetParam(param) << ' ';
132 }
133
134 s << '\n'
135 << "Verbose:\t" << (parser.Found("v") ? "yes" : "no") << '\n'
136 << "Quiet:\t" << (parser.Found("q") ? "yes" : "no") << '\n';
137
138 wxString strVal;
139 long lVal;
140 wxDateTime dt;
141 if ( parser.Found("o", &strVal) )
142 s << "Output file:\t" << strVal << '\n';
143 if ( parser.Found("i", &strVal) )
144 s << "Input dir:\t" << strVal << '\n';
145 if ( parser.Found("s", &lVal) )
146 s << "Size:\t" << lVal << '\n';
147 if ( parser.Found("d", &dt) )
148 s << "Date:\t" << dt.FormatISODate() << '\n';
f6bcfd97
BP
149 if ( parser.Found("project_name", &strVal) )
150 s << "Project:\t" << strVal << '\n';
d34bce84
VZ
151
152 wxLogMessage(s);
153}
154
155#endif // TEST_CMDLINE
156
1944c6bd
VZ
157// ----------------------------------------------------------------------------
158// wxDir
159// ----------------------------------------------------------------------------
160
161#ifdef TEST_DIR
162
163#include <wx/dir.h>
164
165static void TestDirEnumHelper(wxDir& dir,
166 int flags = wxDIR_DEFAULT,
167 const wxString& filespec = wxEmptyString)
168{
169 wxString filename;
170
171 if ( !dir.IsOpened() )
172 return;
173
174 bool cont = dir.GetFirst(&filename, filespec, flags);
175 while ( cont )
176 {
177 printf("\t%s\n", filename.c_str());
178
179 cont = dir.GetNext(&filename);
180 }
181
182 puts("");
183}
184
185static void TestDirEnum()
186{
187 wxDir dir(wxGetCwd());
188
189 puts("Enumerating everything in current directory:");
190 TestDirEnumHelper(dir);
191
192 puts("Enumerating really everything in current directory:");
193 TestDirEnumHelper(dir, wxDIR_DEFAULT | wxDIR_DOTDOT);
194
195 puts("Enumerating object files in current directory:");
196 TestDirEnumHelper(dir, wxDIR_DEFAULT, "*.o");
197
198 puts("Enumerating directories in current directory:");
199 TestDirEnumHelper(dir, wxDIR_DIRS);
200
201 puts("Enumerating files in current directory:");
202 TestDirEnumHelper(dir, wxDIR_FILES);
203
204 puts("Enumerating files including hidden in current directory:");
205 TestDirEnumHelper(dir, wxDIR_FILES | wxDIR_HIDDEN);
206
207#ifdef __UNIX__
208 dir.Open("/");
209#elif defined(__WXMSW__)
210 dir.Open("c:\\");
211#else
212 #error "don't know where the root directory is"
213#endif
214
215 puts("Enumerating everything in root directory:");
216 TestDirEnumHelper(dir, wxDIR_DEFAULT);
217
218 puts("Enumerating directories in root directory:");
219 TestDirEnumHelper(dir, wxDIR_DIRS);
220
221 puts("Enumerating files in root directory:");
222 TestDirEnumHelper(dir, wxDIR_FILES);
223
224 puts("Enumerating files including hidden in root directory:");
225 TestDirEnumHelper(dir, wxDIR_FILES | wxDIR_HIDDEN);
226
227 puts("Enumerating files in non existing directory:");
228 wxDir dirNo("nosuchdir");
229 TestDirEnumHelper(dirNo);
230}
231
232#endif // TEST_DIR
233
f6bcfd97
BP
234// ----------------------------------------------------------------------------
235// wxDllLoader
236// ----------------------------------------------------------------------------
237
238#ifdef TEST_DLLLOADER
239
240#include <wx/dynlib.h>
241
242static void TestDllLoad()
243{
244#if defined(__WXMSW__)
245 static const wxChar *LIB_NAME = _T("kernel32.dll");
246 static const wxChar *FUNC_NAME = _T("lstrlenA");
247#elif defined(__UNIX__)
248 // weird: using just libc.so does *not* work!
249 static const wxChar *LIB_NAME = _T("/lib/libc-2.0.7.so");
250 static const wxChar *FUNC_NAME = _T("strlen");
251#else
252 #error "don't know how to test wxDllLoader on this platform"
253#endif
254
255 puts("*** testing wxDllLoader ***\n");
256
257 wxDllType dllHandle = wxDllLoader::LoadLibrary(LIB_NAME);
258 if ( !dllHandle )
259 {
260 wxPrintf(_T("ERROR: failed to load '%s'.\n"), LIB_NAME);
261 }
262 else
263 {
264 typedef int (*strlenType)(char *);
265 strlenType pfnStrlen = (strlenType)wxDllLoader::GetSymbol(dllHandle, FUNC_NAME);
266 if ( !pfnStrlen )
267 {
268 wxPrintf(_T("ERROR: function '%s' wasn't found in '%s'.\n"),
269 FUNC_NAME, LIB_NAME);
270 }
271 else
272 {
273 if ( pfnStrlen("foo") != 3 )
274 {
275 wxPrintf(_T("ERROR: loaded function is not strlen()!\n"));
276 }
277 else
278 {
279 puts("... ok");
280 }
281 }
282
283 wxDllLoader::UnloadLibrary(dllHandle);
284 }
285}
286
287#endif // TEST_DLLLOADER
288
8fd0d89b
VZ
289// ----------------------------------------------------------------------------
290// wxGet/SetEnv
291// ----------------------------------------------------------------------------
292
293#ifdef TEST_ENVIRON
294
295#include <wx/utils.h>
296
308978f6
VZ
297static wxString MyGetEnv(const wxString& var)
298{
299 wxString val;
300 if ( !wxGetEnv(var, &val) )
301 val = _T("<empty>");
302 else
303 val = wxString(_T('\'')) + val + _T('\'');
304
305 return val;
306}
307
8fd0d89b
VZ
308static void TestEnvironment()
309{
310 const wxChar *var = _T("wxTestVar");
311
312 puts("*** testing environment access functions ***");
313
308978f6 314 printf("Initially getenv(%s) = %s\n", var, MyGetEnv(var).c_str());
8fd0d89b 315 wxSetEnv(var, _T("value for wxTestVar"));
308978f6 316 printf("After wxSetEnv: getenv(%s) = %s\n", var, MyGetEnv(var).c_str());
8fd0d89b 317 wxSetEnv(var, _T("another value"));
308978f6 318 printf("After 2nd wxSetEnv: getenv(%s) = %s\n", var, MyGetEnv(var).c_str());
8fd0d89b 319 wxUnsetEnv(var);
308978f6
VZ
320 printf("After wxUnsetEnv: getenv(%s) = %s\n", var, MyGetEnv(var).c_str());
321 printf("PATH = %s\n", MyGetEnv(_T("PATH")));
8fd0d89b
VZ
322}
323
324#endif // TEST_ENVIRON
325
d93c719a
VZ
326// ----------------------------------------------------------------------------
327// wxExecute
328// ----------------------------------------------------------------------------
329
330#ifdef TEST_EXECUTE
331
332#include <wx/utils.h>
333
334static void TestExecute()
335{
336 puts("*** testing wxExecute ***");
337
338#ifdef __UNIX__
a1f79c1e 339 #define COMMAND "cat -n ../../Makefile" // "echo hi"
2c8e4738 340 #define SHELL_COMMAND "echo hi from shell"
a1f79c1e 341 #define REDIRECT_COMMAND COMMAND // "date"
d93c719a
VZ
342#elif defined(__WXMSW__)
343 #define COMMAND "command.com -c 'echo hi'"
2c8e4738
VZ
344 #define SHELL_COMMAND "echo hi"
345 #define REDIRECT_COMMAND COMMAND
d93c719a
VZ
346#else
347 #error "no command to exec"
348#endif // OS
349
2c8e4738
VZ
350 printf("Testing wxShell: ");
351 fflush(stdout);
352 if ( wxShell(SHELL_COMMAND) )
353 puts("Ok.");
d93c719a 354 else
2c8e4738
VZ
355 puts("ERROR.");
356
357 printf("Testing wxExecute: ");
358 fflush(stdout);
359 if ( wxExecute(COMMAND, TRUE /* sync */) == 0 )
360 puts("Ok.");
361 else
362 puts("ERROR.");
363
364#if 0 // no, it doesn't work (yet?)
365 printf("Testing async wxExecute: ");
366 fflush(stdout);
367 if ( wxExecute(COMMAND) != 0 )
368 puts("Ok (command launched).");
369 else
370 puts("ERROR.");
371#endif // 0
372
373 printf("Testing wxExecute with redirection:\n");
374 wxArrayString output;
375 if ( wxExecute(REDIRECT_COMMAND, output) != 0 )
376 {
377 puts("ERROR.");
378 }
379 else
380 {
381 size_t count = output.GetCount();
382 for ( size_t n = 0; n < count; n++ )
383 {
384 printf("\t%s\n", output[n].c_str());
385 }
386
387 puts("Ok.");
388 }
d93c719a
VZ
389}
390
391#endif // TEST_EXECUTE
392
f6bcfd97
BP
393// ----------------------------------------------------------------------------
394// file
395// ----------------------------------------------------------------------------
396
397#ifdef TEST_FILE
398
399#include <wx/file.h>
a339970a 400#include <wx/ffile.h>
f6bcfd97
BP
401#include <wx/textfile.h>
402
403static void TestFileRead()
404{
405 puts("*** wxFile read test ***");
406
407 wxFile file(_T("testdata.fc"));
408 if ( file.IsOpened() )
409 {
410 printf("File length: %lu\n", file.Length());
411
412 puts("File dump:\n----------");
413
3ca6a5f0 414 static const off_t len = 1024;
f6bcfd97
BP
415 char buf[len];
416 for ( ;; )
417 {
418 off_t nRead = file.Read(buf, len);
419 if ( nRead == wxInvalidOffset )
420 {
421 printf("Failed to read the file.");
422 break;
423 }
424
425 fwrite(buf, nRead, 1, stdout);
426
427 if ( nRead < len )
428 break;
429 }
430
431 puts("----------");
432 }
433 else
434 {
435 printf("ERROR: can't open test file.\n");
436 }
437
438 puts("");
439}
440
441static void TestTextFileRead()
442{
443 puts("*** wxTextFile read test ***");
444
445 wxTextFile file(_T("testdata.fc"));
446 if ( file.Open() )
447 {
448 printf("Number of lines: %u\n", file.GetLineCount());
449 printf("Last line: '%s'\n", file.GetLastLine().c_str());
3ca6a5f0
BP
450
451 wxString s;
452
453 puts("\nDumping the entire file:");
454 for ( s = file.GetFirstLine(); !file.Eof(); s = file.GetNextLine() )
455 {
456 printf("%6u: %s\n", file.GetCurrentLine() + 1, s.c_str());
457 }
458 printf("%6u: %s\n", file.GetCurrentLine() + 1, s.c_str());
459
460 puts("\nAnd now backwards:");
461 for ( s = file.GetLastLine();
462 file.GetCurrentLine() != 0;
463 s = file.GetPrevLine() )
464 {
465 printf("%6u: %s\n", file.GetCurrentLine() + 1, s.c_str());
466 }
467 printf("%6u: %s\n", file.GetCurrentLine() + 1, s.c_str());
f6bcfd97
BP
468 }
469 else
470 {
471 printf("ERROR: can't open '%s'\n", file.GetName());
472 }
473
474 puts("");
475}
476
a339970a
VZ
477static void TestFileCopy()
478{
479 puts("*** Testing wxCopyFile ***");
480
481 static const wxChar *filename1 = _T("testdata.fc");
482 static const wxChar *filename2 = _T("test2");
483 if ( !wxCopyFile(filename1, filename2) )
484 {
485 puts("ERROR: failed to copy file");
486 }
487 else
488 {
489 wxFFile f1(filename1, "rb"),
490 f2(filename2, "rb");
491
492 if ( !f1.IsOpened() || !f2.IsOpened() )
493 {
494 puts("ERROR: failed to open file(s)");
495 }
496 else
497 {
498 wxString s1, s2;
499 if ( !f1.ReadAll(&s1) || !f2.ReadAll(&s2) )
500 {
501 puts("ERROR: failed to read file(s)");
502 }
503 else
504 {
505 if ( (s1.length() != s2.length()) ||
506 (memcmp(s1.c_str(), s2.c_str(), s1.length()) != 0) )
507 {
508 puts("ERROR: copy error!");
509 }
510 else
511 {
512 puts("File was copied ok.");
513 }
514 }
515 }
516 }
517
518 if ( !wxRemoveFile(filename2) )
519 {
520 puts("ERROR: failed to remove the file");
521 }
522
523 puts("");
524}
525
f6bcfd97
BP
526#endif // TEST_FILE
527
ee6e1b1d
VZ
528// ----------------------------------------------------------------------------
529// wxFileConfig
530// ----------------------------------------------------------------------------
531
532#ifdef TEST_FILECONF
533
534#include <wx/confbase.h>
535#include <wx/fileconf.h>
536
537static const struct FileConfTestData
538{
539 const wxChar *name; // value name
540 const wxChar *value; // the value from the file
541} fcTestData[] =
542{
543 { _T("value1"), _T("one") },
544 { _T("value2"), _T("two") },
545 { _T("novalue"), _T("default") },
546};
547
548static void TestFileConfRead()
549{
550 puts("*** testing wxFileConfig loading/reading ***");
551
552 wxFileConfig fileconf(_T("test"), wxEmptyString,
553 _T("testdata.fc"), wxEmptyString,
554 wxCONFIG_USE_RELATIVE_PATH);
555
556 // test simple reading
557 puts("\nReading config file:");
558 wxString defValue(_T("default")), value;
559 for ( size_t n = 0; n < WXSIZEOF(fcTestData); n++ )
560 {
561 const FileConfTestData& data = fcTestData[n];
562 value = fileconf.Read(data.name, defValue);
563 printf("\t%s = %s ", data.name, value.c_str());
564 if ( value == data.value )
565 {
566 puts("(ok)");
567 }
568 else
569 {
570 printf("(ERROR: should be %s)\n", data.value);
571 }
572 }
573
574 // test enumerating the entries
575 puts("\nEnumerating all root entries:");
576 long dummy;
577 wxString name;
578 bool cont = fileconf.GetFirstEntry(name, dummy);
579 while ( cont )
580 {
581 printf("\t%s = %s\n",
582 name.c_str(),
583 fileconf.Read(name.c_str(), _T("ERROR")).c_str());
584
585 cont = fileconf.GetNextEntry(name, dummy);
586 }
587}
588
589#endif // TEST_FILECONF
590
844f90fb
VZ
591// ----------------------------------------------------------------------------
592// wxFileName
593// ----------------------------------------------------------------------------
594
595#ifdef TEST_FILENAME
596
597#include <wx/filename.h>
598
8e7dda21 599static struct FileNameInfo
42b1f941 600{
8e7dda21
VZ
601 const wxChar *fullname;
602 const wxChar *path;
603 const wxChar *name;
604 const wxChar *ext;
605} filenames[] =
606{
607 { _T("/usr/bin/ls"), _T("/usr/bin"), _T("ls"), _T("") },
608 { _T("/usr/bin/"), _T("/usr/bin"), _T(""), _T("") },
609 { _T("~/.zshrc"), _T("~"), _T(".zshrc"), _T("") },
610 { _T("../../foo"), _T("../.."), _T("foo"), _T("") },
611 { _T("foo.bar"), _T(""), _T("foo"), _T("bar") },
612 { _T("~/foo.bar"), _T("~"), _T("foo"), _T("bar") },
613 { _T("Mahogany-0.60/foo.bar"), _T("Mahogany-0.60"), _T("foo"), _T("bar") },
614 { _T("/tmp/wxwin.tar.bz"), _T("/tmp"), _T("wxwin.tar"), _T("bz") },
42b1f941
VZ
615};
616
844f90fb
VZ
617static void TestFileNameConstruction()
618{
619 puts("*** testing wxFileName construction ***");
620
844f90fb
VZ
621 for ( size_t n = 0; n < WXSIZEOF(filenames); n++ )
622 {
8e7dda21 623 wxFileName fn(filenames[n].fullname, wxPATH_UNIX);
844f90fb
VZ
624
625 printf("Filename: '%s'\t", fn.GetFullPath().c_str());
9e8d8607 626 if ( !fn.Normalize(wxPATH_NORM_ALL, _T(""), wxPATH_UNIX) )
844f90fb
VZ
627 {
628 puts("ERROR (couldn't be normalized)");
629 }
630 else
631 {
632 printf("normalized: '%s'\n", fn.GetFullPath().c_str());
633 }
634 }
635
636 puts("");
637}
638
42b1f941
VZ
639static void TestFileNameSplit()
640{
641 puts("*** testing wxFileName splitting ***");
642
643 for ( size_t n = 0; n < WXSIZEOF(filenames); n++ )
644 {
8e7dda21 645 const FileNameInfo &fni = filenames[n];
42b1f941 646 wxString path, name, ext;
8e7dda21
VZ
647 wxFileName::SplitPath(fni.fullname, &path, &name, &ext);
648
649 printf("%s -> path = '%s', name = '%s', ext = '%s'",
650 fni.fullname, path.c_str(), name.c_str(), ext.c_str());
651 if ( path != fni.path )
652 printf(" (ERROR: path = '%s')", fni.path);
653 if ( name != fni.name )
654 printf(" (ERROR: name = '%s')", fni.name);
655 if ( ext != fni.ext )
656 printf(" (ERROR: ext = '%s')", fni.ext);
657 puts("");
42b1f941
VZ
658 }
659
660 puts("");
661}
662
844f90fb
VZ
663static void TestFileNameComparison()
664{
665 // TODO!
666}
667
668static void TestFileNameOperations()
669{
670 // TODO!
671}
672
673static void TestFileNameCwd()
674{
675 // TODO!
676}
677
678#endif // TEST_FILENAME
679
2c8e4738
VZ
680// ----------------------------------------------------------------------------
681// wxHashTable
682// ----------------------------------------------------------------------------
683
684#ifdef TEST_HASH
685
686#include <wx/hash.h>
687
688struct Foo
689{
690 Foo(int n_) { n = n_; count++; }
691 ~Foo() { count--; }
692
693 int n;
694
695 static size_t count;
696};
697
698size_t Foo::count = 0;
699
700WX_DECLARE_LIST(Foo, wxListFoos);
701WX_DECLARE_HASH(Foo, wxListFoos, wxHashFoos);
702
703#include <wx/listimpl.cpp>
704
705WX_DEFINE_LIST(wxListFoos);
706
707static void TestHash()
708{
709 puts("*** Testing wxHashTable ***\n");
710
711 {
712 wxHashFoos hash;
713 hash.DeleteContents(TRUE);
714
715 printf("Hash created: %u foos in hash, %u foos totally\n",
716 hash.GetCount(), Foo::count);
717
718 static const int hashTestData[] =
719 {
720 0, 1, 17, -2, 2, 4, -4, 345, 3, 3, 2, 1,
721 };
722
723 size_t n;
724 for ( n = 0; n < WXSIZEOF(hashTestData); n++ )
725 {
726 hash.Put(hashTestData[n], n, new Foo(n));
727 }
728
729 printf("Hash filled: %u foos in hash, %u foos totally\n",
730 hash.GetCount(), Foo::count);
731
732 puts("Hash access test:");
733 for ( n = 0; n < WXSIZEOF(hashTestData); n++ )
734 {
735 printf("\tGetting element with key %d, value %d: ",
736 hashTestData[n], n);
737 Foo *foo = hash.Get(hashTestData[n], n);
738 if ( !foo )
739 {
740 printf("ERROR, not found.\n");
741 }
742 else
743 {
744 printf("%d (%s)\n", foo->n,
745 (size_t)foo->n == n ? "ok" : "ERROR");
746 }
747 }
748
749 printf("\nTrying to get an element not in hash: ");
750
751 if ( hash.Get(1234) || hash.Get(1, 0) )
752 {
753 puts("ERROR: found!");
754 }
755 else
756 {
757 puts("ok (not found)");
758 }
759 }
760
761 printf("Hash destroyed: %u foos left\n", Foo::count);
762}
763
764#endif // TEST_HASH
765
f6bcfd97
BP
766// ----------------------------------------------------------------------------
767// wxList
768// ----------------------------------------------------------------------------
769
770#ifdef TEST_LIST
771
772#include <wx/list.h>
773
774WX_DECLARE_LIST(Bar, wxListBars);
775#include <wx/listimpl.cpp>
776WX_DEFINE_LIST(wxListBars);
777
778static void TestListCtor()
779{
780 puts("*** Testing wxList construction ***\n");
781
782 {
783 wxListBars list1;
784 list1.Append(new Bar(_T("first")));
785 list1.Append(new Bar(_T("second")));
786
787 printf("After 1st list creation: %u objects in the list, %u objects total.\n",
788 list1.GetCount(), Bar::GetNumber());
789
790 wxListBars list2;
791 list2 = list1;
792
793 printf("After 2nd list creation: %u and %u objects in the lists, %u objects total.\n",
794 list1.GetCount(), list2.GetCount(), Bar::GetNumber());
795
796 list1.DeleteContents(TRUE);
797 }
798
799 printf("After list destruction: %u objects left.\n", Bar::GetNumber());
800}
801
802#endif // TEST_LIST
803
696e1ea0
VZ
804// ----------------------------------------------------------------------------
805// MIME types
806// ----------------------------------------------------------------------------
807
808#ifdef TEST_MIME
809
810#include <wx/mimetype.h>
811
f6bcfd97
BP
812static wxMimeTypesManager g_mimeManager;
813
696e1ea0
VZ
814static void TestMimeEnum()
815{
a6c65e88
VZ
816 wxPuts(_T("*** Testing wxMimeTypesManager::EnumAllFileTypes() ***\n"));
817
696e1ea0
VZ
818 wxArrayString mimetypes;
819
f6bcfd97 820 size_t count = g_mimeManager.EnumAllFileTypes(mimetypes);
696e1ea0
VZ
821
822 printf("*** All %u known filetypes: ***\n", count);
823
824 wxArrayString exts;
825 wxString desc;
826
827 for ( size_t n = 0; n < count; n++ )
828 {
f6bcfd97 829 wxFileType *filetype = g_mimeManager.GetFileTypeFromMimeType(mimetypes[n]);
696e1ea0 830 if ( !filetype )
c61f4f6d 831 {
97e0ceea
VZ
832 printf("nothing known about the filetype '%s'!\n",
833 mimetypes[n].c_str());
696e1ea0 834 continue;
c61f4f6d
VZ
835 }
836
696e1ea0
VZ
837 filetype->GetDescription(&desc);
838 filetype->GetExtensions(exts);
839
299fcbfe
VZ
840 filetype->GetIcon(NULL);
841
696e1ea0
VZ
842 wxString extsAll;
843 for ( size_t e = 0; e < exts.GetCount(); e++ )
844 {
845 if ( e > 0 )
846 extsAll << _T(", ");
847 extsAll += exts[e];
848 }
849
54acce90
VZ
850 printf("\t%s: %s (%s)\n",
851 mimetypes[n].c_str(), desc.c_str(), extsAll.c_str());
696e1ea0
VZ
852 }
853}
854
f6bcfd97
BP
855static void TestMimeOverride()
856{
857 wxPuts(_T("*** Testing wxMimeTypesManager additional files loading ***\n"));
858
859 wxString mailcap = _T("/tmp/mailcap"),
860 mimetypes = _T("/tmp/mime.types");
861
862 wxPrintf(_T("Loading mailcap from '%s': %s\n"),
863 mailcap.c_str(),
864 g_mimeManager.ReadMailcap(mailcap) ? _T("ok") : _T("ERROR"));
865 wxPrintf(_T("Loading mime.types from '%s': %s\n"),
866 mimetypes.c_str(),
867 g_mimeManager.ReadMimeTypes(mimetypes) ? _T("ok") : _T("ERROR"));
868}
869
870static void TestMimeFilename()
871{
872 wxPuts(_T("*** Testing MIME type from filename query ***\n"));
873
874 static const wxChar *filenames[] =
875 {
876 _T("readme.txt"),
877 _T("document.pdf"),
878 _T("image.gif"),
879 };
880
881 for ( size_t n = 0; n < WXSIZEOF(filenames); n++ )
882 {
883 const wxString fname = filenames[n];
884 wxString ext = fname.AfterLast(_T('.'));
885 wxFileType *ft = g_mimeManager.GetFileTypeFromExtension(ext);
886 if ( !ft )
887 {
888 wxPrintf(_T("WARNING: extension '%s' is unknown.\n"), ext.c_str());
889 }
890 else
891 {
892 wxString desc;
893 if ( !ft->GetDescription(&desc) )
894 desc = _T("<no description>");
895
896 wxString cmd;
897 if ( !ft->GetOpenCommand(&cmd,
898 wxFileType::MessageParameters(fname, _T(""))) )
899 cmd = _T("<no command available>");
900
901 wxPrintf(_T("To open %s (%s) do '%s'.\n"),
902 fname.c_str(), desc.c_str(), cmd.c_str());
903
904 delete ft;
905 }
906 }
907}
908
c7ce8392
VZ
909static void TestMimeAssociate()
910{
911 wxPuts(_T("*** Testing creation of filetype association ***\n"));
912
a6c65e88
VZ
913 wxFileTypeInfo ftInfo(
914 _T("application/x-xyz"),
915 _T("xyzview '%s'"), // open cmd
916 _T(""), // print cmd
917 _T("XYZ File") // description
918 _T(".xyz"), // extensions
919 NULL // end of extensions
920 );
921 ftInfo.SetShortDesc(_T("XYZFile")); // used under Win32 only
922
923 wxFileType *ft = g_mimeManager.Associate(ftInfo);
c7ce8392
VZ
924 if ( !ft )
925 {
926 wxPuts(_T("ERROR: failed to create association!"));
927 }
928 else
929 {
a6c65e88 930 // TODO: read it back
c7ce8392
VZ
931 delete ft;
932 }
933}
934
696e1ea0
VZ
935#endif // TEST_MIME
936
89e60357
VZ
937// ----------------------------------------------------------------------------
938// misc information functions
939// ----------------------------------------------------------------------------
940
941#ifdef TEST_INFO_FUNCTIONS
942
943#include <wx/utils.h>
944
945static void TestOsInfo()
946{
947 puts("*** Testing OS info functions ***\n");
948
949 int major, minor;
950 wxGetOsVersion(&major, &minor);
951 printf("Running under: %s, version %d.%d\n",
952 wxGetOsDescription().c_str(), major, minor);
953
bd3277fe 954 printf("%ld free bytes of memory left.\n", wxGetFreeMemory());
89e60357
VZ
955
956 printf("Host name is %s (%s).\n",
957 wxGetHostName().c_str(), wxGetFullHostName().c_str());
bd3277fe
VZ
958
959 puts("");
89e60357
VZ
960}
961
962static void TestUserInfo()
963{
964 puts("*** Testing user info functions ***\n");
965
966 printf("User id is:\t%s\n", wxGetUserId().c_str());
967 printf("User name is:\t%s\n", wxGetUserName().c_str());
968 printf("Home dir is:\t%s\n", wxGetHomeDir().c_str());
969 printf("Email address:\t%s\n", wxGetEmailAddress().c_str());
bd3277fe
VZ
970
971 puts("");
89e60357
VZ
972}
973
974#endif // TEST_INFO_FUNCTIONS
975
b76b015e
VZ
976// ----------------------------------------------------------------------------
977// long long
978// ----------------------------------------------------------------------------
979
980#ifdef TEST_LONGLONG
981
982#include <wx/longlong.h>
983#include <wx/timer.h>
984
2a310492
VZ
985// make a 64 bit number from 4 16 bit ones
986#define MAKE_LL(x1, x2, x3, x4) wxLongLong((x1 << 16) | x2, (x3 << 16) | x3)
987
988// get a random 64 bit number
989#define RAND_LL() MAKE_LL(rand(), rand(), rand(), rand())
990
7d0bb74d 991#if wxUSE_LONGLONG_WX
2a310492
VZ
992inline bool operator==(const wxLongLongWx& a, const wxLongLongNative& b)
993 { return a.GetHi() == b.GetHi() && a.GetLo() == b.GetLo(); }
994inline bool operator==(const wxLongLongNative& a, const wxLongLongWx& b)
995 { return a.GetHi() == b.GetHi() && a.GetLo() == b.GetLo(); }
7d0bb74d 996#endif // wxUSE_LONGLONG_WX
2a310492 997
b76b015e
VZ
998static void TestSpeed()
999{
1000 static const long max = 100000000;
1001 long n;
9fc3ad34 1002
b76b015e
VZ
1003 {
1004 wxStopWatch sw;
1005
1006 long l = 0;
1007 for ( n = 0; n < max; n++ )
1008 {
1009 l += n;
1010 }
1011
1012 printf("Summing longs took %ld milliseconds.\n", sw.Time());
1013 }
1014
2ea24d9f 1015#if wxUSE_LONGLONG_NATIVE
b76b015e
VZ
1016 {
1017 wxStopWatch sw;
1018
2ea24d9f 1019 wxLongLong_t l = 0;
b76b015e
VZ
1020 for ( n = 0; n < max; n++ )
1021 {
1022 l += n;
1023 }
1024
2ea24d9f 1025 printf("Summing wxLongLong_t took %ld milliseconds.\n", sw.Time());
b76b015e 1026 }
2ea24d9f 1027#endif // wxUSE_LONGLONG_NATIVE
b76b015e
VZ
1028
1029 {
1030 wxStopWatch sw;
1031
1032 wxLongLong l;
1033 for ( n = 0; n < max; n++ )
1034 {
1035 l += n;
1036 }
1037
1038 printf("Summing wxLongLongs took %ld milliseconds.\n", sw.Time());
1039 }
1040}
1041
2a310492 1042static void TestLongLongConversion()
b76b015e 1043{
2a310492
VZ
1044 puts("*** Testing wxLongLong conversions ***\n");
1045
1046 wxLongLong a;
1047 size_t nTested = 0;
1048 for ( size_t n = 0; n < 100000; n++ )
1049 {
1050 a = RAND_LL();
1051
1052#if wxUSE_LONGLONG_NATIVE
1053 wxLongLongNative b(a.GetHi(), a.GetLo());
5e6a0e83 1054
2a310492
VZ
1055 wxASSERT_MSG( a == b, "conversions failure" );
1056#else
1057 puts("Can't do it without native long long type, test skipped.");
b76b015e 1058
2a310492
VZ
1059 return;
1060#endif // wxUSE_LONGLONG_NATIVE
1061
1062 if ( !(nTested % 1000) )
1063 {
1064 putchar('.');
1065 fflush(stdout);
1066 }
1067
1068 nTested++;
1069 }
1070
1071 puts(" done!");
1072}
1073
1074static void TestMultiplication()
1075{
1076 puts("*** Testing wxLongLong multiplication ***\n");
1077
1078 wxLongLong a, b;
1079 size_t nTested = 0;
1080 for ( size_t n = 0; n < 100000; n++ )
1081 {
1082 a = RAND_LL();
1083 b = RAND_LL();
1084
1085#if wxUSE_LONGLONG_NATIVE
1086 wxLongLongNative aa(a.GetHi(), a.GetLo());
1087 wxLongLongNative bb(b.GetHi(), b.GetLo());
1088
1089 wxASSERT_MSG( a*b == aa*bb, "multiplication failure" );
1090#else // !wxUSE_LONGLONG_NATIVE
1091 puts("Can't do it without native long long type, test skipped.");
1092
1093 return;
1094#endif // wxUSE_LONGLONG_NATIVE
1095
1096 if ( !(nTested % 1000) )
1097 {
1098 putchar('.');
1099 fflush(stdout);
1100 }
1101
1102 nTested++;
1103 }
1104
1105 puts(" done!");
1106}
1107
1108static void TestDivision()
1109{
1110 puts("*** Testing wxLongLong division ***\n");
2f02cb89 1111
2ea24d9f 1112 wxLongLong q, r;
2f02cb89 1113 size_t nTested = 0;
5e6a0e83 1114 for ( size_t n = 0; n < 100000; n++ )
2f02cb89
VZ
1115 {
1116 // get a random wxLongLong (shifting by 12 the MSB ensures that the
1117 // multiplication will not overflow)
1118 wxLongLong ll = MAKE_LL((rand() >> 12), rand(), rand(), rand());
1119
2ea24d9f
VZ
1120 // get a random long (not wxLongLong for now) to divide it with
1121 long l = rand();
1122 q = ll / l;
1123 r = ll % l;
1124
2a310492
VZ
1125#if wxUSE_LONGLONG_NATIVE
1126 wxLongLongNative m(ll.GetHi(), ll.GetLo());
1127
1128 wxLongLongNative p = m / l, s = m % l;
1129 wxASSERT_MSG( q == p && r == s, "division failure" );
1130#else // !wxUSE_LONGLONG_NATIVE
5e6a0e83 1131 // verify the result
2ea24d9f 1132 wxASSERT_MSG( ll == q*l + r, "division failure" );
2a310492 1133#endif // wxUSE_LONGLONG_NATIVE
2f02cb89 1134
5e6a0e83
VZ
1135 if ( !(nTested % 1000) )
1136 {
1137 putchar('.');
1138 fflush(stdout);
1139 }
1140
2f02cb89
VZ
1141 nTested++;
1142 }
1143
5e6a0e83 1144 puts(" done!");
2a310492 1145}
2f02cb89 1146
2a310492
VZ
1147static void TestAddition()
1148{
1149 puts("*** Testing wxLongLong addition ***\n");
1150
1151 wxLongLong a, b, c;
1152 size_t nTested = 0;
1153 for ( size_t n = 0; n < 100000; n++ )
1154 {
1155 a = RAND_LL();
1156 b = RAND_LL();
1157 c = a + b;
1158
1159#if wxUSE_LONGLONG_NATIVE
1160 wxASSERT_MSG( c == wxLongLongNative(a.GetHi(), a.GetLo()) +
1161 wxLongLongNative(b.GetHi(), b.GetLo()),
7c968cee 1162 "addition failure" );
2a310492
VZ
1163#else // !wxUSE_LONGLONG_NATIVE
1164 wxASSERT_MSG( c - b == a, "addition failure" );
1165#endif // wxUSE_LONGLONG_NATIVE
1166
1167 if ( !(nTested % 1000) )
1168 {
1169 putchar('.');
1170 fflush(stdout);
1171 }
1172
1173 nTested++;
1174 }
1175
1176 puts(" done!");
b76b015e
VZ
1177}
1178
2a310492
VZ
1179static void TestBitOperations()
1180{
1181 puts("*** Testing wxLongLong bit operation ***\n");
1182
f6bcfd97 1183 wxLongLong ll;
2a310492
VZ
1184 size_t nTested = 0;
1185 for ( size_t n = 0; n < 100000; n++ )
1186 {
f6bcfd97 1187 ll = RAND_LL();
2a310492
VZ
1188
1189#if wxUSE_LONGLONG_NATIVE
1190 for ( size_t n = 0; n < 33; n++ )
1191 {
2a310492 1192 }
2a310492
VZ
1193#else // !wxUSE_LONGLONG_NATIVE
1194 puts("Can't do it without native long long type, test skipped.");
1195
1196 return;
1197#endif // wxUSE_LONGLONG_NATIVE
1198
1199 if ( !(nTested % 1000) )
1200 {
1201 putchar('.');
1202 fflush(stdout);
1203 }
1204
1205 nTested++;
1206 }
1207
1208 puts(" done!");
1209}
1210
f6bcfd97
BP
1211static void TestLongLongComparison()
1212{
1213 puts("*** Testing wxLongLong comparison ***\n");
1214
1215 static const long testLongs[] =
1216 {
1217 0,
1218 1,
1219 -1,
1220 LONG_MAX,
1221 LONG_MIN,
1222 0x1234,
1223 -0x1234
1224 };
1225
1226 static const long ls[2] =
1227 {
1228 0x1234,
1229 -0x1234,
1230 };
1231
1232 wxLongLongWx lls[2];
1233 lls[0] = ls[0];
1234 lls[1] = ls[1];
1235
1236 for ( size_t n = 0; n < WXSIZEOF(testLongs); n++ )
1237 {
1238 bool res;
1239
1240 for ( size_t m = 0; m < WXSIZEOF(lls); m++ )
1241 {
1242 res = lls[m] > testLongs[n];
1243 printf("0x%lx > 0x%lx is %s (%s)\n",
1244 ls[m], testLongs[n], res ? "true" : "false",
1245 res == (ls[m] > testLongs[n]) ? "ok" : "ERROR");
1246
1247 res = lls[m] < testLongs[n];
1248 printf("0x%lx < 0x%lx is %s (%s)\n",
1249 ls[m], testLongs[n], res ? "true" : "false",
1250 res == (ls[m] < testLongs[n]) ? "ok" : "ERROR");
1251
1252 res = lls[m] == testLongs[n];
1253 printf("0x%lx == 0x%lx is %s (%s)\n",
1254 ls[m], testLongs[n], res ? "true" : "false",
1255 res == (ls[m] == testLongs[n]) ? "ok" : "ERROR");
1256 }
1257 }
1258}
1259
2a310492
VZ
1260#undef MAKE_LL
1261#undef RAND_LL
1262
b76b015e
VZ
1263#endif // TEST_LONGLONG
1264
6dfec4b8
VZ
1265// ----------------------------------------------------------------------------
1266// registry
1267// ----------------------------------------------------------------------------
1268
1269// this is for MSW only
1270#ifndef __WXMSW__
1271 #undef TEST_REGISTRY
1272#endif
1273
1274#ifdef TEST_REGISTRY
1275
1276#include <wx/msw/registry.h>
1277
1278// I chose this one because I liked its name, but it probably only exists under
1279// NT
1280static const wxChar *TESTKEY =
1281 _T("HKEY_LOCAL_MACHINE\\SYSTEM\\ControlSet001\\Control\\CrashControl");
1282
1283static void TestRegistryRead()
1284{
1285 puts("*** testing registry reading ***");
1286
1287 wxRegKey key(TESTKEY);
1288 printf("The test key name is '%s'.\n", key.GetName().c_str());
1289 if ( !key.Open() )
1290 {
1291 puts("ERROR: test key can't be opened, aborting test.");
1292
1293 return;
1294 }
1295
1296 size_t nSubKeys, nValues;
1297 if ( key.GetKeyInfo(&nSubKeys, NULL, &nValues, NULL) )
1298 {
1299 printf("It has %u subkeys and %u values.\n", nSubKeys, nValues);
1300 }
1301
1302 printf("Enumerating values:\n");
1303
1304 long dummy;
1305 wxString value;
1306 bool cont = key.GetFirstValue(value, dummy);
1307 while ( cont )
1308 {
1309 printf("Value '%s': type ", value.c_str());
1310 switch ( key.GetValueType(value) )
1311 {
1312 case wxRegKey::Type_None: printf("ERROR (none)"); break;
1313 case wxRegKey::Type_String: printf("SZ"); break;
1314 case wxRegKey::Type_Expand_String: printf("EXPAND_SZ"); break;
1315 case wxRegKey::Type_Binary: printf("BINARY"); break;
1316 case wxRegKey::Type_Dword: printf("DWORD"); break;
1317 case wxRegKey::Type_Multi_String: printf("MULTI_SZ"); break;
1318 default: printf("other (unknown)"); break;
1319 }
1320
1321 printf(", value = ");
1322 if ( key.IsNumericValue(value) )
1323 {
1324 long val;
1325 key.QueryValue(value, &val);
1326 printf("%ld", val);
1327 }
1328 else // string
1329 {
1330 wxString val;
1331 key.QueryValue(value, val);
1332 printf("'%s'", val.c_str());
1333
1334 key.QueryRawValue(value, val);
1335 printf(" (raw value '%s')", val.c_str());
1336 }
1337
1338 putchar('\n');
1339
1340 cont = key.GetNextValue(value, dummy);
1341 }
1342}
1343
6ba63600
VZ
1344static void TestRegistryAssociation()
1345{
1346 /*
1347 The second call to deleteself genertaes an error message, with a
1348 messagebox saying .flo is crucial to system operation, while the .ddf
1349 call also fails, but with no error message
1350 */
1351
1352 wxRegKey key;
1353
1354 key.SetName("HKEY_CLASSES_ROOT\\.ddf" );
1355 key.Create();
1356 key = "ddxf_auto_file" ;
1357 key.SetName("HKEY_CLASSES_ROOT\\.flo" );
1358 key.Create();
1359 key = "ddxf_auto_file" ;
1360 key.SetName("HKEY_CLASSES_ROOT\\ddxf_auto_file\\DefaultIcon");
1361 key.Create();
1362 key = "program,0" ;
1363 key.SetName("HKEY_CLASSES_ROOT\\ddxf_auto_file\\shell\\open\\command");
1364 key.Create();
1365 key = "program \"%1\"" ;
1366
1367 key.SetName("HKEY_CLASSES_ROOT\\.ddf" );
1368 key.DeleteSelf();
1369 key.SetName("HKEY_CLASSES_ROOT\\.flo" );
1370 key.DeleteSelf();
1371 key.SetName("HKEY_CLASSES_ROOT\\ddxf_auto_file\\DefaultIcon");
1372 key.DeleteSelf();
1373 key.SetName("HKEY_CLASSES_ROOT\\ddxf_auto_file\\shell\\open\\command");
1374 key.DeleteSelf();
1375}
1376
6dfec4b8
VZ
1377#endif // TEST_REGISTRY
1378
2c8e4738
VZ
1379// ----------------------------------------------------------------------------
1380// sockets
1381// ----------------------------------------------------------------------------
1382
1383#ifdef TEST_SOCKETS
1384
1385#include <wx/socket.h>
8e907a13 1386#include <wx/protocol/protocol.h>
8e907a13
VZ
1387#include <wx/protocol/http.h>
1388
1389static void TestSocketServer()
1390{
1391 puts("*** Testing wxSocketServer ***\n");
1392
ccdb23df
VZ
1393 static const int PORT = 3000;
1394
8e907a13 1395 wxIPV4address addr;
ccdb23df 1396 addr.Service(PORT);
8e907a13
VZ
1397
1398 wxSocketServer *server = new wxSocketServer(addr);
1399 if ( !server->Ok() )
1400 {
1401 puts("ERROR: failed to bind");
ccdb23df
VZ
1402
1403 return;
8e907a13 1404 }
8dfea369
VZ
1405
1406 for ( ;; )
1407 {
ccdb23df 1408 printf("Server: waiting for connection on port %d...\n", PORT);
8dfea369
VZ
1409
1410 wxSocketBase *socket = server->Accept();
1411 if ( !socket )
1412 {
1413 puts("ERROR: wxSocketServer::Accept() failed.");
1414 break;
1415 }
1416
1417 puts("Server: got a client.");
1418
ccdb23df
VZ
1419 server->SetTimeout(60); // 1 min
1420
1421 while ( socket->IsConnected() )
8dfea369 1422 {
ccdb23df
VZ
1423 wxString s;
1424 char ch = '\0';
1425 for ( ;; )
8dfea369 1426 {
ccdb23df
VZ
1427 if ( socket->Read(&ch, sizeof(ch)).Error() )
1428 {
1429 // don't log error if the client just close the connection
1430 if ( socket->IsConnected() )
1431 {
1432 puts("ERROR: in wxSocket::Read.");
1433 }
8dfea369 1434
ccdb23df
VZ
1435 break;
1436 }
8dfea369 1437
ccdb23df
VZ
1438 if ( ch == '\r' )
1439 continue;
8dfea369 1440
ccdb23df
VZ
1441 if ( ch == '\n' )
1442 break;
8dfea369 1443
ccdb23df
VZ
1444 s += ch;
1445 }
8dfea369 1446
ccdb23df
VZ
1447 if ( ch != '\n' )
1448 {
1449 break;
1450 }
8dfea369 1451
ccdb23df
VZ
1452 printf("Server: got '%s'.\n", s.c_str());
1453 if ( s == _T("bye") )
1454 {
1455 delete socket;
8dfea369 1456
ccdb23df
VZ
1457 break;
1458 }
1459
1460 socket->Write(s.MakeUpper().c_str(), s.length());
1461 socket->Write("\r\n", 2);
1462 printf("Server: wrote '%s'.\n", s.c_str());
8dfea369
VZ
1463 }
1464
ccdb23df 1465 puts("Server: lost a client.");
8dfea369 1466
ccdb23df 1467 socket->Destroy();
8dfea369 1468 }
9fc3cba7 1469
ccdb23df
VZ
1470 // same as "delete server" but is consistent with GUI programs
1471 server->Destroy();
8e907a13 1472}
2c8e4738
VZ
1473
1474static void TestSocketClient()
1475{
1476 puts("*** Testing wxSocketClient ***\n");
1477
8e907a13
VZ
1478 static const char *hostname = "www.wxwindows.org";
1479
1480 wxIPV4address addr;
1481 addr.Hostname(hostname);
1482 addr.Service(80);
1483
1484 printf("--- Attempting to connect to %s:80...\n", hostname);
2c8e4738
VZ
1485
1486 wxSocketClient client;
8e907a13 1487 if ( !client.Connect(addr) )
2c8e4738 1488 {
8e907a13 1489 printf("ERROR: failed to connect to %s\n", hostname);
2c8e4738
VZ
1490 }
1491 else
1492 {
8e907a13
VZ
1493 printf("--- Connected to %s:%u...\n",
1494 addr.Hostname().c_str(), addr.Service());
1495
2c8e4738
VZ
1496 char buf[8192];
1497
8e907a13
VZ
1498 // could use simply "GET" here I suppose
1499 wxString cmdGet =
1500 wxString::Format("GET http://%s/\r\n", hostname);
1501 client.Write(cmdGet, cmdGet.length());
1502 printf("--- Sent command '%s' to the server\n",
1503 MakePrintable(cmdGet).c_str());
2c8e4738 1504 client.Read(buf, WXSIZEOF(buf));
8e907a13
VZ
1505 printf("--- Server replied:\n%s", buf);
1506 }
1507}
1508
2e907fab
VZ
1509#endif // TEST_SOCKETS
1510
b92fd37c
VZ
1511// ----------------------------------------------------------------------------
1512// FTP
1513// ----------------------------------------------------------------------------
1514
2e907fab
VZ
1515#ifdef TEST_FTP
1516
1517#include <wx/protocol/ftp.h>
1518
b92fd37c
VZ
1519static wxFTP ftp;
1520
1521#define FTP_ANONYMOUS
1522
1523#ifdef FTP_ANONYMOUS
1524 static const char *directory = "/pub";
1525 static const char *filename = "welcome.msg";
1526#else
1527 static const char *directory = "/etc";
1528 static const char *filename = "issue";
1529#endif
1530
1531static bool TestFtpConnect()
8e907a13 1532{
b92fd37c 1533 puts("*** Testing FTP connect ***");
8e907a13 1534
b92fd37c
VZ
1535#ifdef FTP_ANONYMOUS
1536 static const char *hostname = "ftp.wxwindows.org";
1537
1538 printf("--- Attempting to connect to %s:21 anonymously...\n", hostname);
1539#else // !FTP_ANONYMOUS
1540 static const char *hostname = "localhost";
1541
1542 char user[256];
1543 fgets(user, WXSIZEOF(user), stdin);
1544 user[strlen(user) - 1] = '\0'; // chop off '\n'
1545 ftp.SetUser(user);
1546
1547 char password[256];
1548 printf("Password for %s: ", password);
1549 fgets(password, WXSIZEOF(password), stdin);
1550 password[strlen(password) - 1] = '\0'; // chop off '\n'
1551 ftp.SetPassword(password);
1552
1553 printf("--- Attempting to connect to %s:21 as %s...\n", hostname, user);
1554#endif // FTP_ANONYMOUS/!FTP_ANONYMOUS
1555
1556 if ( !ftp.Connect(hostname) )
1557 {
1558 printf("ERROR: failed to connect to %s\n", hostname);
1559
1560 return FALSE;
1561 }
1562 else
1563 {
1564 printf("--- Connected to %s, current directory is '%s'\n",
1565 hostname, ftp.Pwd().c_str());
1566 }
1567
1568 return TRUE;
1569}
b1229561 1570
b92fd37c
VZ
1571// test (fixed?) wxFTP bug with wu-ftpd >= 2.6.0?
1572static void TestFtpWuFtpd()
1573{
1574 wxFTP ftp;
b1229561
VZ
1575 static const char *hostname = "ftp.eudora.com";
1576 if ( !ftp.Connect(hostname) )
1577 {
1578 printf("ERROR: failed to connect to %s\n", hostname);
1579 }
1580 else
1581 {
1582 static const char *filename = "eudora/pubs/draft-gellens-submit-09.txt";
1583 wxInputStream *in = ftp.GetInputStream(filename);
1584 if ( !in )
1585 {
1586 printf("ERROR: couldn't get input stream for %s\n", filename);
1587 }
1588 else
1589 {
1590 size_t size = in->StreamSize();
1591 printf("Reading file %s (%u bytes)...", filename, size);
1592
1593 char *data = new char[size];
1594 if ( !in->Read(data, size) )
1595 {
1596 puts("ERROR: read error");
1597 }
1598 else
1599 {
1600 printf("Successfully retrieved the file.\n");
1601 }
1602
1603 delete [] data;
1604 delete in;
1605 }
1606 }
b92fd37c 1607}
b1229561 1608
b92fd37c
VZ
1609static void TestFtpList()
1610{
1611 puts("*** Testing wxFTP file listing ***\n");
8e907a13 1612
b92fd37c
VZ
1613 // test CWD
1614 if ( !ftp.ChDir(directory) )
1615 {
1616 printf("ERROR: failed to cd to %s\n", directory);
1617 }
2e907fab 1618
b92fd37c 1619 printf("Current directory is '%s'\n", ftp.Pwd().c_str());
2e907fab 1620
b92fd37c
VZ
1621 // test NLIST and LIST
1622 wxArrayString files;
1623 if ( !ftp.GetFilesList(files) )
8e907a13 1624 {
b92fd37c 1625 puts("ERROR: failed to get NLIST of files");
8e907a13
VZ
1626 }
1627 else
1628 {
b92fd37c
VZ
1629 printf("Brief list of files under '%s':\n", ftp.Pwd().c_str());
1630 size_t count = files.GetCount();
1631 for ( size_t n = 0; n < count; n++ )
8e907a13 1632 {
b92fd37c 1633 printf("\t%s\n", files[n].c_str());
8e907a13 1634 }
b92fd37c
VZ
1635 puts("End of the file list");
1636 }
8e907a13 1637
b92fd37c
VZ
1638 if ( !ftp.GetDirList(files) )
1639 {
1640 puts("ERROR: failed to get LIST of files");
1641 }
1642 else
1643 {
1644 printf("Detailed list of files under '%s':\n", ftp.Pwd().c_str());
1645 size_t count = files.GetCount();
1646 for ( size_t n = 0; n < count; n++ )
8e907a13 1647 {
b92fd37c 1648 printf("\t%s\n", files[n].c_str());
2e907fab 1649 }
b92fd37c
VZ
1650 puts("End of the file list");
1651 }
1652
1653 if ( !ftp.ChDir(_T("..")) )
1654 {
1655 puts("ERROR: failed to cd to ..");
1656 }
2e907fab 1657
b92fd37c
VZ
1658 printf("Current directory is '%s'\n", ftp.Pwd().c_str());
1659}
1660
1661static void TestFtpDownload()
1662{
1663 puts("*** Testing wxFTP download ***\n");
1664
1665 // test RETR
1666 wxInputStream *in = ftp.GetInputStream(filename);
1667 if ( !in )
1668 {
1669 printf("ERROR: couldn't get input stream for %s\n", filename);
1670 }
1671 else
1672 {
1673 size_t size = in->StreamSize();
1674 printf("Reading file %s (%u bytes)...", filename, size);
1675 fflush(stdout);
1676
1677 char *data = new char[size];
1678 if ( !in->Read(data, size) )
2e907fab 1679 {
b92fd37c 1680 puts("ERROR: read error");
2e907fab
VZ
1681 }
1682 else
1683 {
b92fd37c 1684 printf("\nContents of %s:\n%s\n", filename, data);
8e907a13
VZ
1685 }
1686
b92fd37c
VZ
1687 delete [] data;
1688 delete in;
1689 }
1690}
8e907a13 1691
b92fd37c
VZ
1692static void TestFtpFileSize()
1693{
1694 puts("*** Testing FTP SIZE command ***");
1695
1696 if ( !ftp.ChDir(directory) )
1697 {
1698 printf("ERROR: failed to cd to %s\n", directory);
1699 }
1700
1701 printf("Current directory is '%s'\n", ftp.Pwd().c_str());
1702
1703 if ( ftp.FileExists(filename) )
1704 {
1705 int size = ftp.GetFileSize(filename);
1706 if ( size == -1 )
1707 printf("ERROR: couldn't get size of '%s'\n", filename);
8e907a13 1708 else
b92fd37c
VZ
1709 printf("Size of '%s' is %d bytes.\n", filename, size);
1710 }
1711 else
1712 {
1713 printf("ERROR: '%s' doesn't exist\n", filename);
1714 }
1715}
1716
1717static void TestFtpMisc()
1718{
1719 puts("*** Testing miscellaneous wxFTP functions ***");
1720
1721 if ( ftp.SendCommand("STAT") != '2' )
1722 {
1723 puts("ERROR: STAT failed");
1724 }
1725 else
1726 {
1727 printf("STAT returned:\n\n%s\n", ftp.GetLastResult().c_str());
1728 }
1729
1730 if ( ftp.SendCommand("HELP SITE") != '2' )
1731 {
1732 puts("ERROR: HELP SITE failed");
1733 }
1734 else
1735 {
1736 printf("The list of site-specific commands:\n\n%s\n",
1737 ftp.GetLastResult().c_str());
1738 }
1739}
1740
1741static void TestFtpInteractive()
1742{
1743 puts("\n*** Interactive wxFTP test ***");
1744
1745 char buf[128];
1746
1747 for ( ;; )
1748 {
1749 printf("Enter FTP command: ");
1750 if ( !fgets(buf, WXSIZEOF(buf), stdin) )
1751 break;
1752
1753 // kill the last '\n'
1754 buf[strlen(buf) - 1] = 0;
1755
1756 // special handling of LIST and NLST as they require data connection
1757 wxString start(buf, 4);
1758 start.MakeUpper();
1759 if ( start == "LIST" || start == "NLST" )
8e907a13 1760 {
b92fd37c
VZ
1761 wxString wildcard;
1762 if ( strlen(buf) > 4 )
1763 wildcard = buf + 5;
8e907a13 1764
b92fd37c
VZ
1765 wxArrayString files;
1766 if ( !ftp.GetList(files, wildcard, start == "LIST") )
8e907a13 1767 {
b92fd37c 1768 printf("ERROR: failed to get %s of files\n", start.c_str());
8e907a13
VZ
1769 }
1770 else
1771 {
b92fd37c
VZ
1772 printf("--- %s of '%s' under '%s':\n",
1773 start.c_str(), wildcard.c_str(), ftp.Pwd().c_str());
1774 size_t count = files.GetCount();
1775 for ( size_t n = 0; n < count; n++ )
1776 {
1777 printf("\t%s\n", files[n].c_str());
1778 }
1779 puts("--- End of the file list");
8e907a13 1780 }
2e907fab 1781 }
b92fd37c 1782 else // !list
2e907fab 1783 {
b92fd37c
VZ
1784 char ch = ftp.SendCommand(buf);
1785 printf("Command %s", ch ? "succeeded" : "failed");
1786 if ( ch )
1787 {
1788 printf(" (return code %c)", ch);
1789 }
2e907fab 1790
b92fd37c 1791 printf(", server reply:\n%s\n\n", ftp.GetLastResult().c_str());
2e907fab 1792 }
2c8e4738 1793 }
b92fd37c
VZ
1794
1795 puts("\n*** done ***");
2c8e4738
VZ
1796}
1797
b92fd37c 1798static void TestFtpUpload()
f6bcfd97
BP
1799{
1800 puts("*** Testing wxFTP uploading ***\n");
1801
b92fd37c
VZ
1802 // upload a file
1803 static const char *file1 = "test1";
1804 static const char *file2 = "test2";
1805 wxOutputStream *out = ftp.GetOutputStream(file1);
1806 if ( out )
1807 {
1808 printf("--- Uploading to %s ---\n", file1);
1809 out->Write("First hello", 11);
1810 delete out;
1811 }
f6bcfd97 1812
b92fd37c
VZ
1813 // send a command to check the remote file
1814 if ( ftp.SendCommand(wxString("STAT ") + file1) != '2' )
f6bcfd97 1815 {
b92fd37c 1816 printf("ERROR: STAT %s failed\n", file1);
f6bcfd97
BP
1817 }
1818 else
1819 {
b92fd37c
VZ
1820 printf("STAT %s returned:\n\n%s\n",
1821 file1, ftp.GetLastResult().c_str());
1822 }
2e907fab 1823
b92fd37c
VZ
1824 out = ftp.GetOutputStream(file2);
1825 if ( out )
1826 {
1827 printf("--- Uploading to %s ---\n", file1);
1828 out->Write("Second hello", 12);
1829 delete out;
f6bcfd97
BP
1830 }
1831}
1832
2e907fab 1833#endif // TEST_FTP
2c8e4738 1834
83141d3a
VZ
1835// ----------------------------------------------------------------------------
1836// streams
1837// ----------------------------------------------------------------------------
1838
1839#ifdef TEST_STREAMS
1840
24f25c8a 1841#include <wx/wfstream.h>
83141d3a
VZ
1842#include <wx/mstream.h>
1843
24f25c8a
VZ
1844static void TestFileStream()
1845{
1846 puts("*** Testing wxFileInputStream ***");
1847
1848 static const wxChar *filename = _T("testdata.fs");
1849 {
1850 wxFileOutputStream fsOut(filename);
1851 fsOut.Write("foo", 3);
1852 }
1853
1854 wxFileInputStream fsIn(filename);
1855 printf("File stream size: %u\n", fsIn.GetSize());
1856 while ( !fsIn.Eof() )
1857 {
1858 putchar(fsIn.GetC());
1859 }
1860
1861 if ( !wxRemoveFile(filename) )
1862 {
1863 printf("ERROR: failed to remove the file '%s'.\n", filename);
1864 }
1865
1866 puts("\n*** wxFileInputStream test done ***");
1867}
1868
83141d3a
VZ
1869static void TestMemoryStream()
1870{
1871 puts("*** Testing wxMemoryInputStream ***");
1872
1873 wxChar buf[1024];
1874 wxStrncpy(buf, _T("Hello, stream!"), WXSIZEOF(buf));
1875
1876 wxMemoryInputStream memInpStream(buf, wxStrlen(buf));
1877 printf(_T("Memory stream size: %u\n"), memInpStream.GetSize());
1878 while ( !memInpStream.Eof() )
1879 {
1880 putchar(memInpStream.GetC());
1881 }
1882
1883 puts("\n*** wxMemoryInputStream test done ***");
1884}
1885
1886#endif // TEST_STREAMS
1887
d31b7b68
VZ
1888// ----------------------------------------------------------------------------
1889// timers
1890// ----------------------------------------------------------------------------
1891
1892#ifdef TEST_TIMER
1893
1894#include <wx/timer.h>
1895#include <wx/utils.h>
1896
1897static void TestStopWatch()
1898{
1899 puts("*** Testing wxStopWatch ***\n");
1900
1901 wxStopWatch sw;
1902 printf("Sleeping 3 seconds...");
1903 wxSleep(3);
87798c00 1904 printf("\telapsed time: %ldms\n", sw.Time());
d31b7b68
VZ
1905
1906 sw.Pause();
1907 printf("Sleeping 2 more seconds...");
1908 wxSleep(2);
87798c00 1909 printf("\telapsed time: %ldms\n", sw.Time());
d31b7b68
VZ
1910
1911 sw.Resume();
1912 printf("And 3 more seconds...");
1913 wxSleep(3);
87798c00
VZ
1914 printf("\telapsed time: %ldms\n", sw.Time());
1915
1916 wxStopWatch sw2;
1917 puts("\nChecking for 'backwards clock' bug...");
1918 for ( size_t n = 0; n < 70; n++ )
1919 {
1920 sw2.Start();
89e6463c
GRG
1921
1922 for ( size_t m = 0; m < 100000; m++ )
87798c00 1923 {
89e6463c
GRG
1924 if ( sw.Time() < 0 || sw2.Time() < 0 )
1925 {
1926 puts("\ntime is negative - ERROR!");
1927 }
87798c00
VZ
1928 }
1929
1930 putchar('.');
1931 }
1932
1933 puts(", ok.");
d31b7b68
VZ
1934}
1935
1936#endif // TEST_TIMER
1937
f6bcfd97
BP
1938// ----------------------------------------------------------------------------
1939// vCard support
1940// ----------------------------------------------------------------------------
1941
1942#ifdef TEST_VCARD
1943
1944#include <wx/vcard.h>
1945
1946static void DumpVObject(size_t level, const wxVCardObject& vcard)
1947{
1948 void *cookie;
1949 wxVCardObject *vcObj = vcard.GetFirstProp(&cookie);
1950 while ( vcObj )
1951 {
1952 printf("%s%s",
1953 wxString(_T('\t'), level).c_str(),
1954 vcObj->GetName().c_str());
1955
1956 wxString value;
1957 switch ( vcObj->GetType() )
1958 {
1959 case wxVCardObject::String:
1960 case wxVCardObject::UString:
1961 {
1962 wxString val;
1963 vcObj->GetValue(&val);
1964 value << _T('"') << val << _T('"');
1965 }
1966 break;
1967
1968 case wxVCardObject::Int:
1969 {
1970 unsigned int i;
1971 vcObj->GetValue(&i);
1972 value.Printf(_T("%u"), i);
1973 }
1974 break;
1975
1976 case wxVCardObject::Long:
1977 {
1978 unsigned long l;
1979 vcObj->GetValue(&l);
1980 value.Printf(_T("%lu"), l);
1981 }
1982 break;
1983
1984 case wxVCardObject::None:
1985 break;
1986
1987 case wxVCardObject::Object:
1988 value = _T("<node>");
1989 break;
1990
1991 default:
1992 value = _T("<unknown value type>");
1993 }
1994
1995 if ( !!value )
1996 printf(" = %s", value.c_str());
1997 putchar('\n');
1998
1999 DumpVObject(level + 1, *vcObj);
2000
2001 delete vcObj;
2002 vcObj = vcard.GetNextProp(&cookie);
2003 }
2004}
2005
2006static void DumpVCardAddresses(const wxVCard& vcard)
2007{
2008 puts("\nShowing all addresses from vCard:\n");
2009
2010 size_t nAdr = 0;
2011 void *cookie;
2012 wxVCardAddress *addr = vcard.GetFirstAddress(&cookie);
2013 while ( addr )
2014 {
2015 wxString flagsStr;
2016 int flags = addr->GetFlags();
2017 if ( flags & wxVCardAddress::Domestic )
2018 {
2019 flagsStr << _T("domestic ");
2020 }
2021 if ( flags & wxVCardAddress::Intl )
2022 {
2023 flagsStr << _T("international ");
2024 }
2025 if ( flags & wxVCardAddress::Postal )
2026 {
2027 flagsStr << _T("postal ");
2028 }
2029 if ( flags & wxVCardAddress::Parcel )
2030 {
2031 flagsStr << _T("parcel ");
2032 }
2033 if ( flags & wxVCardAddress::Home )
2034 {
2035 flagsStr << _T("home ");
2036 }
2037 if ( flags & wxVCardAddress::Work )
2038 {
2039 flagsStr << _T("work ");
2040 }
2041
2042 printf("Address %u:\n"
2043 "\tflags = %s\n"
2044 "\tvalue = %s;%s;%s;%s;%s;%s;%s\n",
2045 ++nAdr,
2046 flagsStr.c_str(),
2047 addr->GetPostOffice().c_str(),
2048 addr->GetExtAddress().c_str(),
2049 addr->GetStreet().c_str(),
2050 addr->GetLocality().c_str(),
2051 addr->GetRegion().c_str(),
2052 addr->GetPostalCode().c_str(),
2053 addr->GetCountry().c_str()
2054 );
2055
2056 delete addr;
2057 addr = vcard.GetNextAddress(&cookie);
2058 }
2059}
2060
2061static void DumpVCardPhoneNumbers(const wxVCard& vcard)
2062{
2063 puts("\nShowing all phone numbers from vCard:\n");
2064
2065 size_t nPhone = 0;
2066 void *cookie;
2067 wxVCardPhoneNumber *phone = vcard.GetFirstPhoneNumber(&cookie);
2068 while ( phone )
2069 {
2070 wxString flagsStr;
2071 int flags = phone->GetFlags();
2072 if ( flags & wxVCardPhoneNumber::Voice )
2073 {
2074 flagsStr << _T("voice ");
2075 }
2076 if ( flags & wxVCardPhoneNumber::Fax )
2077 {
2078 flagsStr << _T("fax ");
2079 }
2080 if ( flags & wxVCardPhoneNumber::Cellular )
2081 {
2082 flagsStr << _T("cellular ");
2083 }
2084 if ( flags & wxVCardPhoneNumber::Modem )
2085 {
2086 flagsStr << _T("modem ");
2087 }
2088 if ( flags & wxVCardPhoneNumber::Home )
2089 {
2090 flagsStr << _T("home ");
2091 }
2092 if ( flags & wxVCardPhoneNumber::Work )
2093 {
2094 flagsStr << _T("work ");
2095 }
2096
2097 printf("Phone number %u:\n"
2098 "\tflags = %s\n"
2099 "\tvalue = %s\n",
2100 ++nPhone,
2101 flagsStr.c_str(),
2102 phone->GetNumber().c_str()
2103 );
2104
2105 delete phone;
2106 phone = vcard.GetNextPhoneNumber(&cookie);
2107 }
2108}
2109
2110static void TestVCardRead()
2111{
2112 puts("*** Testing wxVCard reading ***\n");
2113
2114 wxVCard vcard(_T("vcard.vcf"));
2115 if ( !vcard.IsOk() )
2116 {
2117 puts("ERROR: couldn't load vCard.");
2118 }
2119 else
2120 {
2121 // read individual vCard properties
2122 wxVCardObject *vcObj = vcard.GetProperty("FN");
2123 wxString value;
2124 if ( vcObj )
2125 {
2126 vcObj->GetValue(&value);
2127 delete vcObj;
2128 }
2129 else
2130 {
2131 value = _T("<none>");
2132 }
2133
2134 printf("Full name retrieved directly: %s\n", value.c_str());
2135
2136
2137 if ( !vcard.GetFullName(&value) )
2138 {
2139 value = _T("<none>");
2140 }
2141
2142 printf("Full name from wxVCard API: %s\n", value.c_str());
2143
2144 // now show how to deal with multiply occuring properties
2145 DumpVCardAddresses(vcard);
2146 DumpVCardPhoneNumbers(vcard);
2147
2148 // and finally show all
2149 puts("\nNow dumping the entire vCard:\n"
2150 "-----------------------------\n");
2151
2152 DumpVObject(0, vcard);
2153 }
2154}
2155
2156static void TestVCardWrite()
2157{
2158 puts("*** Testing wxVCard writing ***\n");
2159
2160 wxVCard vcard;
2161 if ( !vcard.IsOk() )
2162 {
2163 puts("ERROR: couldn't create vCard.");
2164 }
2165 else
2166 {
2167 // set some fields
2168 vcard.SetName("Zeitlin", "Vadim");
2169 vcard.SetFullName("Vadim Zeitlin");
2170 vcard.SetOrganization("wxWindows", "R&D");
2171
2172 // just dump the vCard back
2173 puts("Entire vCard follows:\n");
2174 puts(vcard.Write());
2175 }
2176}
2177
2178#endif // TEST_VCARD
2179
2180// ----------------------------------------------------------------------------
2181// wide char (Unicode) support
2182// ----------------------------------------------------------------------------
2183
2184#ifdef TEST_WCHAR
2185
2186#include <wx/strconv.h>
24f25c8a
VZ
2187#include <wx/fontenc.h>
2188#include <wx/encconv.h>
f6bcfd97
BP
2189#include <wx/buffer.h>
2190
2191static void TestUtf8()
2192{
2193 puts("*** Testing UTF8 support ***\n");
2194
24f25c8a
VZ
2195 static const char textInUtf8[] =
2196 {
2197 208, 157, 208, 181, 209, 129, 208, 186, 208, 176, 208, 183, 208, 176,
2198 208, 189, 208, 189, 208, 190, 32, 208, 191, 208, 190, 209, 128, 208,
2199 176, 208, 180, 208, 190, 208, 178, 208, 176, 208, 187, 32, 208, 188,
2200 208, 181, 208, 189, 209, 143, 32, 209, 129, 208, 178, 208, 190, 208,
2201 181, 208, 185, 32, 208, 186, 209, 128, 209, 131, 209, 130, 208, 181,
2202 208, 185, 209, 136, 208, 181, 208, 185, 32, 208, 189, 208, 190, 208,
2203 178, 208, 190, 209, 129, 209, 130, 209, 140, 209, 142, 0
2204 };
f6bcfd97 2205
24f25c8a
VZ
2206 char buf[1024];
2207 wchar_t wbuf[1024];
2208 if ( wxConvUTF8.MB2WC(wbuf, textInUtf8, WXSIZEOF(textInUtf8)) <= 0 )
f6bcfd97 2209 {
24f25c8a 2210 puts("ERROR: UTF-8 decoding failed.");
f6bcfd97 2211 }
24f25c8a
VZ
2212 else
2213 {
2214 // using wxEncodingConverter
2215#if 0
2216 wxEncodingConverter ec;
2217 ec.Init(wxFONTENCODING_UNICODE, wxFONTENCODING_KOI8);
2218 ec.Convert(wbuf, buf);
2219#else // using wxCSConv
2220 wxCSConv conv(_T("koi8-r"));
2221 if ( conv.WC2MB(buf, wbuf, 0 /* not needed wcslen(wbuf) */) <= 0 )
2222 {
2223 puts("ERROR: conversion to KOI8-R failed.");
2224 }
2225 else
2226#endif
f6bcfd97 2227
24f25c8a
VZ
2228 printf("The resulting string (in koi8-r): %s\n", buf);
2229 }
f6bcfd97
BP
2230}
2231
2232#endif // TEST_WCHAR
2233
2234// ----------------------------------------------------------------------------
2235// ZIP stream
2236// ----------------------------------------------------------------------------
2237
2238#ifdef TEST_ZIP
2239
2240#include "wx/zipstrm.h"
2241
2242static void TestZipStreamRead()
2243{
2244 puts("*** Testing ZIP reading ***\n");
2245
2246 wxZipInputStream istr(_T("idx.zip"), _T("IDX.txt"));
2247 printf("Archive size: %u\n", istr.GetSize());
2248
2249 puts("Dumping the file:");
2250 while ( !istr.Eof() )
2251 {
2252 putchar(istr.GetC());
2253 fflush(stdout);
2254 }
2255
2256 puts("\n----- done ------");
2257}
2258
2259#endif // TEST_ZIP
2260
3ca6a5f0
BP
2261// ----------------------------------------------------------------------------
2262// ZLIB stream
2263// ----------------------------------------------------------------------------
2264
2265#ifdef TEST_ZLIB
2266
2267#include <wx/zstream.h>
2268#include <wx/wfstream.h>
2269
2270static const wxChar *FILENAME_GZ = _T("test.gz");
2271static const char *TEST_DATA = "hello and hello again";
2272
2273static void TestZlibStreamWrite()
2274{
2275 puts("*** Testing Zlib stream reading ***\n");
2276
2277 wxFileOutputStream fileOutStream(FILENAME_GZ);
2278 wxZlibOutputStream ostr(fileOutStream, 0);
2279 printf("Compressing the test string... ");
2280 ostr.Write(TEST_DATA, sizeof(TEST_DATA));
2281 if ( !ostr )
2282 {
2283 puts("(ERROR: failed)");
2284 }
2285 else
2286 {
2287 puts("(ok)");
2288 }
2289
2290 puts("\n----- done ------");
2291}
2292
2293static void TestZlibStreamRead()
2294{
2295 puts("*** Testing Zlib stream reading ***\n");
2296
2297 wxFileInputStream fileInStream(FILENAME_GZ);
2298 wxZlibInputStream istr(fileInStream);
2299 printf("Archive size: %u\n", istr.GetSize());
2300
2301 puts("Dumping the file:");
2302 while ( !istr.Eof() )
2303 {
2304 putchar(istr.GetC());
2305 fflush(stdout);
2306 }
2307
2308 puts("\n----- done ------");
2309}
2310
2311#endif // TEST_ZLIB
2312
b76b015e
VZ
2313// ----------------------------------------------------------------------------
2314// date time
2315// ----------------------------------------------------------------------------
2316
d31b7b68 2317#ifdef TEST_DATETIME
b76b015e 2318
97e0ceea
VZ
2319#include <wx/date.h>
2320
b76b015e
VZ
2321#include <wx/datetime.h>
2322
299fcbfe
VZ
2323// the test data
2324struct Date
2325{
2326 wxDateTime::wxDateTime_t day;
2327 wxDateTime::Month month;
2328 int year;
2329 wxDateTime::wxDateTime_t hour, min, sec;
2330 double jdn;
211c2250 2331 wxDateTime::WeekDay wday;
299fcbfe
VZ
2332 time_t gmticks, ticks;
2333
2334 void Init(const wxDateTime::Tm& tm)
2335 {
2336 day = tm.mday;
2337 month = tm.mon;
2338 year = tm.year;
2339 hour = tm.hour;
2340 min = tm.min;
2341 sec = tm.sec;
2342 jdn = 0.0;
2343 gmticks = ticks = -1;
2344 }
2345
2346 wxDateTime DT() const
2347 { return wxDateTime(day, month, year, hour, min, sec); }
2348
239446b4
VZ
2349 bool SameDay(const wxDateTime::Tm& tm) const
2350 {
2351 return day == tm.mday && month == tm.mon && year == tm.year;
2352 }
2353
299fcbfe
VZ
2354 wxString Format() const
2355 {
2356 wxString s;
2357 s.Printf("%02d:%02d:%02d %10s %02d, %4d%s",
2358 hour, min, sec,
2359 wxDateTime::GetMonthName(month).c_str(),
2360 day,
2361 abs(wxDateTime::ConvertYearToBC(year)),
2362 year > 0 ? "AD" : "BC");
2363 return s;
2364 }
239446b4
VZ
2365
2366 wxString FormatDate() const
2367 {
2368 wxString s;
2369 s.Printf("%02d-%s-%4d%s",
2370 day,
f0f951fa 2371 wxDateTime::GetMonthName(month, wxDateTime::Name_Abbr).c_str(),
239446b4
VZ
2372 abs(wxDateTime::ConvertYearToBC(year)),
2373 year > 0 ? "AD" : "BC");
2374 return s;
2375 }
299fcbfe
VZ
2376};
2377
2378static const Date testDates[] =
2379{
211c2250
VZ
2380 { 1, wxDateTime::Jan, 1970, 00, 00, 00, 2440587.5, wxDateTime::Thu, 0, -3600 },
2381 { 21, wxDateTime::Jan, 2222, 00, 00, 00, 2532648.5, wxDateTime::Mon, -1, -1 },
2382 { 29, wxDateTime::May, 1976, 12, 00, 00, 2442928.0, wxDateTime::Sat, 202219200, 202212000 },
2383 { 29, wxDateTime::Feb, 1976, 00, 00, 00, 2442837.5, wxDateTime::Sun, 194400000, 194396400 },
2384 { 1, wxDateTime::Jan, 1900, 12, 00, 00, 2415021.0, wxDateTime::Mon, -1, -1 },
2385 { 1, wxDateTime::Jan, 1900, 00, 00, 00, 2415020.5, wxDateTime::Mon, -1, -1 },
2386 { 15, wxDateTime::Oct, 1582, 00, 00, 00, 2299160.5, wxDateTime::Fri, -1, -1 },
2387 { 4, wxDateTime::Oct, 1582, 00, 00, 00, 2299149.5, wxDateTime::Mon, -1, -1 },
2388 { 1, wxDateTime::Mar, 1, 00, 00, 00, 1721484.5, wxDateTime::Thu, -1, -1 },
2389 { 1, wxDateTime::Jan, 1, 00, 00, 00, 1721425.5, wxDateTime::Mon, -1, -1 },
239446b4
VZ
2390 { 31, wxDateTime::Dec, 0, 00, 00, 00, 1721424.5, wxDateTime::Sun, -1, -1 },
2391 { 1, wxDateTime::Jan, 0, 00, 00, 00, 1721059.5, wxDateTime::Sat, -1, -1 },
2392 { 12, wxDateTime::Aug, -1234, 00, 00, 00, 1270573.5, wxDateTime::Fri, -1, -1 },
2393 { 12, wxDateTime::Aug, -4000, 00, 00, 00, 260313.5, wxDateTime::Sat, -1, -1 },
211c2250 2394 { 24, wxDateTime::Nov, -4713, 00, 00, 00, -0.5, wxDateTime::Mon, -1, -1 },
299fcbfe
VZ
2395};
2396
2f02cb89
VZ
2397// this test miscellaneous static wxDateTime functions
2398static void TestTimeStatic()
2399{
2400 puts("\n*** wxDateTime static methods test ***");
2401
2402 // some info about the current date
2403 int year = wxDateTime::GetCurrentYear();
2404 printf("Current year %d is %sa leap one and has %d days.\n",
2405 year,
2406 wxDateTime::IsLeapYear(year) ? "" : "not ",
2407 wxDateTime::GetNumberOfDays(year));
2408
2409 wxDateTime::Month month = wxDateTime::GetCurrentMonth();
2410 printf("Current month is '%s' ('%s') and it has %d days\n",
f0f951fa 2411 wxDateTime::GetMonthName(month, wxDateTime::Name_Abbr).c_str(),
2f02cb89
VZ
2412 wxDateTime::GetMonthName(month).c_str(),
2413 wxDateTime::GetNumberOfDays(month));
2414
2415 // leap year logic
fcc3d7cb
VZ
2416 static const size_t nYears = 5;
2417 static const size_t years[2][nYears] =
2f02cb89
VZ
2418 {
2419 // first line: the years to test
2420 { 1990, 1976, 2000, 2030, 1984, },
2421
2422 // second line: TRUE if leap, FALSE otherwise
2423 { FALSE, TRUE, TRUE, FALSE, TRUE }
2424 };
2425
2426 for ( size_t n = 0; n < nYears; n++ )
2427 {
2428 int year = years[0][n];
239446b4
VZ
2429 bool should = years[1][n] != 0,
2430 is = wxDateTime::IsLeapYear(year);
2f02cb89 2431
239446b4 2432 printf("Year %d is %sa leap year (%s)\n",
2f02cb89 2433 year,
239446b4
VZ
2434 is ? "" : "not ",
2435 should == is ? "ok" : "ERROR");
2f02cb89
VZ
2436
2437 wxASSERT( should == wxDateTime::IsLeapYear(year) );
2438 }
2439}
2440
2441// test constructing wxDateTime objects
2442static void TestTimeSet()
2443{
2444 puts("\n*** wxDateTime construction test ***");
2445
299fcbfe
VZ
2446 for ( size_t n = 0; n < WXSIZEOF(testDates); n++ )
2447 {
2448 const Date& d1 = testDates[n];
2449 wxDateTime dt = d1.DT();
2450
2451 Date d2;
2452 d2.Init(dt.GetTm());
2453
2454 wxString s1 = d1.Format(),
2455 s2 = d2.Format();
2456
2457 printf("Date: %s == %s (%s)\n",
2458 s1.c_str(), s2.c_str(),
2459 s1 == s2 ? "ok" : "ERROR");
2460 }
2f02cb89
VZ
2461}
2462
fcc3d7cb
VZ
2463// test time zones stuff
2464static void TestTimeZones()
2465{
2466 puts("\n*** wxDateTime timezone test ***");
2467
2468 wxDateTime now = wxDateTime::Now();
2469
299fcbfe
VZ
2470 printf("Current GMT time:\t%s\n", now.Format("%c", wxDateTime::GMT0).c_str());
2471 printf("Unix epoch (GMT):\t%s\n", wxDateTime((time_t)0).Format("%c", wxDateTime::GMT0).c_str());
2472 printf("Unix epoch (EST):\t%s\n", wxDateTime((time_t)0).Format("%c", wxDateTime::EST).c_str());
2473 printf("Current time in Paris:\t%s\n", now.Format("%c", wxDateTime::CET).c_str());
2474 printf(" Moscow:\t%s\n", now.Format("%c", wxDateTime::MSK).c_str());
2475 printf(" New York:\t%s\n", now.Format("%c", wxDateTime::EST).c_str());
9d9b7755
VZ
2476
2477 wxDateTime::Tm tm = now.GetTm();
2478 if ( wxDateTime(tm) != now )
2479 {
2480 printf("ERROR: got %s instead of %s\n",
2481 wxDateTime(tm).Format().c_str(), now.Format().c_str());
2482 }
fcc3d7cb
VZ
2483}
2484
e6ec579c
VZ
2485// test some minimal support for the dates outside the standard range
2486static void TestTimeRange()
2487{
2488 puts("\n*** wxDateTime out-of-standard-range dates test ***");
2489
211c2250
VZ
2490 static const char *fmt = "%d-%b-%Y %H:%M:%S";
2491
1ef54dcf 2492 printf("Unix epoch:\t%s\n",
211c2250 2493 wxDateTime(2440587.5).Format(fmt).c_str());
1ef54dcf 2494 printf("Feb 29, 0: \t%s\n",
211c2250 2495 wxDateTime(29, wxDateTime::Feb, 0).Format(fmt).c_str());
e6ec579c 2496 printf("JDN 0: \t%s\n",
211c2250 2497 wxDateTime(0.0).Format(fmt).c_str());
e6ec579c 2498 printf("Jan 1, 1AD:\t%s\n",
211c2250 2499 wxDateTime(1, wxDateTime::Jan, 1).Format(fmt).c_str());
e6ec579c 2500 printf("May 29, 2099:\t%s\n",
211c2250 2501 wxDateTime(29, wxDateTime::May, 2099).Format(fmt).c_str());
e6ec579c
VZ
2502}
2503
299fcbfe 2504static void TestTimeTicks()
e6ec579c 2505{
299fcbfe 2506 puts("\n*** wxDateTime ticks test ***");
e6ec579c 2507
299fcbfe 2508 for ( size_t n = 0; n < WXSIZEOF(testDates); n++ )
1ef54dcf 2509 {
299fcbfe
VZ
2510 const Date& d = testDates[n];
2511 if ( d.ticks == -1 )
2512 continue;
1ef54dcf 2513
299fcbfe
VZ
2514 wxDateTime dt = d.DT();
2515 long ticks = (dt.GetValue() / 1000).ToLong();
2516 printf("Ticks of %s:\t% 10ld", d.Format().c_str(), ticks);
2517 if ( ticks == d.ticks )
2518 {
2519 puts(" (ok)");
2520 }
2521 else
2522 {
2523 printf(" (ERROR: should be %ld, delta = %ld)\n",
2524 d.ticks, ticks - d.ticks);
2525 }
2526
2527 dt = d.DT().ToTimezone(wxDateTime::GMT0);
2528 ticks = (dt.GetValue() / 1000).ToLong();
2529 printf("GMtks of %s:\t% 10ld", d.Format().c_str(), ticks);
2530 if ( ticks == d.gmticks )
2531 {
2532 puts(" (ok)");
2533 }
2534 else
2535 {
2536 printf(" (ERROR: should be %ld, delta = %ld)\n",
2537 d.gmticks, ticks - d.gmticks);
2538 }
2539 }
2540
2541 puts("");
2542}
2543
2544// test conversions to JDN &c
2545static void TestTimeJDN()
2546{
2547 puts("\n*** wxDateTime to JDN test ***");
1ef54dcf
VZ
2548
2549 for ( size_t n = 0; n < WXSIZEOF(testDates); n++ )
2550 {
2551 const Date& d = testDates[n];
299fcbfe 2552 wxDateTime dt(d.day, d.month, d.year, d.hour, d.min, d.sec);
1ef54dcf
VZ
2553 double jdn = dt.GetJulianDayNumber();
2554
299fcbfe 2555 printf("JDN of %s is:\t% 15.6f", d.Format().c_str(), jdn);
1ef54dcf
VZ
2556 if ( jdn == d.jdn )
2557 {
2558 puts(" (ok)");
2559 }
2560 else
2561 {
2562 printf(" (ERROR: should be %f, delta = %f)\n",
2563 d.jdn, jdn - d.jdn);
2564 }
2565 }
e6ec579c
VZ
2566}
2567
211c2250
VZ
2568// test week days computation
2569static void TestTimeWDays()
2570{
2571 puts("\n*** wxDateTime weekday test ***");
2572
239446b4
VZ
2573 // test GetWeekDay()
2574 size_t n;
2575 for ( n = 0; n < WXSIZEOF(testDates); n++ )
211c2250
VZ
2576 {
2577 const Date& d = testDates[n];
2578 wxDateTime dt(d.day, d.month, d.year, d.hour, d.min, d.sec);
2579
2580 wxDateTime::WeekDay wday = dt.GetWeekDay();
2581 printf("%s is: %s",
2582 d.Format().c_str(),
239446b4 2583 wxDateTime::GetWeekDayName(wday).c_str());
211c2250
VZ
2584 if ( wday == d.wday )
2585 {
2586 puts(" (ok)");
2587 }
2588 else
2589 {
2590 printf(" (ERROR: should be %s)\n",
239446b4
VZ
2591 wxDateTime::GetWeekDayName(d.wday).c_str());
2592 }
2593 }
2594
2595 puts("");
2596
2597 // test SetToWeekDay()
2598 struct WeekDateTestData
2599 {
2600 Date date; // the real date (precomputed)
2601 int nWeek; // its week index in the month
2602 wxDateTime::WeekDay wday; // the weekday
2603 wxDateTime::Month month; // the month
2604 int year; // and the year
2605
2606 wxString Format() const
2607 {
2608 wxString s, which;
2609 switch ( nWeek < -1 ? -nWeek : nWeek )
2610 {
2611 case 1: which = "first"; break;
2612 case 2: which = "second"; break;
2613 case 3: which = "third"; break;
2614 case 4: which = "fourth"; break;
2615 case 5: which = "fifth"; break;
2616
2617 case -1: which = "last"; break;
2618 }
2619
2620 if ( nWeek < -1 )
2621 {
2622 which += " from end";
2623 }
2624
2625 s.Printf("The %s %s of %s in %d",
2626 which.c_str(),
2627 wxDateTime::GetWeekDayName(wday).c_str(),
2628 wxDateTime::GetMonthName(month).c_str(),
2629 year);
2630
2631 return s;
2632 }
2633 };
2634
2635 // the array data was generated by the following python program
2636 /*
2637from DateTime import *
2638from whrandom import *
2639from string import *
2640
2641monthNames = [ 'Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec' ]
2642wdayNames = [ 'Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat', 'Sun' ]
2643
2644week = DateTimeDelta(7)
2645
2646for n in range(20):
2647 year = randint(1900, 2100)
2648 month = randint(1, 12)
2649 day = randint(1, 28)
2650 dt = DateTime(year, month, day)
2651 wday = dt.day_of_week
2652
2653 countFromEnd = choice([-1, 1])
2654 weekNum = 0;
2655
2656 while dt.month is month:
2657 dt = dt - countFromEnd * week
2658 weekNum = weekNum + countFromEnd
2659
2660 data = { 'day': rjust(`day`, 2), 'month': monthNames[month - 1], 'year': year, 'weekNum': rjust(`weekNum`, 2), 'wday': wdayNames[wday] }
97e0ceea 2661
239446b4
VZ
2662 print "{ { %(day)s, wxDateTime::%(month)s, %(year)d }, %(weekNum)d, "\
2663 "wxDateTime::%(wday)s, wxDateTime::%(month)s, %(year)d }," % data
97e0ceea 2664 */
239446b4
VZ
2665
2666 static const WeekDateTestData weekDatesTestData[] =
2667 {
2668 { { 20, wxDateTime::Mar, 2045 }, 3, wxDateTime::Mon, wxDateTime::Mar, 2045 },
2669 { { 5, wxDateTime::Jun, 1985 }, -4, wxDateTime::Wed, wxDateTime::Jun, 1985 },
2670 { { 12, wxDateTime::Nov, 1961 }, -3, wxDateTime::Sun, wxDateTime::Nov, 1961 },
2671 { { 27, wxDateTime::Feb, 2093 }, -1, wxDateTime::Fri, wxDateTime::Feb, 2093 },
2672 { { 4, wxDateTime::Jul, 2070 }, -4, wxDateTime::Fri, wxDateTime::Jul, 2070 },
2673 { { 2, wxDateTime::Apr, 1906 }, -5, wxDateTime::Mon, wxDateTime::Apr, 1906 },
2674 { { 19, wxDateTime::Jul, 2023 }, -2, wxDateTime::Wed, wxDateTime::Jul, 2023 },
2675 { { 5, wxDateTime::May, 1958 }, -4, wxDateTime::Mon, wxDateTime::May, 1958 },
2676 { { 11, wxDateTime::Aug, 1900 }, 2, wxDateTime::Sat, wxDateTime::Aug, 1900 },
2677 { { 14, wxDateTime::Feb, 1945 }, 2, wxDateTime::Wed, wxDateTime::Feb, 1945 },
2678 { { 25, wxDateTime::Jul, 1967 }, -1, wxDateTime::Tue, wxDateTime::Jul, 1967 },
2679 { { 9, wxDateTime::May, 1916 }, -4, wxDateTime::Tue, wxDateTime::May, 1916 },
2680 { { 20, wxDateTime::Jun, 1927 }, 3, wxDateTime::Mon, wxDateTime::Jun, 1927 },
2681 { { 2, wxDateTime::Aug, 2000 }, 1, wxDateTime::Wed, wxDateTime::Aug, 2000 },
2682 { { 20, wxDateTime::Apr, 2044 }, 3, wxDateTime::Wed, wxDateTime::Apr, 2044 },
2683 { { 20, wxDateTime::Feb, 1932 }, -2, wxDateTime::Sat, wxDateTime::Feb, 1932 },
2684 { { 25, wxDateTime::Jul, 2069 }, 4, wxDateTime::Thu, wxDateTime::Jul, 2069 },
2685 { { 3, wxDateTime::Apr, 1925 }, 1, wxDateTime::Fri, wxDateTime::Apr, 1925 },
2686 { { 21, wxDateTime::Mar, 2093 }, 3, wxDateTime::Sat, wxDateTime::Mar, 2093 },
2687 { { 3, wxDateTime::Dec, 2074 }, -5, wxDateTime::Mon, wxDateTime::Dec, 2074 },
2688 };
2689
2690 static const char *fmt = "%d-%b-%Y";
2691
2692 wxDateTime dt;
2693 for ( n = 0; n < WXSIZEOF(weekDatesTestData); n++ )
2694 {
2695 const WeekDateTestData& wd = weekDatesTestData[n];
2696
2697 dt.SetToWeekDay(wd.wday, wd.nWeek, wd.month, wd.year);
2698
2699 printf("%s is %s", wd.Format().c_str(), dt.Format(fmt).c_str());
2700
2701 const Date& d = wd.date;
2702 if ( d.SameDay(dt.GetTm()) )
2703 {
2704 puts(" (ok)");
2705 }
2706 else
2707 {
2708 dt.Set(d.day, d.month, d.year);
2709
2710 printf(" (ERROR: should be %s)\n", dt.Format(fmt).c_str());
211c2250
VZ
2711 }
2712 }
2713}
2714
239446b4
VZ
2715// test the computation of (ISO) week numbers
2716static void TestTimeWNumber()
2717{
2718 puts("\n*** wxDateTime week number test ***");
2719
2720 struct WeekNumberTestData
2721 {
2722 Date date; // the date
9d9b7755
VZ
2723 wxDateTime::wxDateTime_t week; // the week number in the year
2724 wxDateTime::wxDateTime_t wmon; // the week number in the month
2725 wxDateTime::wxDateTime_t wmon2; // same but week starts with Sun
239446b4
VZ
2726 wxDateTime::wxDateTime_t dnum; // day number in the year
2727 };
2728
2729 // data generated with the following python script:
2730 /*
2731from DateTime import *
2732from whrandom import *
2733from string import *
2734
2735monthNames = [ 'Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec' ]
2736wdayNames = [ 'Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat', 'Sun' ]
2737
9d9b7755
VZ
2738def GetMonthWeek(dt):
2739 weekNumMonth = dt.iso_week[1] - DateTime(dt.year, dt.month, 1).iso_week[1] + 1
2740 if weekNumMonth < 0:
2741 weekNumMonth = weekNumMonth + 53
2742 return weekNumMonth
7c968cee 2743
9d9b7755
VZ
2744def GetLastSundayBefore(dt):
2745 if dt.iso_week[2] == 7:
2746 return dt
2747 else:
2748 return dt - DateTimeDelta(dt.iso_week[2])
2749
239446b4
VZ
2750for n in range(20):
2751 year = randint(1900, 2100)
2752 month = randint(1, 12)
2753 day = randint(1, 28)
2754 dt = DateTime(year, month, day)
2755 dayNum = dt.day_of_year
2756 weekNum = dt.iso_week[1]
9d9b7755
VZ
2757 weekNumMonth = GetMonthWeek(dt)
2758
2759 weekNumMonth2 = 0
2760 dtSunday = GetLastSundayBefore(dt)
2761
2762 while dtSunday >= GetLastSundayBefore(DateTime(dt.year, dt.month, 1)):
2763 weekNumMonth2 = weekNumMonth2 + 1
2764 dtSunday = dtSunday - DateTimeDelta(7)
2765
2766 data = { 'day': rjust(`day`, 2), \
2767 'month': monthNames[month - 1], \
2768 'year': year, \
2769 'weekNum': rjust(`weekNum`, 2), \
2770 'weekNumMonth': weekNumMonth, \
2771 'weekNumMonth2': weekNumMonth2, \
2772 'dayNum': rjust(`dayNum`, 3) }
2773
2774 print " { { %(day)s, "\
2775 "wxDateTime::%(month)s, "\
2776 "%(year)d }, "\
2777 "%(weekNum)s, "\
2778 "%(weekNumMonth)s, "\
2779 "%(weekNumMonth2)s, "\
239446b4 2780 "%(dayNum)s }," % data
9d9b7755 2781
239446b4
VZ
2782 */
2783 static const WeekNumberTestData weekNumberTestDates[] =
2784 {
9d9b7755
VZ
2785 { { 27, wxDateTime::Dec, 1966 }, 52, 5, 5, 361 },
2786 { { 22, wxDateTime::Jul, 1926 }, 29, 4, 4, 203 },
2787 { { 22, wxDateTime::Oct, 2076 }, 43, 4, 4, 296 },
2788 { { 1, wxDateTime::Jul, 1967 }, 26, 1, 1, 182 },
2789 { { 8, wxDateTime::Nov, 2004 }, 46, 2, 2, 313 },
2790 { { 21, wxDateTime::Mar, 1920 }, 12, 3, 4, 81 },
2791 { { 7, wxDateTime::Jan, 1965 }, 1, 2, 2, 7 },
2792 { { 19, wxDateTime::Oct, 1999 }, 42, 4, 4, 292 },
2793 { { 13, wxDateTime::Aug, 1955 }, 32, 2, 2, 225 },
2794 { { 18, wxDateTime::Jul, 2087 }, 29, 3, 3, 199 },
2795 { { 2, wxDateTime::Sep, 2028 }, 35, 1, 1, 246 },
2796 { { 28, wxDateTime::Jul, 1945 }, 30, 5, 4, 209 },
2797 { { 15, wxDateTime::Jun, 1901 }, 24, 3, 3, 166 },
2798 { { 10, wxDateTime::Oct, 1939 }, 41, 3, 2, 283 },
2799 { { 3, wxDateTime::Dec, 1965 }, 48, 1, 1, 337 },
2800 { { 23, wxDateTime::Feb, 1940 }, 8, 4, 4, 54 },
2801 { { 2, wxDateTime::Jan, 1987 }, 1, 1, 1, 2 },
2802 { { 11, wxDateTime::Aug, 2079 }, 32, 2, 2, 223 },
2803 { { 2, wxDateTime::Feb, 2063 }, 5, 1, 1, 33 },
2804 { { 16, wxDateTime::Oct, 1942 }, 42, 3, 3, 289 },
239446b4
VZ
2805 };
2806
2807 for ( size_t n = 0; n < WXSIZEOF(weekNumberTestDates); n++ )
2808 {
2809 const WeekNumberTestData& wn = weekNumberTestDates[n];
2810 const Date& d = wn.date;
2811
2812 wxDateTime dt = d.DT();
2813
9d9b7755
VZ
2814 wxDateTime::wxDateTime_t
2815 week = dt.GetWeekOfYear(wxDateTime::Monday_First),
2816 wmon = dt.GetWeekOfMonth(wxDateTime::Monday_First),
2817 wmon2 = dt.GetWeekOfMonth(wxDateTime::Sunday_First),
2818 dnum = dt.GetDayOfYear();
239446b4
VZ
2819
2820 printf("%s: the day number is %d",
2821 d.FormatDate().c_str(), dnum);
2822 if ( dnum == wn.dnum )
2823 {
2824 printf(" (ok)");
2825 }
2826 else
2827 {
2828 printf(" (ERROR: should be %d)", wn.dnum);
2829 }
2830
9d9b7755
VZ
2831 printf(", week in month is %d", wmon);
2832 if ( wmon == wn.wmon )
2833 {
2834 printf(" (ok)");
2835 }
2836 else
2837 {
2838 printf(" (ERROR: should be %d)", wn.wmon);
2839 }
2840
2841 printf(" or %d", wmon2);
2842 if ( wmon2 == wn.wmon2 )
2843 {
2844 printf(" (ok)");
2845 }
2846 else
2847 {
2848 printf(" (ERROR: should be %d)", wn.wmon2);
2849 }
2850
2851 printf(", week in year is %d", week);
239446b4
VZ
2852 if ( week == wn.week )
2853 {
2854 puts(" (ok)");
2855 }
2856 else
2857 {
2858 printf(" (ERROR: should be %d)\n", wn.week);
2859 }
2860 }
2861}
2862
2863// test DST calculations
2864static void TestTimeDST()
2865{
2866 puts("\n*** wxDateTime DST test ***");
2867
2868 printf("DST is%s in effect now.\n\n",
2869 wxDateTime::Now().IsDST() ? "" : " not");
2870
2871 // taken from http://www.energy.ca.gov/daylightsaving.html
2872 static const Date datesDST[2][2004 - 1900 + 1] =
2873 {
2874 {
2875 { 1, wxDateTime::Apr, 1990 },
2876 { 7, wxDateTime::Apr, 1991 },
2877 { 5, wxDateTime::Apr, 1992 },
2878 { 4, wxDateTime::Apr, 1993 },
2879 { 3, wxDateTime::Apr, 1994 },
2880 { 2, wxDateTime::Apr, 1995 },
2881 { 7, wxDateTime::Apr, 1996 },
2882 { 6, wxDateTime::Apr, 1997 },
2883 { 5, wxDateTime::Apr, 1998 },
2884 { 4, wxDateTime::Apr, 1999 },
2885 { 2, wxDateTime::Apr, 2000 },
2886 { 1, wxDateTime::Apr, 2001 },
2887 { 7, wxDateTime::Apr, 2002 },
2888 { 6, wxDateTime::Apr, 2003 },
2889 { 4, wxDateTime::Apr, 2004 },
2890 },
2891 {
2892 { 28, wxDateTime::Oct, 1990 },
2893 { 27, wxDateTime::Oct, 1991 },
2894 { 25, wxDateTime::Oct, 1992 },
2895 { 31, wxDateTime::Oct, 1993 },
2896 { 30, wxDateTime::Oct, 1994 },
2897 { 29, wxDateTime::Oct, 1995 },
2898 { 27, wxDateTime::Oct, 1996 },
2899 { 26, wxDateTime::Oct, 1997 },
2900 { 25, wxDateTime::Oct, 1998 },
2901 { 31, wxDateTime::Oct, 1999 },
2902 { 29, wxDateTime::Oct, 2000 },
2903 { 28, wxDateTime::Oct, 2001 },
2904 { 27, wxDateTime::Oct, 2002 },
2905 { 26, wxDateTime::Oct, 2003 },
2906 { 31, wxDateTime::Oct, 2004 },
2907 }
2908 };
2909
2910 int year;
2911 for ( year = 1990; year < 2005; year++ )
2912 {
2913 wxDateTime dtBegin = wxDateTime::GetBeginDST(year, wxDateTime::USA),
2914 dtEnd = wxDateTime::GetEndDST(year, wxDateTime::USA);
2915
2916 printf("DST period in the US for year %d: from %s to %s",
2917 year, dtBegin.Format().c_str(), dtEnd.Format().c_str());
2918
2919 size_t n = year - 1990;
2920 const Date& dBegin = datesDST[0][n];
2921 const Date& dEnd = datesDST[1][n];
97e0ceea 2922
239446b4
VZ
2923 if ( dBegin.SameDay(dtBegin.GetTm()) && dEnd.SameDay(dtEnd.GetTm()) )
2924 {
2925 puts(" (ok)");
2926 }
2927 else
2928 {
2929 printf(" (ERROR: should be %s %d to %s %d)\n",
2930 wxDateTime::GetMonthName(dBegin.month).c_str(), dBegin.day,
2931 wxDateTime::GetMonthName(dEnd.month).c_str(), dEnd.day);
2932 }
2933 }
2934
2935 puts("");
2936
2937 for ( year = 1990; year < 2005; year++ )
2938 {
2939 printf("DST period in Europe for year %d: from %s to %s\n",
2940 year,
2941 wxDateTime::GetBeginDST(year, wxDateTime::Country_EEC).Format().c_str(),
2942 wxDateTime::GetEndDST(year, wxDateTime::Country_EEC).Format().c_str());
2943 }
2944}
2945
68ee7c47
VZ
2946// test wxDateTime -> text conversion
2947static void TestTimeFormat()
2948{
2949 puts("\n*** wxDateTime formatting test ***");
2950
b38e2f7d
VZ
2951 // some information may be lost during conversion, so store what kind
2952 // of info should we recover after a round trip
2953 enum CompareKind
68ee7c47 2954 {
b38e2f7d
VZ
2955 CompareNone, // don't try comparing
2956 CompareBoth, // dates and times should be identical
2957 CompareDate, // dates only
2958 CompareTime // time only
2959 };
2960
2961 static const struct
2962 {
2963 CompareKind compareKind;
2964 const char *format;
2965 } formatTestFormats[] =
2966 {
2967 { CompareBoth, "---> %c" },
2968 { CompareDate, "Date is %A, %d of %B, in year %Y" },
2969 { CompareBoth, "Date is %x, time is %X" },
2970 { CompareTime, "Time is %H:%M:%S or %I:%M:%S %p" },
2971 { CompareNone, "The day of year: %j, the week of year: %W" },
f6bcfd97 2972 { CompareDate, "ISO date without separators: %4Y%2m%2d" },
68ee7c47
VZ
2973 };
2974
2975 static const Date formatTestDates[] =
2976 {
68ee7c47
VZ
2977 { 29, wxDateTime::May, 1976, 18, 30, 00 },
2978 { 31, wxDateTime::Dec, 1999, 23, 30, 00 },
b38e2f7d
VZ
2979#if 0
2980 // this test can't work for other centuries because it uses two digit
2981 // years in formats, so don't even try it
68ee7c47
VZ
2982 { 29, wxDateTime::May, 2076, 18, 30, 00 },
2983 { 29, wxDateTime::Feb, 2400, 02, 15, 25 },
2984 { 01, wxDateTime::Jan, -52, 03, 16, 47 },
b38e2f7d 2985#endif
68ee7c47
VZ
2986 };
2987
2988 // an extra test (as it doesn't depend on date, don't do it in the loop)
2989 printf("%s\n", wxDateTime::Now().Format("Our timezone is %Z").c_str());
2990
b38e2f7d 2991 for ( size_t d = 0; d < WXSIZEOF(formatTestDates) + 1; d++ )
68ee7c47
VZ
2992 {
2993 puts("");
2994
b38e2f7d 2995 wxDateTime dt = d == 0 ? wxDateTime::Now() : formatTestDates[d - 1].DT();
68ee7c47
VZ
2996 for ( size_t n = 0; n < WXSIZEOF(formatTestFormats); n++ )
2997 {
b38e2f7d 2998 wxString s = dt.Format(formatTestFormats[n].format);
f0f951fa
VZ
2999 printf("%s", s.c_str());
3000
b38e2f7d
VZ
3001 // what can we recover?
3002 int kind = formatTestFormats[n].compareKind;
3003
f0f951fa
VZ
3004 // convert back
3005 wxDateTime dt2;
b38e2f7d 3006 const wxChar *result = dt2.ParseFormat(s, formatTestFormats[n].format);
f0f951fa
VZ
3007 if ( !result )
3008 {
b38e2f7d
VZ
3009 // converion failed - should it have?
3010 if ( kind == CompareNone )
3011 puts(" (ok)");
3012 else
3013 puts(" (ERROR: conversion back failed)");
f0f951fa
VZ
3014 }
3015 else if ( *result )
3016 {
3017 // should have parsed the entire string
3018 puts(" (ERROR: conversion back stopped too soon)");
3019 }
f0f951fa
VZ
3020 else
3021 {
b38e2f7d
VZ
3022 bool equal = FALSE; // suppress compilaer warning
3023 switch ( kind )
3024 {
3025 case CompareBoth:
3026 equal = dt2 == dt;
3027 break;
3028
3029 case CompareDate:
3030 equal = dt.IsSameDate(dt2);
3031 break;
3032
3033 case CompareTime:
3034 equal = dt.IsSameTime(dt2);
3035 break;
3036 }
3037
3038 if ( !equal )
3039 {
3040 printf(" (ERROR: got back '%s' instead of '%s')\n",
3041 dt2.Format().c_str(), dt.Format().c_str());
3042 }
3043 else
3044 {
3045 puts(" (ok)");
3046 }
f0f951fa 3047 }
68ee7c47
VZ
3048 }
3049 }
3050}
3051
97e0ceea
VZ
3052// test text -> wxDateTime conversion
3053static void TestTimeParse()
3054{
3055 puts("\n*** wxDateTime parse test ***");
3056
3057 struct ParseTestData
3058 {
3059 const char *format;
3060 Date date;
3061 bool good;
3062 };
3063
3064 static const ParseTestData parseTestDates[] =
3065 {
68ee7c47
VZ
3066 { "Sat, 18 Dec 1999 00:46:40 +0100", { 18, wxDateTime::Dec, 1999, 00, 46, 40 }, TRUE },
3067 { "Wed, 1 Dec 1999 05:17:20 +0300", { 1, wxDateTime::Dec, 1999, 03, 17, 20 }, TRUE },
97e0ceea
VZ
3068 };
3069
3070 for ( size_t n = 0; n < WXSIZEOF(parseTestDates); n++ )
3071 {
3072 const char *format = parseTestDates[n].format;
3073
3074 printf("%s => ", format);
3075
3076 wxDateTime dt;
3077 if ( dt.ParseRfc822Date(format) )
3078 {
3079 printf("%s ", dt.Format().c_str());
3080
3081 if ( parseTestDates[n].good )
3082 {
3083 wxDateTime dtReal = parseTestDates[n].date.DT();
3084 if ( dt == dtReal )
3085 {
3086 puts("(ok)");
3087 }
3088 else
3089 {
3090 printf("(ERROR: should be %s)\n", dtReal.Format().c_str());
3091 }
3092 }
3093 else
3094 {
3095 puts("(ERROR: bad format)");
3096 }
3097 }
3098 else
3099 {
3100 printf("bad format (%s)\n",
3101 parseTestDates[n].good ? "ERROR" : "ok");
3102 }
3103 }
3104}
3105
b92fd37c 3106static void TestDateTimeInteractive()
9d9b7755
VZ
3107{
3108 puts("\n*** interactive wxDateTime tests ***");
3109
3110 char buf[128];
3111
3112 for ( ;; )
3113 {
3114 printf("Enter a date: ");
3115 if ( !fgets(buf, WXSIZEOF(buf), stdin) )
3116 break;
3117
f6bcfd97
BP
3118 // kill the last '\n'
3119 buf[strlen(buf) - 1] = 0;
3120
9d9b7755 3121 wxDateTime dt;
f6bcfd97
BP
3122 const char *p = dt.ParseDate(buf);
3123 if ( !p )
9d9b7755 3124 {
f6bcfd97 3125 printf("ERROR: failed to parse the date '%s'.\n", buf);
9d9b7755
VZ
3126
3127 continue;
3128 }
f6bcfd97
BP
3129 else if ( *p )
3130 {
3131 printf("WARNING: parsed only first %u characters.\n", p - buf);
3132 }
9d9b7755
VZ
3133
3134 printf("%s: day %u, week of month %u/%u, week of year %u\n",
f6bcfd97 3135 dt.Format("%b %d, %Y").c_str(),
9d9b7755
VZ
3136 dt.GetDayOfYear(),
3137 dt.GetWeekOfMonth(wxDateTime::Monday_First),
3138 dt.GetWeekOfMonth(wxDateTime::Sunday_First),
3139 dt.GetWeekOfYear(wxDateTime::Monday_First));
3140 }
3141
3142 puts("\n*** done ***");
3143}
3144
f6bcfd97
BP
3145static void TestTimeMS()
3146{
3147 puts("*** testing millisecond-resolution support in wxDateTime ***");
3148
3149 wxDateTime dt1 = wxDateTime::Now(),
3150 dt2 = wxDateTime::UNow();
3151
3152 printf("Now = %s\n", dt1.Format("%H:%M:%S:%l").c_str());
3153 printf("UNow = %s\n", dt2.Format("%H:%M:%S:%l").c_str());
3ca6a5f0
BP
3154 printf("Dummy loop: ");
3155 for ( int i = 0; i < 6000; i++ )
3156 {
3157 //for ( int j = 0; j < 10; j++ )
3158 {
3159 wxString s;
3160 s.Printf("%g", sqrt(i));
3161 }
3162
3163 if ( !(i % 100) )
3164 putchar('.');
3165 }
3166 puts(", done");
3167
3168 dt1 = dt2;
3169 dt2 = wxDateTime::UNow();
3170 printf("UNow = %s\n", dt2.Format("%H:%M:%S:%l").c_str());
3171
3172 printf("Loop executed in %s ms\n", (dt2 - dt1).Format("%l").c_str());
f6bcfd97
BP
3173
3174 puts("\n*** done ***");
3175}
3176
9d9b7755
VZ
3177static void TestTimeArithmetics()
3178{
3179 puts("\n*** testing arithmetic operations on wxDateTime ***");
3180
f6bcfd97 3181 static const struct ArithmData
9d9b7755 3182 {
f6bcfd97
BP
3183 ArithmData(const wxDateSpan& sp, const char *nam)
3184 : span(sp), name(nam) { }
3185
9d9b7755
VZ
3186 wxDateSpan span;
3187 const char *name;
7c968cee 3188 } testArithmData[] =
9d9b7755 3189 {
f6bcfd97
BP
3190 ArithmData(wxDateSpan::Day(), "day"),
3191 ArithmData(wxDateSpan::Week(), "week"),
3192 ArithmData(wxDateSpan::Month(), "month"),
3193 ArithmData(wxDateSpan::Year(), "year"),
3194 ArithmData(wxDateSpan(1, 2, 3, 4), "year, 2 months, 3 weeks, 4 days"),
9d9b7755 3195 };
7c968cee 3196
9d9b7755
VZ
3197 wxDateTime dt(29, wxDateTime::Dec, 1999), dt1, dt2;
3198
3199 for ( size_t n = 0; n < WXSIZEOF(testArithmData); n++ )
3200 {
3201 wxDateSpan span = testArithmData[n].span;
3202 dt1 = dt + span;
3203 dt2 = dt - span;
3204
3205 const char *name = testArithmData[n].name;
3206 printf("%s + %s = %s, %s - %s = %s\n",
3207 dt.FormatISODate().c_str(), name, dt1.FormatISODate().c_str(),
3208 dt.FormatISODate().c_str(), name, dt2.FormatISODate().c_str());
3209
3210 printf("Going back: %s", (dt1 - span).FormatISODate().c_str());
3211 if ( dt1 - span == dt )
3212 {
3213 puts(" (ok)");
3214 }
3215 else
3216 {
3217 printf(" (ERROR: should be %s)\n", dt.FormatISODate().c_str());
3218 }
3219
3220 printf("Going forward: %s", (dt2 + span).FormatISODate().c_str());
3221 if ( dt2 + span == dt )
3222 {
3223 puts(" (ok)");
3224 }
3225 else
3226 {
3227 printf(" (ERROR: should be %s)\n", dt.FormatISODate().c_str());
3228 }
3229
3230 printf("Double increment: %s", (dt2 + 2*span).FormatISODate().c_str());
3231 if ( dt2 + 2*span == dt1 )
3232 {
3233 puts(" (ok)");
3234 }
3235 else
3236 {
3237 printf(" (ERROR: should be %s)\n", dt2.FormatISODate().c_str());
3238 }
3239
3240 puts("");
3241 }
3242}
3243
0de868d9
VZ
3244static void TestTimeHolidays()
3245{
3246 puts("\n*** testing wxDateTimeHolidayAuthority ***\n");
3247
3248 wxDateTime::Tm tm = wxDateTime(29, wxDateTime::May, 2000).GetTm();
3249 wxDateTime dtStart(1, tm.mon, tm.year),
3250 dtEnd = dtStart.GetLastMonthDay();
3251
3252 wxDateTimeArray hol;
3253 wxDateTimeHolidayAuthority::GetHolidaysInRange(dtStart, dtEnd, hol);
3254
3255 const wxChar *format = "%d-%b-%Y (%a)";
3256
3257 printf("All holidays between %s and %s:\n",
3258 dtStart.Format(format).c_str(), dtEnd.Format(format).c_str());
3259
3260 size_t count = hol.GetCount();
3261 for ( size_t n = 0; n < count; n++ )
3262 {
3263 printf("\t%s\n", hol[n].Format(format).c_str());
3264 }
3265
3266 puts("");
3267}
3268
f6bcfd97
BP
3269static void TestTimeZoneBug()
3270{
3271 puts("\n*** testing for DST/timezone bug ***\n");
3272
3273 wxDateTime date = wxDateTime(1, wxDateTime::Mar, 2000);
3274 for ( int i = 0; i < 31; i++ )
3275 {
3276 printf("Date %s: week day %s.\n",
3277 date.Format(_T("%d-%m-%Y")).c_str(),
3278 date.GetWeekDayName(date.GetWeekDay()).c_str());
3279
3280 date += wxDateSpan::Day();
3281 }
3282
3283 puts("");
3284}
3285
68ee7c47
VZ
3286#if 0
3287
97e0ceea
VZ
3288// test compatibility with the old wxDate/wxTime classes
3289static void TestTimeCompatibility()
3290{
3291 puts("\n*** wxDateTime compatibility test ***");
3292
3293 printf("wxDate for JDN 0: %s\n", wxDate(0l).FormatDate().c_str());
3294 printf("wxDate for MJD 0: %s\n", wxDate(2400000).FormatDate().c_str());
3295
3296 double jdnNow = wxDateTime::Now().GetJDN();
3297 long jdnMidnight = (long)(jdnNow - 0.5);
3298 printf("wxDate for today: %s\n", wxDate(jdnMidnight).FormatDate().c_str());
3299
3300 jdnMidnight = wxDate().Set().GetJulianDate();
3301 printf("wxDateTime for today: %s\n",
3302 wxDateTime((double)(jdnMidnight + 0.5)).Format("%c", wxDateTime::GMT0).c_str());
3303
3304 int flags = wxEUROPEAN;//wxFULL;
3305 wxDate date;
3306 date.Set();
3307 printf("Today is %s\n", date.FormatDate(flags).c_str());
3308 for ( int n = 0; n < 7; n++ )
3309 {
3310 printf("Previous %s is %s\n",
3311 wxDateTime::GetWeekDayName((wxDateTime::WeekDay)n),
3312 date.Previous(n + 1).FormatDate(flags).c_str());
3313 }
3314}
3315
68ee7c47
VZ
3316#endif // 0
3317
d31b7b68 3318#endif // TEST_DATETIME
b76b015e 3319
e87271f3
VZ
3320// ----------------------------------------------------------------------------
3321// threads
3322// ----------------------------------------------------------------------------
3323
3324#ifdef TEST_THREADS
3325
bbfa0322 3326#include <wx/thread.h>
37667812 3327
bbfa0322
VZ
3328static size_t gs_counter = (size_t)-1;
3329static wxCriticalSection gs_critsect;
b568d04f 3330static wxCondition gs_cond;
bbfa0322 3331
b568d04f 3332class MyJoinableThread : public wxThread
bbfa0322
VZ
3333{
3334public:
b568d04f
VZ
3335 MyJoinableThread(size_t n) : wxThread(wxTHREAD_JOINABLE)
3336 { m_n = n; Create(); }
bbfa0322
VZ
3337
3338 // thread execution starts here
b568d04f 3339 virtual ExitCode Entry();
bbfa0322 3340
b568d04f
VZ
3341private:
3342 size_t m_n;
bbfa0322
VZ
3343};
3344
b568d04f 3345wxThread::ExitCode MyJoinableThread::Entry()
bbfa0322 3346{
b568d04f
VZ
3347 unsigned long res = 1;
3348 for ( size_t n = 1; n < m_n; n++ )
3349 {
3350 res *= n;
3351
3352 // it's a loooong calculation :-)
3353 Sleep(100);
3354 }
bbfa0322 3355
b568d04f 3356 return (ExitCode)res;
bbfa0322
VZ
3357}
3358
b568d04f
VZ
3359class MyDetachedThread : public wxThread
3360{
3361public:
fcc3d7cb
VZ
3362 MyDetachedThread(size_t n, char ch)
3363 {
3364 m_n = n;
3365 m_ch = ch;
3366 m_cancelled = FALSE;
3367
3368 Create();
3369 }
b568d04f
VZ
3370
3371 // thread execution starts here
3372 virtual ExitCode Entry();
3373
3374 // and stops here
3375 virtual void OnExit();
3376
3377private:
9fc3ad34
VZ
3378 size_t m_n; // number of characters to write
3379 char m_ch; // character to write
fcc3d7cb
VZ
3380
3381 bool m_cancelled; // FALSE if we exit normally
b568d04f
VZ
3382};
3383
3384wxThread::ExitCode MyDetachedThread::Entry()
bbfa0322
VZ
3385{
3386 {
3387 wxCriticalSectionLocker lock(gs_critsect);
3388 if ( gs_counter == (size_t)-1 )
3389 gs_counter = 1;
3390 else
3391 gs_counter++;
3392 }
3393
9fc3ad34 3394 for ( size_t n = 0; n < m_n; n++ )
bbfa0322
VZ
3395 {
3396 if ( TestDestroy() )
fcc3d7cb
VZ
3397 {
3398 m_cancelled = TRUE;
3399
bbfa0322 3400 break;
fcc3d7cb 3401 }
bbfa0322
VZ
3402
3403 putchar(m_ch);
3404 fflush(stdout);
3405
3406 wxThread::Sleep(100);
3407 }
3408
b568d04f 3409 return 0;
bbfa0322
VZ
3410}
3411
b568d04f 3412void MyDetachedThread::OnExit()
bbfa0322 3413{
9fc3ad34
VZ
3414 wxLogTrace("thread", "Thread %ld is in OnExit", GetId());
3415
bbfa0322 3416 wxCriticalSectionLocker lock(gs_critsect);
fcc3d7cb 3417 if ( !--gs_counter && !m_cancelled )
b568d04f 3418 gs_cond.Signal();
bbfa0322
VZ
3419}
3420
9fc3ad34
VZ
3421void TestDetachedThreads()
3422{
2f02cb89 3423 puts("\n*** Testing detached threads ***");
9fc3ad34
VZ
3424
3425 static const size_t nThreads = 3;
3426 MyDetachedThread *threads[nThreads];
3427 size_t n;
3428 for ( n = 0; n < nThreads; n++ )
3429 {
3430 threads[n] = new MyDetachedThread(10, 'A' + n);
3431 }
3432
3433 threads[0]->SetPriority(WXTHREAD_MIN_PRIORITY);
3434 threads[1]->SetPriority(WXTHREAD_MAX_PRIORITY);
3435
3436 for ( n = 0; n < nThreads; n++ )
3437 {
3438 threads[n]->Run();
3439 }
3440
3441 // wait until all threads terminate
3442 gs_cond.Wait();
3443
3444 puts("");
3445}
3446
3447void TestJoinableThreads()
3448{
2f02cb89 3449 puts("\n*** Testing a joinable thread (a loooong calculation...) ***");
9fc3ad34
VZ
3450
3451 // calc 10! in the background
3452 MyJoinableThread thread(10);
3453 thread.Run();
3454
3455 printf("\nThread terminated with exit code %lu.\n",
3456 (unsigned long)thread.Wait());
3457}
3458
3459void TestThreadSuspend()
3460{
2f02cb89
VZ
3461 puts("\n*** Testing thread suspend/resume functions ***");
3462
3463 MyDetachedThread *thread = new MyDetachedThread(15, 'X');
9fc3ad34
VZ
3464
3465 thread->Run();
3466
3467 // this is for this demo only, in a real life program we'd use another
3468 // condition variable which would be signaled from wxThread::Entry() to
3469 // tell us that the thread really started running - but here just wait a
3470 // bit and hope that it will be enough (the problem is, of course, that
3471 // the thread might still not run when we call Pause() which will result
3472 // in an error)
3473 wxThread::Sleep(300);
3474
3475 for ( size_t n = 0; n < 3; n++ )
3476 {
3477 thread->Pause();
3478
3479 puts("\nThread suspended");
3480 if ( n > 0 )
3481 {
3482 // don't sleep but resume immediately the first time
3483 wxThread::Sleep(300);
3484 }
3485 puts("Going to resume the thread");
3486
3487 thread->Resume();
3488 }
3489
4c460b34
VZ
3490 puts("Waiting until it terminates now");
3491
9fc3ad34
VZ
3492 // wait until the thread terminates
3493 gs_cond.Wait();
3494
3495 puts("");
3496}
3497
2f02cb89
VZ
3498void TestThreadDelete()
3499{
3500 // As above, using Sleep() is only for testing here - we must use some
3501 // synchronisation object instead to ensure that the thread is still
3502 // running when we delete it - deleting a detached thread which already
3503 // terminated will lead to a crash!
3504
3505 puts("\n*** Testing thread delete function ***");
3506
4c460b34
VZ
3507 MyDetachedThread *thread0 = new MyDetachedThread(30, 'W');
3508
3509 thread0->Delete();
3510
3511 puts("\nDeleted a thread which didn't start to run yet.");
3512
2f02cb89
VZ
3513 MyDetachedThread *thread1 = new MyDetachedThread(30, 'Y');
3514
3515 thread1->Run();
3516
3517 wxThread::Sleep(300);
3518
3519 thread1->Delete();
3520
3521 puts("\nDeleted a running thread.");
3522
3523 MyDetachedThread *thread2 = new MyDetachedThread(30, 'Z');
3524
3525 thread2->Run();
3526
3527 wxThread::Sleep(300);
3528
3529 thread2->Pause();
3530
3531 thread2->Delete();
3532
3533 puts("\nDeleted a sleeping thread.");
3534
4c460b34
VZ
3535 MyJoinableThread thread3(20);
3536 thread3.Run();
2f02cb89 3537
4c460b34 3538 thread3.Delete();
2f02cb89
VZ
3539
3540 puts("\nDeleted a joinable thread.");
3541
4c460b34
VZ
3542 MyJoinableThread thread4(2);
3543 thread4.Run();
2f02cb89
VZ
3544
3545 wxThread::Sleep(300);
3546
4c460b34 3547 thread4.Delete();
2f02cb89
VZ
3548
3549 puts("\nDeleted a joinable thread which already terminated.");
3550
3551 puts("");
3552}
3553
e87271f3
VZ
3554#endif // TEST_THREADS
3555
3556// ----------------------------------------------------------------------------
3557// arrays
3558// ----------------------------------------------------------------------------
3559
3560#ifdef TEST_ARRAYS
3561
f6bcfd97 3562static void PrintArray(const char* name, const wxArrayString& array)
e87271f3
VZ
3563{
3564 printf("Dump of the array '%s'\n", name);
3565
3566 size_t nCount = array.GetCount();
3567 for ( size_t n = 0; n < nCount; n++ )
3568 {
3569 printf("\t%s[%u] = '%s'\n", name, n, array[n].c_str());
3570 }
3571}
3572
d6c9c1b7
VZ
3573static void PrintArray(const char* name, const wxArrayInt& array)
3574{
3575 printf("Dump of the array '%s'\n", name);
3576
3577 size_t nCount = array.GetCount();
3578 for ( size_t n = 0; n < nCount; n++ )
3579 {
3580 printf("\t%s[%u] = %d\n", name, n, array[n]);
3581 }
3582}
3583
3584int wxCMPFUNC_CONV StringLenCompare(const wxString& first,
3585 const wxString& second)
f6bcfd97
BP
3586{
3587 return first.length() - second.length();
3588}
3589
d6c9c1b7
VZ
3590int wxCMPFUNC_CONV IntCompare(int *first,
3591 int *second)
3592{
3593 return *first - *second;
3594}
3595
3596int wxCMPFUNC_CONV IntRevCompare(int *first,
3597 int *second)
3598{
3599 return *second - *first;
3600}
3601
3602static void TestArrayOfInts()
3603{
3604 puts("*** Testing wxArrayInt ***\n");
3605
3606 wxArrayInt a;
3607 a.Add(1);
3608 a.Add(17);
3609 a.Add(5);
3610 a.Add(3);
3611
3612 puts("Initially:");
3613 PrintArray("a", a);
3614
3615 puts("After sort:");
3616 a.Sort(IntCompare);
3617 PrintArray("a", a);
3618
3619 puts("After reverse sort:");
3620 a.Sort(IntRevCompare);
3621 PrintArray("a", a);
3622}
3623
f6bcfd97
BP
3624#include "wx/dynarray.h"
3625
3626WX_DECLARE_OBJARRAY(Bar, ArrayBars);
3627#include "wx/arrimpl.cpp"
3628WX_DEFINE_OBJARRAY(ArrayBars);
3629
3630static void TestArrayOfObjects()
3631{
3632 puts("*** Testing wxObjArray ***\n");
3633
3634 {
3635 ArrayBars bars;
3636 Bar bar("second bar");
3637
3638 printf("Initially: %u objects in the array, %u objects total.\n",
3639 bars.GetCount(), Bar::GetNumber());
3640
3641 bars.Add(new Bar("first bar"));
3642 bars.Add(bar);
3643
3644 printf("Now: %u objects in the array, %u objects total.\n",
3645 bars.GetCount(), Bar::GetNumber());
3646
3647 bars.Empty();
3648
3649 printf("After Empty(): %u objects in the array, %u objects total.\n",
3650 bars.GetCount(), Bar::GetNumber());
3651 }
3652
3653 printf("Finally: no more objects in the array, %u objects total.\n",
3654 Bar::GetNumber());
3655}
3656
e87271f3
VZ
3657#endif // TEST_ARRAYS
3658
9fc3ad34
VZ
3659// ----------------------------------------------------------------------------
3660// strings
3661// ----------------------------------------------------------------------------
3662
3663#ifdef TEST_STRINGS
3664
3665#include "wx/timer.h"
bbf8fc53 3666#include "wx/tokenzr.h"
9fc3ad34 3667
7c968cee
VZ
3668static void TestStringConstruction()
3669{
3670 puts("*** Testing wxString constructores ***");
3671
3672 #define TEST_CTOR(args, res) \
3673 { \
3674 wxString s args ; \
3675 printf("wxString%s = %s ", #args, s.c_str()); \
3676 if ( s == res ) \
3677 { \
3678 puts("(ok)"); \
3679 } \
3680 else \
3681 { \
3682 printf("(ERROR: should be %s)\n", res); \
3683 } \
3684 }
3685
3686 TEST_CTOR((_T('Z'), 4), _T("ZZZZ"));
3687 TEST_CTOR((_T("Hello"), 4), _T("Hell"));
3688 TEST_CTOR((_T("Hello"), 5), _T("Hello"));
3689 // TEST_CTOR((_T("Hello"), 6), _T("Hello")); -- should give assert failure
3690
3691 static const wxChar *s = _T("?really!");
3692 const wxChar *start = wxStrchr(s, _T('r'));
3693 const wxChar *end = wxStrchr(s, _T('!'));
3694 TEST_CTOR((start, end), _T("really"));
3695
3696 puts("");
3697}
3698
299fcbfe 3699static void TestString()
9fc3ad34
VZ
3700{
3701 wxStopWatch sw;
3702
3703 wxString a, b, c;
3704
3705 a.reserve (128);
3706 b.reserve (128);
3707 c.reserve (128);
3708
3709 for (int i = 0; i < 1000000; ++i)
3710 {
3711 a = "Hello";
3712 b = " world";
3713 c = "! How'ya doin'?";
3714 a += b;
3715 a += c;
3716 c = "Hello world! What's up?";
3717 if (c != a)
3718 c = "Doh!";
3719 }
3720
3721 printf ("TestString elapsed time: %ld\n", sw.Time());
3722}
3723
299fcbfe 3724static void TestPChar()
9fc3ad34
VZ
3725{
3726 wxStopWatch sw;
3727
3728 char a [128];
3729 char b [128];
3730 char c [128];
3731
3732 for (int i = 0; i < 1000000; ++i)
3733 {
3734 strcpy (a, "Hello");
3735 strcpy (b, " world");
3736 strcpy (c, "! How'ya doin'?");
3737 strcat (a, b);
3738 strcat (a, c);
3739 strcpy (c, "Hello world! What's up?");
3740 if (strcmp (c, a) == 0)
3741 strcpy (c, "Doh!");
3742 }
3743
3744 printf ("TestPChar elapsed time: %ld\n", sw.Time());
3745}
3746
299fcbfe
VZ
3747static void TestStringSub()
3748{
3749 wxString s("Hello, world!");
3750
3751 puts("*** Testing wxString substring extraction ***");
3752
3753 printf("String = '%s'\n", s.c_str());
3754 printf("Left(5) = '%s'\n", s.Left(5).c_str());
3755 printf("Right(6) = '%s'\n", s.Right(6).c_str());
3756 printf("Mid(3, 5) = '%s'\n", s(3, 5).c_str());
3757 printf("Mid(3) = '%s'\n", s.Mid(3).c_str());
3758 printf("substr(3, 5) = '%s'\n", s.substr(3, 5).c_str());
3759 printf("substr(3) = '%s'\n", s.substr(3).c_str());
3760
f6bcfd97
BP
3761 static const wxChar *prefixes[] =
3762 {
3763 _T("Hello"),
3764 _T("Hello, "),
3765 _T("Hello, world!"),
3766 _T("Hello, world!!!"),
3767 _T(""),
3768 _T("Goodbye"),
3769 _T("Hi"),
3770 };
3771
3772 for ( size_t n = 0; n < WXSIZEOF(prefixes); n++ )
3773 {
3774 wxString prefix = prefixes[n], rest;
3775 bool rc = s.StartsWith(prefix, &rest);
3776 printf("StartsWith('%s') = %s", prefix.c_str(), rc ? "TRUE" : "FALSE");
3777 if ( rc )
3778 {
3779 printf(" (the rest is '%s')\n", rest.c_str());
3780 }
3781 else
3782 {
3783 putchar('\n');
3784 }
3785 }
3786
299fcbfe
VZ
3787 puts("");
3788}
3789
f0f951fa
VZ
3790static void TestStringFormat()
3791{
3792 puts("*** Testing wxString formatting ***");
3793
3794 wxString s;
3795 s.Printf("%03d", 18);
3796
3797 printf("Number 18: %s\n", wxString::Format("%03d", 18).c_str());
3798 printf("Number 18: %s\n", s.c_str());
3799
3800 puts("");
3801}
3802
d71fa6fb
VZ
3803// returns "not found" for npos, value for all others
3804static wxString PosToString(size_t res)
3805{
3806 wxString s = res == wxString::npos ? wxString(_T("not found"))
3807 : wxString::Format(_T("%u"), res);
3808 return s;
3809}
3810
3811static void TestStringFind()
3812{
3813 puts("*** Testing wxString find() functions ***");
3814
3815 static const wxChar *strToFind = _T("ell");
3816 static const struct StringFindTest
3817 {
3818 const wxChar *str;
3819 size_t start,
3820 result; // of searching "ell" in str
3821 } findTestData[] =
3822 {
3823 { _T("Well, hello world"), 0, 1 },
3824 { _T("Well, hello world"), 6, 7 },
3825 { _T("Well, hello world"), 9, wxString::npos },
3826 };
3827
3828 for ( size_t n = 0; n < WXSIZEOF(findTestData); n++ )
3829 {
3830 const StringFindTest& ft = findTestData[n];
3831 size_t res = wxString(ft.str).find(strToFind, ft.start);
3832
3833 printf(_T("Index of '%s' in '%s' starting from %u is %s "),
3834 strToFind, ft.str, ft.start, PosToString(res).c_str());
3835
3836 size_t resTrue = ft.result;
3837 if ( res == resTrue )
3838 {
3839 puts(_T("(ok)"));
3840 }
3841 else
3842 {
3843 printf(_T("(ERROR: should be %s)\n"),
3844 PosToString(resTrue).c_str());
3845 }
3846 }
3847
3848 puts("");
3849}
3850
bbf8fc53
VZ
3851static void TestStringTokenizer()
3852{
3853 puts("*** Testing wxStringTokenizer ***");
3854
7c968cee
VZ
3855 static const wxChar *modeNames[] =
3856 {
3857 _T("default"),
3858 _T("return empty"),
3859 _T("return all empty"),
3860 _T("with delims"),
3861 _T("like strtok"),
3862 };
3863
bbf8fc53
VZ
3864 static const struct StringTokenizerTest
3865 {
7c968cee
VZ
3866 const wxChar *str; // string to tokenize
3867 const wxChar *delims; // delimiters to use
3868 size_t count; // count of token
3869 wxStringTokenizerMode mode; // how should we tokenize it
3870 } tokenizerTestData[] =
3871 {
3872 { _T(""), _T(" "), 0 },
3873 { _T("Hello, world"), _T(" "), 2 },
3874 { _T("Hello, world "), _T(" "), 2 },
3875 { _T("Hello, world"), _T(","), 2 },
3876 { _T("Hello, world!"), _T(",!"), 2 },
3877 { _T("Hello,, world!"), _T(",!"), 3 },
3878 { _T("Hello, world!"), _T(",!"), 3, wxTOKEN_RET_EMPTY_ALL },
3879 { _T("username:password:uid:gid:gecos:home:shell"), _T(":"), 7 },
3880 { _T("1 \t3\t4 6 "), wxDEFAULT_DELIMITERS, 4 },
3881 { _T("1 \t3\t4 6 "), wxDEFAULT_DELIMITERS, 6, wxTOKEN_RET_EMPTY },
3882 { _T("1 \t3\t4 6 "), wxDEFAULT_DELIMITERS, 9, wxTOKEN_RET_EMPTY_ALL },
3883 { _T("01/02/99"), _T("/-"), 3 },
3884 { _T("01-02/99"), _T("/-"), 3, wxTOKEN_RET_DELIMS },
bbf8fc53
VZ
3885 };
3886
3887 for ( size_t n = 0; n < WXSIZEOF(tokenizerTestData); n++ )
3888 {
3889 const StringTokenizerTest& tt = tokenizerTestData[n];
7c968cee 3890 wxStringTokenizer tkz(tt.str, tt.delims, tt.mode);
bbf8fc53
VZ
3891
3892 size_t count = tkz.CountTokens();
7c968cee
VZ
3893 printf(_T("String '%s' has %u tokens delimited by '%s' (mode = %s) "),
3894 MakePrintable(tt.str).c_str(),
bbf8fc53 3895 count,
7c968cee
VZ
3896 MakePrintable(tt.delims).c_str(),
3897 modeNames[tkz.GetMode()]);
bbf8fc53
VZ
3898 if ( count == tt.count )
3899 {
3900 puts(_T("(ok)"));
3901 }
3902 else
3903 {
3904 printf(_T("(ERROR: should be %u)\n"), tt.count);
3905
3906 continue;
3907 }
3908
7c968cee 3909 // if we emulate strtok(), check that we do it correctly
f6bcfd97 3910 wxChar *buf, *s = NULL, *last;
7c968cee
VZ
3911
3912 if ( tkz.GetMode() == wxTOKEN_STRTOK )
3913 {
3914 buf = new wxChar[wxStrlen(tt.str) + 1];
3915 wxStrcpy(buf, tt.str);
3916
3917 s = wxStrtok(buf, tt.delims, &last);
3918 }
3919 else
3920 {
3921 buf = NULL;
3922 }
3923
bbf8fc53
VZ
3924 // now show the tokens themselves
3925 size_t count2 = 0;
3926 while ( tkz.HasMoreTokens() )
3927 {
7c968cee
VZ
3928 wxString token = tkz.GetNextToken();
3929
3930 printf(_T("\ttoken %u: '%s'"),
bbf8fc53 3931 ++count2,
7c968cee
VZ
3932 MakePrintable(token).c_str());
3933
3934 if ( buf )
3935 {
3936 if ( token == s )
3937 {
3938 puts(" (ok)");
3939 }
3940 else
3941 {
3942 printf(" (ERROR: should be %s)\n", s);
3943 }
3944
3945 s = wxStrtok(NULL, tt.delims, &last);
3946 }
3947 else
3948 {
3949 // nothing to compare with
3950 puts("");
3951 }
bbf8fc53
VZ
3952 }
3953
3954 if ( count2 != count )
3955 {
7c968cee 3956 puts(_T("\tERROR: token count mismatch"));
bbf8fc53 3957 }
7c968cee
VZ
3958
3959 delete [] buf;
bbf8fc53
VZ
3960 }
3961
3962 puts("");
3963}
3964
f6bcfd97
BP
3965static void TestStringReplace()
3966{
3967 puts("*** Testing wxString::replace ***");
3968
3969 static const struct StringReplaceTestData
3970 {
3971 const wxChar *original; // original test string
3972 size_t start, len; // the part to replace
3973 const wxChar *replacement; // the replacement string
3974 const wxChar *result; // and the expected result
3975 } stringReplaceTestData[] =
3976 {
3977 { _T("012-AWORD-XYZ"), 4, 5, _T("BWORD"), _T("012-BWORD-XYZ") },
3978 { _T("increase"), 0, 2, _T("de"), _T("decrease") },
3979 { _T("wxWindow"), 8, 0, _T("s"), _T("wxWindows") },
3980 { _T("foobar"), 3, 0, _T("-"), _T("foo-bar") },
3981 { _T("barfoo"), 0, 6, _T("foobar"), _T("foobar") },
3982 };
3983
3984 for ( size_t n = 0; n < WXSIZEOF(stringReplaceTestData); n++ )
3985 {
3986 const StringReplaceTestData data = stringReplaceTestData[n];
3987
3988 wxString original = data.original;
3989 original.replace(data.start, data.len, data.replacement);
3990
3991 wxPrintf(_T("wxString(\"%s\").replace(%u, %u, %s) = %s "),
3992 data.original, data.start, data.len, data.replacement,
3993 original.c_str());
3994
3995 if ( original == data.result )
3996 {
3997 puts("(ok)");
3998 }
3999 else
4000 {
4001 wxPrintf(_T("(ERROR: should be '%s')\n"), data.result);
4002 }
4003 }
4004
4005 puts("");
4006}
4007
9fc3ad34
VZ
4008#endif // TEST_STRINGS
4009
e87271f3
VZ
4010// ----------------------------------------------------------------------------
4011// entry point
4012// ----------------------------------------------------------------------------
4013
bbfa0322 4014int main(int argc, char **argv)
37667812
VZ
4015{
4016 if ( !wxInitialize() )
4017 {
4018 fprintf(stderr, "Failed to initialize the wxWindows library, aborting.");
4019 }
4020
0de868d9
VZ
4021#ifdef TEST_USLEEP
4022 puts("Sleeping for 3 seconds... z-z-z-z-z...");
4023 wxUsleep(3000);
4024#endif // TEST_USLEEP
4025
d34bce84
VZ
4026#ifdef TEST_CMDLINE
4027 static const wxCmdLineEntryDesc cmdLineDesc[] =
4028 {
4029 { wxCMD_LINE_SWITCH, "v", "verbose", "be verbose" },
4030 { wxCMD_LINE_SWITCH, "q", "quiet", "be quiet" },
4031
4032 { wxCMD_LINE_OPTION, "o", "output", "output file" },
4033 { wxCMD_LINE_OPTION, "i", "input", "input dir" },
4034 { wxCMD_LINE_OPTION, "s", "size", "output block size", wxCMD_LINE_VAL_NUMBER },
1e245dc2 4035 { wxCMD_LINE_OPTION, "d", "date", "output file date", wxCMD_LINE_VAL_DATE },
d34bce84
VZ
4036
4037 { wxCMD_LINE_PARAM, NULL, NULL, "input file",
4038 wxCMD_LINE_VAL_STRING, wxCMD_LINE_PARAM_MULTIPLE },
4039
4040 { wxCMD_LINE_NONE }
4041 };
4042
4043 wxCmdLineParser parser(cmdLineDesc, argc, argv);
4044
f6bcfd97
BP
4045 parser.AddOption("project_name", "", "full path to project file",
4046 wxCMD_LINE_VAL_STRING,
4047 wxCMD_LINE_OPTION_MANDATORY | wxCMD_LINE_NEEDS_SEPARATOR);
4048
d34bce84
VZ
4049 switch ( parser.Parse() )
4050 {
4051 case -1:
4052 wxLogMessage("Help was given, terminating.");
4053 break;
4054
4055 case 0:
4056 ShowCmdLine(parser);
4057 break;
4058
4059 default:
4060 wxLogMessage("Syntax error detected, aborting.");
4061 break;
4062 }
4063#endif // TEST_CMDLINE
4064
9fc3ad34 4065#ifdef TEST_STRINGS
299fcbfe
VZ
4066 if ( 0 )
4067 {
4068 TestPChar();
4069 TestString();
4070 }
f6bcfd97 4071 TestStringSub();
f0f951fa
VZ
4072 if ( 0 )
4073 {
7c968cee 4074 TestStringConstruction();
d71fa6fb 4075 TestStringFormat();
bbf8fc53 4076 TestStringFind();
7c968cee 4077 TestStringTokenizer();
f6bcfd97 4078 TestStringReplace();
ee6e1b1d 4079 }
9fc3ad34
VZ
4080#endif // TEST_STRINGS
4081
e87271f3 4082#ifdef TEST_ARRAYS
d6c9c1b7
VZ
4083 if ( 0 )
4084 {
e87271f3
VZ
4085 wxArrayString a1;
4086 a1.Add("tiger");
4087 a1.Add("cat");
4088 a1.Add("lion");
4089 a1.Add("dog");
4090 a1.Add("human");
4091 a1.Add("ape");
4092
4093 puts("*** Initially:");
4094
4095 PrintArray("a1", a1);
4096
4097 wxArrayString a2(a1);
4098 PrintArray("a2", a2);
4099
4100 wxSortedArrayString a3(a1);
4101 PrintArray("a3", a3);
4102
4103 puts("*** After deleting a string from a1");
4104 a1.Remove(2);
4105
4106 PrintArray("a1", a1);
4107 PrintArray("a2", a2);
4108 PrintArray("a3", a3);
4109
4110 puts("*** After reassigning a1 to a2 and a3");
4111 a3 = a2 = a1;
4112 PrintArray("a2", a2);
4113 PrintArray("a3", a3);
f6bcfd97
BP
4114
4115 puts("*** After sorting a1");
4116 a1.Sort();
4117 PrintArray("a1", a1);
4118
4119 puts("*** After sorting a1 in reverse order");
4120 a1.Sort(TRUE);
4121 PrintArray("a1", a1);
4122
4123 puts("*** After sorting a1 by the string length");
4124 a1.Sort(StringLenCompare);
4125 PrintArray("a1", a1);
4126
4127 TestArrayOfObjects();
d6c9c1b7
VZ
4128 }
4129 TestArrayOfInts();
e87271f3
VZ
4130#endif // TEST_ARRAYS
4131
1944c6bd
VZ
4132#ifdef TEST_DIR
4133 TestDirEnum();
4134#endif // TEST_DIR
4135
f6bcfd97
BP
4136#ifdef TEST_DLLLOADER
4137 TestDllLoad();
4138#endif // TEST_DLLLOADER
4139
8fd0d89b
VZ
4140#ifdef TEST_ENVIRON
4141 TestEnvironment();
4142#endif // TEST_ENVIRON
4143
d93c719a
VZ
4144#ifdef TEST_EXECUTE
4145 TestExecute();
4146#endif // TEST_EXECUTE
4147
ee6e1b1d
VZ
4148#ifdef TEST_FILECONF
4149 TestFileConfRead();
4150#endif // TEST_FILECONF
4151
f6bcfd97
BP
4152#ifdef TEST_LIST
4153 TestListCtor();
4154#endif // TEST_LIST
4155
378b05f7
VZ
4156#ifdef TEST_LOG
4157 wxString s;
4158 for ( size_t n = 0; n < 8000; n++ )
4159 {
4160 s << (char)('A' + (n % 26));
4161 }
4162
4163 wxString msg;
4164 msg.Printf("A very very long message: '%s', the end!\n", s.c_str());
4165
4166 // this one shouldn't be truncated
4167 printf(msg);
4168
4169 // but this one will because log functions use fixed size buffer
b568d04f
VZ
4170 // (note that it doesn't need '\n' at the end neither - will be added
4171 // by wxLog anyhow)
4172 wxLogMessage("A very very long message 2: '%s', the end!", s.c_str());
378b05f7
VZ
4173#endif // TEST_LOG
4174
f6bcfd97 4175#ifdef TEST_FILE
3ca6a5f0 4176 if ( 0 )
a339970a 4177 {
3ca6a5f0 4178 TestFileRead();
a339970a
VZ
4179 TestTextFileRead();
4180 }
4181 TestFileCopy();
f6bcfd97
BP
4182#endif // TEST_FILE
4183
844f90fb 4184#ifdef TEST_FILENAME
42b1f941 4185 TestFileNameSplit();
9e8d8607
VZ
4186 if ( 0 )
4187 {
42b1f941 4188 TestFileNameConstruction();
9e8d8607
VZ
4189 TestFileNameCwd();
4190 TestFileNameComparison();
4191 TestFileNameOperations();
4192 }
844f90fb
VZ
4193#endif // TEST_FILENAME
4194
e87271f3 4195#ifdef TEST_THREADS
696e1ea0
VZ
4196 int nCPUs = wxThread::GetCPUCount();
4197 printf("This system has %d CPUs\n", nCPUs);
4198 if ( nCPUs != -1 )
4199 wxThread::SetConcurrency(nCPUs);
ef8d96c2 4200
9fc3ad34
VZ
4201 if ( argc > 1 && argv[1][0] == 't' )
4202 wxLog::AddTraceMask("thread");
b568d04f 4203
4c460b34 4204 if ( 1 )
2f02cb89 4205 TestDetachedThreads();
4c460b34 4206 if ( 1 )
2f02cb89 4207 TestJoinableThreads();
4c460b34 4208 if ( 1 )
2f02cb89
VZ
4209 TestThreadSuspend();
4210 if ( 1 )
4211 TestThreadDelete();
4212
e87271f3 4213#endif // TEST_THREADS
37667812 4214
b76b015e 4215#ifdef TEST_LONGLONG
2a310492
VZ
4216 // seed pseudo random generator
4217 srand((unsigned)time(NULL));
4218
b76b015e 4219 if ( 0 )
2a310492 4220 {
b76b015e 4221 TestSpeed();
2a310492 4222 }
2a310492
VZ
4223 if ( 0 )
4224 {
f6bcfd97 4225 TestMultiplication();
b76b015e 4226 TestDivision();
2a310492
VZ
4227 TestAddition();
4228 TestLongLongConversion();
4229 TestBitOperations();
4230 }
f6bcfd97 4231 TestLongLongComparison();
b76b015e
VZ
4232#endif // TEST_LONGLONG
4233
2c8e4738
VZ
4234#ifdef TEST_HASH
4235 TestHash();
4236#endif // TEST_HASH
4237
696e1ea0 4238#ifdef TEST_MIME
f6bcfd97 4239 wxLog::AddTraceMask(_T("mime"));
a6c65e88 4240 if ( 1 )
c7ce8392 4241 {
f6bcfd97 4242 TestMimeEnum();
c7ce8392
VZ
4243 TestMimeOverride();
4244 TestMimeFilename();
4245 }
a6c65e88
VZ
4246 else
4247 TestMimeAssociate();
696e1ea0
VZ
4248#endif // TEST_MIME
4249
89e60357
VZ
4250#ifdef TEST_INFO_FUNCTIONS
4251 TestOsInfo();
4252 TestUserInfo();
4253#endif // TEST_INFO_FUNCTIONS
4254
6dfec4b8 4255#ifdef TEST_REGISTRY
6ba63600
VZ
4256 if ( 0 )
4257 TestRegistryRead();
4258 TestRegistryAssociation();
6dfec4b8
VZ
4259#endif // TEST_REGISTRY
4260
2c8e4738 4261#ifdef TEST_SOCKETS
ccdb23df 4262 if ( 0 )
8e907a13 4263 {
f6bcfd97 4264 TestSocketServer();
8dfea369 4265 }
2e907fab 4266 TestSocketClient();
2c8e4738
VZ
4267#endif // TEST_SOCKETS
4268
2e907fab 4269#ifdef TEST_FTP
b92fd37c
VZ
4270 wxLog::AddTraceMask(FTP_TRACE_MASK);
4271 if ( TestFtpConnect() )
4272 {
4273 TestFtpFileSize();
4274 if ( 0 )
4275 {
4276 TestFtpList();
4277 TestFtpDownload();
4278 TestFtpMisc();
4279 TestFtpUpload();
4280 }
4281 if ( 0 )
4282 TestFtpInteractive();
4283 }
4284 //else: connecting to the FTP server failed
4285
2e907fab 4286 if ( 0 )
b92fd37c 4287 TestFtpWuFtpd();
2e907fab
VZ
4288#endif // TEST_FTP
4289
83141d3a 4290#ifdef TEST_STREAMS
24f25c8a
VZ
4291 if ( 0 )
4292 TestFileStream();
83141d3a
VZ
4293 TestMemoryStream();
4294#endif // TEST_STREAMS
4295
d31b7b68
VZ
4296#ifdef TEST_TIMER
4297 TestStopWatch();
4298#endif // TEST_TIMER
4299
4300#ifdef TEST_DATETIME
384223b3 4301 if ( 1 )
299fcbfe 4302 {
9d9b7755
VZ
4303 TestTimeSet();
4304 TestTimeStatic();
4305 TestTimeRange();
4306 TestTimeZones();
4307 TestTimeTicks();
4308 TestTimeJDN();
4309 TestTimeDST();
4310 TestTimeWDays();
4311 TestTimeWNumber();
4312 TestTimeParse();
9d9b7755 4313 TestTimeArithmetics();
f6bcfd97
BP
4314 TestTimeHolidays();
4315 TestTimeFormat();
3ca6a5f0 4316 TestTimeMS();
f6bcfd97
BP
4317
4318 TestTimeZoneBug();
41acf5c0 4319 }
9d9b7755 4320 if ( 0 )
b92fd37c 4321 TestDateTimeInteractive();
d31b7b68 4322#endif // TEST_DATETIME
b76b015e 4323
f6bcfd97
BP
4324#ifdef TEST_VCARD
4325 if ( 0 )
4326 TestVCardRead();
4327 TestVCardWrite();
4328#endif // TEST_VCARD
4329
4330#ifdef TEST_WCHAR
4331 TestUtf8();
4332#endif // TEST_WCHAR
4333
4334#ifdef TEST_ZIP
4335 TestZipStreamRead();
4336#endif // TEST_ZIP
4337
3ca6a5f0
BP
4338#ifdef TEST_ZLIB
4339 if ( 0 )
4340 TestZlibStreamWrite();
4341 TestZlibStreamRead();
4342#endif // TEST_ZLIB
4343
37667812
VZ
4344 wxUninitialize();
4345
4346 return 0;
4347}
f6bcfd97 4348