warning fix
[wxWidgets.git] / samples / console / console.cpp
1 /////////////////////////////////////////////////////////////////////////////
2 // Name: samples/console/console.cpp
3 // Purpose: A sample console (as opposed to GUI) program using wxWidgets
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
12 // ============================================================================
13 // declarations
14 // ============================================================================
15
16 // ----------------------------------------------------------------------------
17 // headers
18 // ----------------------------------------------------------------------------
19
20 #include "wx/defs.h"
21
22 #include <stdio.h>
23
24 #include "wx/string.h"
25 #include "wx/file.h"
26 #include "wx/app.h"
27 #include "wx/log.h"
28 #include "wx/apptrait.h"
29 #include "wx/platinfo.h"
30
31 // without this pragma, the stupid compiler precompiles #defines below so that
32 // changing them doesn't "take place" later!
33 #ifdef __VISUALC__
34 #pragma hdrstop
35 #endif
36
37 // ----------------------------------------------------------------------------
38 // conditional compilation
39 // ----------------------------------------------------------------------------
40
41 /*
42 A note about all these conditional compilation macros: this file is used
43 both as a test suite for various non-GUI wxWidgets classes and as a
44 scratchpad for quick tests. So there are two compilation modes: if you
45 define TEST_ALL all tests are run, otherwise you may enable the individual
46 tests individually in the "#else" branch below.
47 */
48
49 // what to test (in alphabetic order)? Define TEST_ALL to 0 to do a single
50 // test, define it to 1 to do all tests.
51 #define TEST_ALL 0
52
53
54 #if TEST_ALL
55 #define TEST_CMDLINE
56 #define TEST_DATETIME
57 #define TEST_DIR
58 #define TEST_DYNLIB
59 #define TEST_ENVIRON
60 #define TEST_EXECUTE
61 #define TEST_FILE
62 #define TEST_FILECONF
63 #define TEST_FILENAME
64 #define TEST_FILETIME
65 // #define TEST_FTP --FIXME! (RN)
66 #define TEST_INFO_FUNCTIONS
67 #define TEST_LOCALE
68 #define TEST_LOG
69 #define TEST_MIME
70 #define TEST_MODULE
71 #define TEST_PATHLIST
72 #define TEST_ODBC
73 #define TEST_PRINTF
74 #define TEST_REGCONF
75 #define TEST_REGEX
76 #define TEST_REGISTRY
77 #define TEST_SCOPEGUARD
78 #define TEST_SNGLINST
79 // #define TEST_SOCKETS --FIXME! (RN)
80 #define TEST_STACKWALKER
81 #define TEST_STDPATHS
82 #define TEST_STREAMS
83 #define TEST_TEXTSTREAM
84 #define TEST_THREADS
85 #define TEST_TIMER
86 // #define TEST_VCARD -- don't enable this (VZ)
87 // #define TEST_VOLUME --FIXME! (RN)
88 #define TEST_WCHAR
89 #define TEST_ZIP
90 #else // #if TEST_ALL
91 #define TEST_INFO_FUNCTIONS
92 #endif
93
94 // some tests are interactive, define this to run them
95 #ifdef TEST_INTERACTIVE
96 #undef TEST_INTERACTIVE
97
98 #define TEST_INTERACTIVE 1
99 #else
100 #define TEST_INTERACTIVE 0
101 #endif
102
103 // ============================================================================
104 // implementation
105 // ============================================================================
106
107 // ----------------------------------------------------------------------------
108 // helper functions
109 // ----------------------------------------------------------------------------
110
111 #if defined(TEST_SOCKETS)
112
113 // replace TABs with \t and CRs with \n
114 static wxString MakePrintable(const wxChar *s)
115 {
116 wxString str(s);
117 (void)str.Replace(_T("\t"), _T("\\t"));
118 (void)str.Replace(_T("\n"), _T("\\n"));
119 (void)str.Replace(_T("\r"), _T("\\r"));
120
121 return str;
122 }
123
124 #endif // MakePrintable() is used
125
126 // ----------------------------------------------------------------------------
127 // wxCmdLineParser
128 // ----------------------------------------------------------------------------
129
130 #ifdef TEST_CMDLINE
131
132 #include "wx/cmdline.h"
133 #include "wx/datetime.h"
134
135 #if wxUSE_CMDLINE_PARSER
136
137 static void ShowCmdLine(const wxCmdLineParser& parser)
138 {
139 wxString s = _T("Input files: ");
140
141 size_t count = parser.GetParamCount();
142 for ( size_t param = 0; param < count; param++ )
143 {
144 s << parser.GetParam(param) << ' ';
145 }
146
147 s << '\n'
148 << _T("Verbose:\t") << (parser.Found(_T("v")) ? _T("yes") : _T("no")) << '\n'
149 << _T("Quiet:\t") << (parser.Found(_T("q")) ? _T("yes") : _T("no")) << '\n';
150
151 wxString strVal;
152 long lVal;
153 wxDateTime dt;
154 if ( parser.Found(_T("o"), &strVal) )
155 s << _T("Output file:\t") << strVal << '\n';
156 if ( parser.Found(_T("i"), &strVal) )
157 s << _T("Input dir:\t") << strVal << '\n';
158 if ( parser.Found(_T("s"), &lVal) )
159 s << _T("Size:\t") << lVal << '\n';
160 if ( parser.Found(_T("d"), &dt) )
161 s << _T("Date:\t") << dt.FormatISODate() << '\n';
162 if ( parser.Found(_T("project_name"), &strVal) )
163 s << _T("Project:\t") << strVal << '\n';
164
165 wxLogMessage(s);
166 }
167
168 #endif // wxUSE_CMDLINE_PARSER
169
170 static void TestCmdLineConvert()
171 {
172 static const wxChar *cmdlines[] =
173 {
174 _T("arg1 arg2"),
175 _T("-a \"-bstring 1\" -c\"string 2\" \"string 3\""),
176 _T("literal \\\" and \"\""),
177 };
178
179 for ( size_t n = 0; n < WXSIZEOF(cmdlines); n++ )
180 {
181 const wxChar *cmdline = cmdlines[n];
182 wxPrintf(_T("Parsing: %s\n"), cmdline);
183 wxArrayString args = wxCmdLineParser::ConvertStringToArgs(cmdline);
184
185 size_t count = args.GetCount();
186 wxPrintf(_T("\targc = %u\n"), count);
187 for ( size_t arg = 0; arg < count; arg++ )
188 {
189 wxPrintf(_T("\targv[%u] = %s\n"), arg, args[arg].c_str());
190 }
191 }
192 }
193
194 #endif // TEST_CMDLINE
195
196 // ----------------------------------------------------------------------------
197 // wxDir
198 // ----------------------------------------------------------------------------
199
200 #ifdef TEST_DIR
201
202 #include "wx/dir.h"
203
204 #ifdef __UNIX__
205 static const wxChar *ROOTDIR = _T("/");
206 static const wxChar *TESTDIR = _T("/usr/local/share");
207 #elif defined(__WXMSW__) || defined(__DOS__) || defined(__OS2__)
208 static const wxChar *ROOTDIR = _T("c:\\");
209 static const wxChar *TESTDIR = _T("d:\\");
210 #else
211 #error "don't know where the root directory is"
212 #endif
213
214 static void TestDirEnumHelper(wxDir& dir,
215 int flags = wxDIR_DEFAULT,
216 const wxString& filespec = wxEmptyString)
217 {
218 wxString filename;
219
220 if ( !dir.IsOpened() )
221 return;
222
223 bool cont = dir.GetFirst(&filename, filespec, flags);
224 while ( cont )
225 {
226 wxPrintf(_T("\t%s\n"), filename.c_str());
227
228 cont = dir.GetNext(&filename);
229 }
230
231 wxPuts(wxEmptyString);
232 }
233
234 #if TEST_ALL
235
236 static void TestDirEnum()
237 {
238 wxPuts(_T("*** Testing wxDir::GetFirst/GetNext ***"));
239
240 wxString cwd = wxGetCwd();
241 if ( !wxDir::Exists(cwd) )
242 {
243 wxPrintf(_T("ERROR: current directory '%s' doesn't exist?\n"), cwd.c_str());
244 return;
245 }
246
247 wxDir dir(cwd);
248 if ( !dir.IsOpened() )
249 {
250 wxPrintf(_T("ERROR: failed to open current directory '%s'.\n"), cwd.c_str());
251 return;
252 }
253
254 wxPuts(_T("Enumerating everything in current directory:"));
255 TestDirEnumHelper(dir);
256
257 wxPuts(_T("Enumerating really everything in current directory:"));
258 TestDirEnumHelper(dir, wxDIR_DEFAULT | wxDIR_DOTDOT);
259
260 wxPuts(_T("Enumerating object files in current directory:"));
261 TestDirEnumHelper(dir, wxDIR_DEFAULT, _T("*.o*"));
262
263 wxPuts(_T("Enumerating directories in current directory:"));
264 TestDirEnumHelper(dir, wxDIR_DIRS);
265
266 wxPuts(_T("Enumerating files in current directory:"));
267 TestDirEnumHelper(dir, wxDIR_FILES);
268
269 wxPuts(_T("Enumerating files including hidden in current directory:"));
270 TestDirEnumHelper(dir, wxDIR_FILES | wxDIR_HIDDEN);
271
272 dir.Open(ROOTDIR);
273
274 wxPuts(_T("Enumerating everything in root directory:"));
275 TestDirEnumHelper(dir, wxDIR_DEFAULT);
276
277 wxPuts(_T("Enumerating directories in root directory:"));
278 TestDirEnumHelper(dir, wxDIR_DIRS);
279
280 wxPuts(_T("Enumerating files in root directory:"));
281 TestDirEnumHelper(dir, wxDIR_FILES);
282
283 wxPuts(_T("Enumerating files including hidden in root directory:"));
284 TestDirEnumHelper(dir, wxDIR_FILES | wxDIR_HIDDEN);
285
286 wxPuts(_T("Enumerating files in non existing directory:"));
287 wxDir dirNo(_T("nosuchdir"));
288 TestDirEnumHelper(dirNo);
289 }
290
291 #endif // TEST_ALL
292
293 class DirPrintTraverser : public wxDirTraverser
294 {
295 public:
296 virtual wxDirTraverseResult OnFile(const wxString& WXUNUSED(filename))
297 {
298 return wxDIR_CONTINUE;
299 }
300
301 virtual wxDirTraverseResult OnDir(const wxString& dirname)
302 {
303 wxString path, name, ext;
304 wxSplitPath(dirname, &path, &name, &ext);
305
306 if ( !ext.empty() )
307 name << _T('.') << ext;
308
309 wxString indent;
310 for ( const wxChar *p = path.c_str(); *p; p++ )
311 {
312 if ( wxIsPathSeparator(*p) )
313 indent += _T(" ");
314 }
315
316 wxPrintf(_T("%s%s\n"), indent.c_str(), name.c_str());
317
318 return wxDIR_CONTINUE;
319 }
320 };
321
322 static void TestDirTraverse()
323 {
324 wxPuts(_T("*** Testing wxDir::Traverse() ***"));
325
326 // enum all files
327 wxArrayString files;
328 size_t n = wxDir::GetAllFiles(TESTDIR, &files);
329 wxPrintf(_T("There are %u files under '%s'\n"), n, TESTDIR);
330 if ( n > 1 )
331 {
332 wxPrintf(_T("First one is '%s'\n"), files[0u].c_str());
333 wxPrintf(_T(" last one is '%s'\n"), files[n - 1].c_str());
334 }
335
336 // enum again with custom traverser
337 wxPuts(_T("Now enumerating directories:"));
338 wxDir dir(TESTDIR);
339 DirPrintTraverser traverser;
340 dir.Traverse(traverser, wxEmptyString, wxDIR_DIRS | wxDIR_HIDDEN);
341 }
342
343 #if TEST_ALL
344
345 static void TestDirExists()
346 {
347 wxPuts(_T("*** Testing wxDir::Exists() ***"));
348
349 static const wxChar *dirnames[] =
350 {
351 _T("."),
352 #if defined(__WXMSW__)
353 _T("c:"),
354 _T("c:\\"),
355 _T("\\\\share\\file"),
356 _T("c:\\dos"),
357 _T("c:\\dos\\"),
358 _T("c:\\dos\\\\"),
359 _T("c:\\autoexec.bat"),
360 #elif defined(__UNIX__)
361 _T("/"),
362 _T("//"),
363 _T("/usr/bin"),
364 _T("/usr//bin"),
365 _T("/usr///bin"),
366 #endif
367 };
368
369 for ( size_t n = 0; n < WXSIZEOF(dirnames); n++ )
370 {
371 wxPrintf(_T("%-40s: %s\n"),
372 dirnames[n],
373 wxDir::Exists(dirnames[n]) ? _T("exists")
374 : _T("doesn't exist"));
375 }
376 }
377
378 #endif // TEST_ALL
379
380 #endif // TEST_DIR
381
382 // ----------------------------------------------------------------------------
383 // wxDllLoader
384 // ----------------------------------------------------------------------------
385
386 #ifdef TEST_DYNLIB
387
388 #include "wx/dynlib.h"
389
390 static void TestDllLoad()
391 {
392 #if defined(__WXMSW__)
393 static const wxChar *LIB_NAME = _T("kernel32.dll");
394 static const wxChar *FUNC_NAME = _T("lstrlenA");
395 #elif defined(__UNIX__)
396 // weird: using just libc.so does *not* work!
397 static const wxChar *LIB_NAME = _T("/lib/libc.so.6");
398 static const wxChar *FUNC_NAME = _T("strlen");
399 #else
400 #error "don't know how to test wxDllLoader on this platform"
401 #endif
402
403 wxPuts(_T("*** testing basic wxDynamicLibrary functions ***\n"));
404
405 wxDynamicLibrary lib(LIB_NAME);
406 if ( !lib.IsLoaded() )
407 {
408 wxPrintf(_T("ERROR: failed to load '%s'.\n"), LIB_NAME);
409 }
410 else
411 {
412 typedef int (wxSTDCALL *wxStrlenType)(const char *);
413 wxStrlenType pfnStrlen = (wxStrlenType)lib.GetSymbol(FUNC_NAME);
414 if ( !pfnStrlen )
415 {
416 wxPrintf(_T("ERROR: function '%s' wasn't found in '%s'.\n"),
417 FUNC_NAME, LIB_NAME);
418 }
419 else
420 {
421 wxPrintf(_T("Calling %s dynamically loaded from %s "),
422 FUNC_NAME, LIB_NAME);
423
424 if ( pfnStrlen("foo") != 3 )
425 {
426 wxPrintf(_T("ERROR: loaded function is not wxStrlen()!\n"));
427 }
428 else
429 {
430 wxPuts(_T("... ok"));
431 }
432 }
433
434 #ifdef __WXMSW__
435 static const wxChar *FUNC_NAME_AW = _T("lstrlen");
436
437 typedef int (wxSTDCALL *wxStrlenTypeAorW)(const wxChar *);
438 wxStrlenTypeAorW
439 pfnStrlenAorW = (wxStrlenTypeAorW)lib.GetSymbolAorW(FUNC_NAME_AW);
440 if ( !pfnStrlenAorW )
441 {
442 wxPrintf(_T("ERROR: function '%s' wasn't found in '%s'.\n"),
443 FUNC_NAME_AW, LIB_NAME);
444 }
445 else
446 {
447 if ( pfnStrlenAorW(_T("foobar")) != 6 )
448 {
449 wxPrintf(_T("ERROR: loaded function is not wxStrlen()!\n"));
450 }
451 }
452 #endif // __WXMSW__
453 }
454 }
455
456 #if defined(__WXMSW__) || defined(__UNIX__)
457
458 static void TestDllListLoaded()
459 {
460 wxPuts(_T("*** testing wxDynamicLibrary::ListLoaded() ***\n"));
461
462 puts("\nLoaded modules:");
463 wxDynamicLibraryDetailsArray dlls = wxDynamicLibrary::ListLoaded();
464 const size_t count = dlls.GetCount();
465 for ( size_t n = 0; n < count; ++n )
466 {
467 const wxDynamicLibraryDetails& details = dlls[n];
468 printf("%-45s", details.GetPath().mb_str());
469
470 void *addr;
471 size_t len;
472 if ( details.GetAddress(&addr, &len) )
473 {
474 printf(" %08lx:%08lx",
475 (unsigned long)addr, (unsigned long)((char *)addr + len));
476 }
477
478 printf(" %s\n", details.GetVersion().mb_str());
479 }
480 }
481
482 #endif
483
484 #endif // TEST_DYNLIB
485
486 // ----------------------------------------------------------------------------
487 // wxGet/SetEnv
488 // ----------------------------------------------------------------------------
489
490 #ifdef TEST_ENVIRON
491
492 #include "wx/utils.h"
493
494 static wxString MyGetEnv(const wxString& var)
495 {
496 wxString val;
497 if ( !wxGetEnv(var, &val) )
498 val = _T("<empty>");
499 else
500 val = wxString(_T('\'')) + val + _T('\'');
501
502 return val;
503 }
504
505 static void TestEnvironment()
506 {
507 const wxChar *var = _T("wxTestVar");
508
509 wxPuts(_T("*** testing environment access functions ***"));
510
511 wxPrintf(_T("Initially getenv(%s) = %s\n"), var, MyGetEnv(var).c_str());
512 wxSetEnv(var, _T("value for wxTestVar"));
513 wxPrintf(_T("After wxSetEnv: getenv(%s) = %s\n"), var, MyGetEnv(var).c_str());
514 wxSetEnv(var, _T("another value"));
515 wxPrintf(_T("After 2nd wxSetEnv: getenv(%s) = %s\n"), var, MyGetEnv(var).c_str());
516 wxUnsetEnv(var);
517 wxPrintf(_T("After wxUnsetEnv: getenv(%s) = %s\n"), var, MyGetEnv(var).c_str());
518 wxPrintf(_T("PATH = %s\n"), MyGetEnv(_T("PATH")).c_str());
519 }
520
521 #endif // TEST_ENVIRON
522
523 // ----------------------------------------------------------------------------
524 // wxExecute
525 // ----------------------------------------------------------------------------
526
527 #ifdef TEST_EXECUTE
528
529 #include "wx/utils.h"
530
531 static void TestExecute()
532 {
533 wxPuts(_T("*** testing wxExecute ***"));
534
535 #ifdef __UNIX__
536 #define COMMAND "cat -n ../../Makefile" // "echo hi"
537 #define SHELL_COMMAND "echo hi from shell"
538 #define REDIRECT_COMMAND COMMAND // "date"
539 #elif defined(__WXMSW__)
540 #define COMMAND "command.com /c echo hi"
541 #define SHELL_COMMAND "echo hi"
542 #define REDIRECT_COMMAND COMMAND
543 #else
544 #error "no command to exec"
545 #endif // OS
546
547 wxPrintf(_T("Testing wxShell: "));
548 fflush(stdout);
549 if ( wxShell(_T(SHELL_COMMAND)) )
550 wxPuts(_T("Ok."));
551 else
552 wxPuts(_T("ERROR."));
553
554 wxPrintf(_T("Testing wxExecute: "));
555 fflush(stdout);
556 if ( wxExecute(_T(COMMAND), true /* sync */) == 0 )
557 wxPuts(_T("Ok."));
558 else
559 wxPuts(_T("ERROR."));
560
561 #if 0 // no, it doesn't work (yet?)
562 wxPrintf(_T("Testing async wxExecute: "));
563 fflush(stdout);
564 if ( wxExecute(COMMAND) != 0 )
565 wxPuts(_T("Ok (command launched)."));
566 else
567 wxPuts(_T("ERROR."));
568 #endif // 0
569
570 wxPrintf(_T("Testing wxExecute with redirection:\n"));
571 wxArrayString output;
572 if ( wxExecute(_T(REDIRECT_COMMAND), output) != 0 )
573 {
574 wxPuts(_T("ERROR."));
575 }
576 else
577 {
578 size_t count = output.GetCount();
579 for ( size_t n = 0; n < count; n++ )
580 {
581 wxPrintf(_T("\t%s\n"), output[n].c_str());
582 }
583
584 wxPuts(_T("Ok."));
585 }
586 }
587
588 #endif // TEST_EXECUTE
589
590 // ----------------------------------------------------------------------------
591 // file
592 // ----------------------------------------------------------------------------
593
594 #ifdef TEST_FILE
595
596 #include "wx/file.h"
597 #include "wx/ffile.h"
598 #include "wx/textfile.h"
599
600 static void TestFileRead()
601 {
602 wxPuts(_T("*** wxFile read test ***"));
603
604 wxFile file(_T("testdata.fc"));
605 if ( file.IsOpened() )
606 {
607 wxPrintf(_T("File length: %lu\n"), file.Length());
608
609 wxPuts(_T("File dump:\n----------"));
610
611 static const size_t len = 1024;
612 wxChar buf[len];
613 for ( ;; )
614 {
615 size_t nRead = file.Read(buf, len);
616 if ( nRead == (size_t)wxInvalidOffset )
617 {
618 wxPrintf(_T("Failed to read the file."));
619 break;
620 }
621
622 fwrite(buf, nRead, 1, stdout);
623
624 if ( nRead < len )
625 break;
626 }
627
628 wxPuts(_T("----------"));
629 }
630 else
631 {
632 wxPrintf(_T("ERROR: can't open test file.\n"));
633 }
634
635 wxPuts(wxEmptyString);
636 }
637
638 static void TestTextFileRead()
639 {
640 wxPuts(_T("*** wxTextFile read test ***"));
641
642 wxTextFile file(_T("testdata.fc"));
643 if ( file.Open() )
644 {
645 wxPrintf(_T("Number of lines: %u\n"), file.GetLineCount());
646 wxPrintf(_T("Last line: '%s'\n"), file.GetLastLine().c_str());
647
648 wxString s;
649
650 wxPuts(_T("\nDumping the entire file:"));
651 for ( s = file.GetFirstLine(); !file.Eof(); s = file.GetNextLine() )
652 {
653 wxPrintf(_T("%6u: %s\n"), file.GetCurrentLine() + 1, s.c_str());
654 }
655 wxPrintf(_T("%6u: %s\n"), file.GetCurrentLine() + 1, s.c_str());
656
657 wxPuts(_T("\nAnd now backwards:"));
658 for ( s = file.GetLastLine();
659 file.GetCurrentLine() != 0;
660 s = file.GetPrevLine() )
661 {
662 wxPrintf(_T("%6u: %s\n"), file.GetCurrentLine() + 1, s.c_str());
663 }
664 wxPrintf(_T("%6u: %s\n"), file.GetCurrentLine() + 1, s.c_str());
665 }
666 else
667 {
668 wxPrintf(_T("ERROR: can't open '%s'\n"), file.GetName());
669 }
670
671 wxPuts(wxEmptyString);
672 }
673
674 static void TestFileCopy()
675 {
676 wxPuts(_T("*** Testing wxCopyFile ***"));
677
678 static const wxChar *filename1 = _T("testdata.fc");
679 static const wxChar *filename2 = _T("test2");
680 if ( !wxCopyFile(filename1, filename2) )
681 {
682 wxPuts(_T("ERROR: failed to copy file"));
683 }
684 else
685 {
686 wxFFile f1(filename1, _T("rb")),
687 f2(filename2, _T("rb"));
688
689 if ( !f1.IsOpened() || !f2.IsOpened() )
690 {
691 wxPuts(_T("ERROR: failed to open file(s)"));
692 }
693 else
694 {
695 wxString s1, s2;
696 if ( !f1.ReadAll(&s1) || !f2.ReadAll(&s2) )
697 {
698 wxPuts(_T("ERROR: failed to read file(s)"));
699 }
700 else
701 {
702 if ( (s1.length() != s2.length()) ||
703 (memcmp(s1.c_str(), s2.c_str(), s1.length()) != 0) )
704 {
705 wxPuts(_T("ERROR: copy error!"));
706 }
707 else
708 {
709 wxPuts(_T("File was copied ok."));
710 }
711 }
712 }
713 }
714
715 if ( !wxRemoveFile(filename2) )
716 {
717 wxPuts(_T("ERROR: failed to remove the file"));
718 }
719
720 wxPuts(wxEmptyString);
721 }
722
723 #endif // TEST_FILE
724
725 // ----------------------------------------------------------------------------
726 // wxFileConfig
727 // ----------------------------------------------------------------------------
728
729 #ifdef TEST_FILECONF
730
731 #include "wx/confbase.h"
732 #include "wx/fileconf.h"
733
734 static const struct FileConfTestData
735 {
736 const wxChar *name; // value name
737 const wxChar *value; // the value from the file
738 } fcTestData[] =
739 {
740 { _T("value1"), _T("one") },
741 { _T("value2"), _T("two") },
742 { _T("novalue"), _T("default") },
743 };
744
745 static void TestFileConfRead()
746 {
747 wxPuts(_T("*** testing wxFileConfig loading/reading ***"));
748
749 wxFileConfig fileconf(_T("test"), wxEmptyString,
750 _T("testdata.fc"), wxEmptyString,
751 wxCONFIG_USE_RELATIVE_PATH);
752
753 // test simple reading
754 wxPuts(_T("\nReading config file:"));
755 wxString defValue(_T("default")), value;
756 for ( size_t n = 0; n < WXSIZEOF(fcTestData); n++ )
757 {
758 const FileConfTestData& data = fcTestData[n];
759 value = fileconf.Read(data.name, defValue);
760 wxPrintf(_T("\t%s = %s "), data.name, value.c_str());
761 if ( value == data.value )
762 {
763 wxPuts(_T("(ok)"));
764 }
765 else
766 {
767 wxPrintf(_T("(ERROR: should be %s)\n"), data.value);
768 }
769 }
770
771 // test enumerating the entries
772 wxPuts(_T("\nEnumerating all root entries:"));
773 long dummy;
774 wxString name;
775 bool cont = fileconf.GetFirstEntry(name, dummy);
776 while ( cont )
777 {
778 wxPrintf(_T("\t%s = %s\n"),
779 name.c_str(),
780 fileconf.Read(name.c_str(), _T("ERROR")).c_str());
781
782 cont = fileconf.GetNextEntry(name, dummy);
783 }
784
785 static const wxChar *testEntry = _T("TestEntry");
786 wxPrintf(_T("\nTesting deletion of newly created \"Test\" entry: "));
787 fileconf.Write(testEntry, _T("A value"));
788 fileconf.DeleteEntry(testEntry);
789 wxPrintf(fileconf.HasEntry(testEntry) ? _T("ERROR\n") : _T("ok\n"));
790 }
791
792 #endif // TEST_FILECONF
793
794 // ----------------------------------------------------------------------------
795 // wxFileName
796 // ----------------------------------------------------------------------------
797
798 #ifdef TEST_FILENAME
799
800 #include "wx/filename.h"
801
802 #if 0
803 static void DumpFileName(const wxChar *desc, const wxFileName& fn)
804 {
805 wxPuts(desc);
806
807 wxString full = fn.GetFullPath();
808
809 wxString vol, path, name, ext;
810 wxFileName::SplitPath(full, &vol, &path, &name, &ext);
811
812 wxPrintf(_T("'%s'-> vol '%s', path '%s', name '%s', ext '%s'\n"),
813 full.c_str(), vol.c_str(), path.c_str(), name.c_str(), ext.c_str());
814
815 wxFileName::SplitPath(full, &path, &name, &ext);
816 wxPrintf(_T("or\t\t-> path '%s', name '%s', ext '%s'\n"),
817 path.c_str(), name.c_str(), ext.c_str());
818
819 wxPrintf(_T("path is also:\t'%s'\n"), fn.GetPath().c_str());
820 wxPrintf(_T("with volume: \t'%s'\n"),
821 fn.GetPath(wxPATH_GET_VOLUME).c_str());
822 wxPrintf(_T("with separator:\t'%s'\n"),
823 fn.GetPath(wxPATH_GET_SEPARATOR).c_str());
824 wxPrintf(_T("with both: \t'%s'\n"),
825 fn.GetPath(wxPATH_GET_SEPARATOR | wxPATH_GET_VOLUME).c_str());
826
827 wxPuts(_T("The directories in the path are:"));
828 wxArrayString dirs = fn.GetDirs();
829 size_t count = dirs.GetCount();
830 for ( size_t n = 0; n < count; n++ )
831 {
832 wxPrintf(_T("\t%u: %s\n"), n, dirs[n].c_str());
833 }
834 }
835 #endif
836
837 static void TestFileNameTemp()
838 {
839 wxPuts(_T("*** testing wxFileName temp file creation ***"));
840
841 static const wxChar *tmpprefixes[] =
842 {
843 _T(""),
844 _T("foo"),
845 _T(".."),
846 _T("../bar"),
847 #ifdef __UNIX__
848 _T("/tmp/foo"),
849 _T("/tmp/foo/bar"), // this one must be an error
850 #endif // __UNIX__
851 };
852
853 for ( size_t n = 0; n < WXSIZEOF(tmpprefixes); n++ )
854 {
855 wxString path = wxFileName::CreateTempFileName(tmpprefixes[n]);
856 if ( path.empty() )
857 {
858 // "error" is not in upper case because it may be ok
859 wxPrintf(_T("Prefix '%s'\t-> error\n"), tmpprefixes[n]);
860 }
861 else
862 {
863 wxPrintf(_T("Prefix '%s'\t-> temp file '%s'\n"),
864 tmpprefixes[n], path.c_str());
865
866 if ( !wxRemoveFile(path) )
867 {
868 wxLogWarning(_T("Failed to remove temp file '%s'"),
869 path.c_str());
870 }
871 }
872 }
873 }
874
875 static void TestFileNameDirManip()
876 {
877 // TODO: test AppendDir(), RemoveDir(), ...
878 }
879
880 static void TestFileNameComparison()
881 {
882 // TODO!
883 }
884
885 static void TestFileNameOperations()
886 {
887 // TODO!
888 }
889
890 static void TestFileNameCwd()
891 {
892 // TODO!
893 }
894
895 #endif // TEST_FILENAME
896
897 // ----------------------------------------------------------------------------
898 // wxFileName time functions
899 // ----------------------------------------------------------------------------
900
901 #ifdef TEST_FILETIME
902
903 #include "wx/filename.h"
904 #include "wx/datetime.h"
905
906 static void TestFileGetTimes()
907 {
908 wxFileName fn(_T("testdata.fc"));
909
910 wxDateTime dtAccess, dtMod, dtCreate;
911 if ( !fn.GetTimes(&dtAccess, &dtMod, &dtCreate) )
912 {
913 wxPrintf(_T("ERROR: GetTimes() failed.\n"));
914 }
915 else
916 {
917 static const wxChar *fmt = _T("%Y-%b-%d %H:%M:%S");
918
919 wxPrintf(_T("File times for '%s':\n"), fn.GetFullPath().c_str());
920 wxPrintf(_T("Creation: \t%s\n"), dtCreate.Format(fmt).c_str());
921 wxPrintf(_T("Last read: \t%s\n"), dtAccess.Format(fmt).c_str());
922 wxPrintf(_T("Last write: \t%s\n"), dtMod.Format(fmt).c_str());
923 }
924 }
925
926 #if 0
927 static void TestFileSetTimes()
928 {
929 wxFileName fn(_T("testdata.fc"));
930
931 if ( !fn.Touch() )
932 {
933 wxPrintf(_T("ERROR: Touch() failed.\n"));
934 }
935 }
936 #endif
937
938 #endif // TEST_FILETIME
939
940 // ----------------------------------------------------------------------------
941 // wxLocale
942 // ----------------------------------------------------------------------------
943
944 #ifdef TEST_LOCALE
945
946 #include "wx/intl.h"
947 #include "wx/utils.h" // for wxSetEnv
948
949 static wxLocale gs_localeDefault(wxLANGUAGE_ENGLISH);
950
951 // find the name of the language from its value
952 static const wxChar *GetLangName(int lang)
953 {
954 static const wxChar *languageNames[] =
955 {
956 _T("DEFAULT"),
957 _T("UNKNOWN"),
958 _T("ABKHAZIAN"),
959 _T("AFAR"),
960 _T("AFRIKAANS"),
961 _T("ALBANIAN"),
962 _T("AMHARIC"),
963 _T("ARABIC"),
964 _T("ARABIC_ALGERIA"),
965 _T("ARABIC_BAHRAIN"),
966 _T("ARABIC_EGYPT"),
967 _T("ARABIC_IRAQ"),
968 _T("ARABIC_JORDAN"),
969 _T("ARABIC_KUWAIT"),
970 _T("ARABIC_LEBANON"),
971 _T("ARABIC_LIBYA"),
972 _T("ARABIC_MOROCCO"),
973 _T("ARABIC_OMAN"),
974 _T("ARABIC_QATAR"),
975 _T("ARABIC_SAUDI_ARABIA"),
976 _T("ARABIC_SUDAN"),
977 _T("ARABIC_SYRIA"),
978 _T("ARABIC_TUNISIA"),
979 _T("ARABIC_UAE"),
980 _T("ARABIC_YEMEN"),
981 _T("ARMENIAN"),
982 _T("ASSAMESE"),
983 _T("AYMARA"),
984 _T("AZERI"),
985 _T("AZERI_CYRILLIC"),
986 _T("AZERI_LATIN"),
987 _T("BASHKIR"),
988 _T("BASQUE"),
989 _T("BELARUSIAN"),
990 _T("BENGALI"),
991 _T("BHUTANI"),
992 _T("BIHARI"),
993 _T("BISLAMA"),
994 _T("BRETON"),
995 _T("BULGARIAN"),
996 _T("BURMESE"),
997 _T("CAMBODIAN"),
998 _T("CATALAN"),
999 _T("CHINESE"),
1000 _T("CHINESE_SIMPLIFIED"),
1001 _T("CHINESE_TRADITIONAL"),
1002 _T("CHINESE_HONGKONG"),
1003 _T("CHINESE_MACAU"),
1004 _T("CHINESE_SINGAPORE"),
1005 _T("CHINESE_TAIWAN"),
1006 _T("CORSICAN"),
1007 _T("CROATIAN"),
1008 _T("CZECH"),
1009 _T("DANISH"),
1010 _T("DUTCH"),
1011 _T("DUTCH_BELGIAN"),
1012 _T("ENGLISH"),
1013 _T("ENGLISH_UK"),
1014 _T("ENGLISH_US"),
1015 _T("ENGLISH_AUSTRALIA"),
1016 _T("ENGLISH_BELIZE"),
1017 _T("ENGLISH_BOTSWANA"),
1018 _T("ENGLISH_CANADA"),
1019 _T("ENGLISH_CARIBBEAN"),
1020 _T("ENGLISH_DENMARK"),
1021 _T("ENGLISH_EIRE"),
1022 _T("ENGLISH_JAMAICA"),
1023 _T("ENGLISH_NEW_ZEALAND"),
1024 _T("ENGLISH_PHILIPPINES"),
1025 _T("ENGLISH_SOUTH_AFRICA"),
1026 _T("ENGLISH_TRINIDAD"),
1027 _T("ENGLISH_ZIMBABWE"),
1028 _T("ESPERANTO"),
1029 _T("ESTONIAN"),
1030 _T("FAEROESE"),
1031 _T("FARSI"),
1032 _T("FIJI"),
1033 _T("FINNISH"),
1034 _T("FRENCH"),
1035 _T("FRENCH_BELGIAN"),
1036 _T("FRENCH_CANADIAN"),
1037 _T("FRENCH_LUXEMBOURG"),
1038 _T("FRENCH_MONACO"),
1039 _T("FRENCH_SWISS"),
1040 _T("FRISIAN"),
1041 _T("GALICIAN"),
1042 _T("GEORGIAN"),
1043 _T("GERMAN"),
1044 _T("GERMAN_AUSTRIAN"),
1045 _T("GERMAN_BELGIUM"),
1046 _T("GERMAN_LIECHTENSTEIN"),
1047 _T("GERMAN_LUXEMBOURG"),
1048 _T("GERMAN_SWISS"),
1049 _T("GREEK"),
1050 _T("GREENLANDIC"),
1051 _T("GUARANI"),
1052 _T("GUJARATI"),
1053 _T("HAUSA"),
1054 _T("HEBREW"),
1055 _T("HINDI"),
1056 _T("HUNGARIAN"),
1057 _T("ICELANDIC"),
1058 _T("INDONESIAN"),
1059 _T("INTERLINGUA"),
1060 _T("INTERLINGUE"),
1061 _T("INUKTITUT"),
1062 _T("INUPIAK"),
1063 _T("IRISH"),
1064 _T("ITALIAN"),
1065 _T("ITALIAN_SWISS"),
1066 _T("JAPANESE"),
1067 _T("JAVANESE"),
1068 _T("KANNADA"),
1069 _T("KASHMIRI"),
1070 _T("KASHMIRI_INDIA"),
1071 _T("KAZAKH"),
1072 _T("KERNEWEK"),
1073 _T("KINYARWANDA"),
1074 _T("KIRGHIZ"),
1075 _T("KIRUNDI"),
1076 _T("KONKANI"),
1077 _T("KOREAN"),
1078 _T("KURDISH"),
1079 _T("LAOTHIAN"),
1080 _T("LATIN"),
1081 _T("LATVIAN"),
1082 _T("LINGALA"),
1083 _T("LITHUANIAN"),
1084 _T("MACEDONIAN"),
1085 _T("MALAGASY"),
1086 _T("MALAY"),
1087 _T("MALAYALAM"),
1088 _T("MALAY_BRUNEI_DARUSSALAM"),
1089 _T("MALAY_MALAYSIA"),
1090 _T("MALTESE"),
1091 _T("MANIPURI"),
1092 _T("MAORI"),
1093 _T("MARATHI"),
1094 _T("MOLDAVIAN"),
1095 _T("MONGOLIAN"),
1096 _T("NAURU"),
1097 _T("NEPALI"),
1098 _T("NEPALI_INDIA"),
1099 _T("NORWEGIAN_BOKMAL"),
1100 _T("NORWEGIAN_NYNORSK"),
1101 _T("OCCITAN"),
1102 _T("ORIYA"),
1103 _T("OROMO"),
1104 _T("PASHTO"),
1105 _T("POLISH"),
1106 _T("PORTUGUESE"),
1107 _T("PORTUGUESE_BRAZILIAN"),
1108 _T("PUNJABI"),
1109 _T("QUECHUA"),
1110 _T("RHAETO_ROMANCE"),
1111 _T("ROMANIAN"),
1112 _T("RUSSIAN"),
1113 _T("RUSSIAN_UKRAINE"),
1114 _T("SAMOAN"),
1115 _T("SANGHO"),
1116 _T("SANSKRIT"),
1117 _T("SCOTS_GAELIC"),
1118 _T("SERBIAN"),
1119 _T("SERBIAN_CYRILLIC"),
1120 _T("SERBIAN_LATIN"),
1121 _T("SERBO_CROATIAN"),
1122 _T("SESOTHO"),
1123 _T("SETSWANA"),
1124 _T("SHONA"),
1125 _T("SINDHI"),
1126 _T("SINHALESE"),
1127 _T("SISWATI"),
1128 _T("SLOVAK"),
1129 _T("SLOVENIAN"),
1130 _T("SOMALI"),
1131 _T("SPANISH"),
1132 _T("SPANISH_ARGENTINA"),
1133 _T("SPANISH_BOLIVIA"),
1134 _T("SPANISH_CHILE"),
1135 _T("SPANISH_COLOMBIA"),
1136 _T("SPANISH_COSTA_RICA"),
1137 _T("SPANISH_DOMINICAN_REPUBLIC"),
1138 _T("SPANISH_ECUADOR"),
1139 _T("SPANISH_EL_SALVADOR"),
1140 _T("SPANISH_GUATEMALA"),
1141 _T("SPANISH_HONDURAS"),
1142 _T("SPANISH_MEXICAN"),
1143 _T("SPANISH_MODERN"),
1144 _T("SPANISH_NICARAGUA"),
1145 _T("SPANISH_PANAMA"),
1146 _T("SPANISH_PARAGUAY"),
1147 _T("SPANISH_PERU"),
1148 _T("SPANISH_PUERTO_RICO"),
1149 _T("SPANISH_URUGUAY"),
1150 _T("SPANISH_US"),
1151 _T("SPANISH_VENEZUELA"),
1152 _T("SUNDANESE"),
1153 _T("SWAHILI"),
1154 _T("SWEDISH"),
1155 _T("SWEDISH_FINLAND"),
1156 _T("TAGALOG"),
1157 _T("TAJIK"),
1158 _T("TAMIL"),
1159 _T("TATAR"),
1160 _T("TELUGU"),
1161 _T("THAI"),
1162 _T("TIBETAN"),
1163 _T("TIGRINYA"),
1164 _T("TONGA"),
1165 _T("TSONGA"),
1166 _T("TURKISH"),
1167 _T("TURKMEN"),
1168 _T("TWI"),
1169 _T("UIGHUR"),
1170 _T("UKRAINIAN"),
1171 _T("URDU"),
1172 _T("URDU_INDIA"),
1173 _T("URDU_PAKISTAN"),
1174 _T("UZBEK"),
1175 _T("UZBEK_CYRILLIC"),
1176 _T("UZBEK_LATIN"),
1177 _T("VIETNAMESE"),
1178 _T("VOLAPUK"),
1179 _T("WELSH"),
1180 _T("WOLOF"),
1181 _T("XHOSA"),
1182 _T("YIDDISH"),
1183 _T("YORUBA"),
1184 _T("ZHUANG"),
1185 _T("ZULU"),
1186 };
1187
1188 if ( (size_t)lang < WXSIZEOF(languageNames) )
1189 return languageNames[lang];
1190 else
1191 return _T("INVALID");
1192 }
1193
1194 static void TestDefaultLang()
1195 {
1196 wxPuts(_T("*** Testing wxLocale::GetSystemLanguage ***"));
1197
1198 static const wxChar *langStrings[] =
1199 {
1200 NULL, // system default
1201 _T("C"),
1202 _T("fr"),
1203 _T("fr_FR"),
1204 _T("en"),
1205 _T("en_GB"),
1206 _T("en_US"),
1207 _T("de_DE.iso88591"),
1208 _T("german"),
1209 _T("?"), // invalid lang spec
1210 _T("klingonese"), // I bet on some systems it does exist...
1211 };
1212
1213 wxPrintf(_T("The default system encoding is %s (%d)\n"),
1214 wxLocale::GetSystemEncodingName().c_str(),
1215 wxLocale::GetSystemEncoding());
1216
1217 for ( size_t n = 0; n < WXSIZEOF(langStrings); n++ )
1218 {
1219 const wxChar *langStr = langStrings[n];
1220 if ( langStr )
1221 {
1222 // FIXME: this doesn't do anything at all under Windows, we need
1223 // to create a new wxLocale!
1224 wxSetEnv(_T("LC_ALL"), langStr);
1225 }
1226
1227 int lang = gs_localeDefault.GetSystemLanguage();
1228 wxPrintf(_T("Locale for '%s' is %s.\n"),
1229 langStr ? langStr : _T("system default"), GetLangName(lang));
1230 }
1231 }
1232
1233 #endif // TEST_LOCALE
1234
1235 // ----------------------------------------------------------------------------
1236 // MIME types
1237 // ----------------------------------------------------------------------------
1238
1239 #ifdef TEST_MIME
1240
1241 #include "wx/mimetype.h"
1242
1243 static void TestMimeEnum()
1244 {
1245 wxPuts(_T("*** Testing wxMimeTypesManager::EnumAllFileTypes() ***\n"));
1246
1247 wxArrayString mimetypes;
1248
1249 size_t count = wxTheMimeTypesManager->EnumAllFileTypes(mimetypes);
1250
1251 wxPrintf(_T("*** All %u known filetypes: ***\n"), count);
1252
1253 wxArrayString exts;
1254 wxString desc;
1255
1256 for ( size_t n = 0; n < count; n++ )
1257 {
1258 wxFileType *filetype =
1259 wxTheMimeTypesManager->GetFileTypeFromMimeType(mimetypes[n]);
1260 if ( !filetype )
1261 {
1262 wxPrintf(_T("nothing known about the filetype '%s'!\n"),
1263 mimetypes[n].c_str());
1264 continue;
1265 }
1266
1267 filetype->GetDescription(&desc);
1268 filetype->GetExtensions(exts);
1269
1270 filetype->GetIcon(NULL);
1271
1272 wxString extsAll;
1273 for ( size_t e = 0; e < exts.GetCount(); e++ )
1274 {
1275 if ( e > 0 )
1276 extsAll << _T(", ");
1277 extsAll += exts[e];
1278 }
1279
1280 wxPrintf(_T("\t%s: %s (%s)\n"),
1281 mimetypes[n].c_str(), desc.c_str(), extsAll.c_str());
1282 }
1283
1284 wxPuts(wxEmptyString);
1285 }
1286
1287 static void TestMimeOverride()
1288 {
1289 wxPuts(_T("*** Testing wxMimeTypesManager additional files loading ***\n"));
1290
1291 static const wxChar *mailcap = _T("/tmp/mailcap");
1292 static const wxChar *mimetypes = _T("/tmp/mime.types");
1293
1294 if ( wxFile::Exists(mailcap) )
1295 wxPrintf(_T("Loading mailcap from '%s': %s\n"),
1296 mailcap,
1297 wxTheMimeTypesManager->ReadMailcap(mailcap) ? _T("ok") : _T("ERROR"));
1298 else
1299 wxPrintf(_T("WARN: mailcap file '%s' doesn't exist, not loaded.\n"),
1300 mailcap);
1301
1302 if ( wxFile::Exists(mimetypes) )
1303 wxPrintf(_T("Loading mime.types from '%s': %s\n"),
1304 mimetypes,
1305 wxTheMimeTypesManager->ReadMimeTypes(mimetypes) ? _T("ok") : _T("ERROR"));
1306 else
1307 wxPrintf(_T("WARN: mime.types file '%s' doesn't exist, not loaded.\n"),
1308 mimetypes);
1309
1310 wxPuts(wxEmptyString);
1311 }
1312
1313 static void TestMimeFilename()
1314 {
1315 wxPuts(_T("*** Testing MIME type from filename query ***\n"));
1316
1317 static const wxChar *filenames[] =
1318 {
1319 _T("readme.txt"),
1320 _T("document.pdf"),
1321 _T("image.gif"),
1322 _T("picture.jpeg"),
1323 };
1324
1325 for ( size_t n = 0; n < WXSIZEOF(filenames); n++ )
1326 {
1327 const wxString fname = filenames[n];
1328 wxString ext = fname.AfterLast(_T('.'));
1329 wxFileType *ft = wxTheMimeTypesManager->GetFileTypeFromExtension(ext);
1330 if ( !ft )
1331 {
1332 wxPrintf(_T("WARNING: extension '%s' is unknown.\n"), ext.c_str());
1333 }
1334 else
1335 {
1336 wxString desc;
1337 if ( !ft->GetDescription(&desc) )
1338 desc = _T("<no description>");
1339
1340 wxString cmd;
1341 if ( !ft->GetOpenCommand(&cmd,
1342 wxFileType::MessageParameters(fname, wxEmptyString)) )
1343 cmd = _T("<no command available>");
1344 else
1345 cmd = wxString(_T('"')) + cmd + _T('"');
1346
1347 wxPrintf(_T("To open %s (%s) do %s.\n"),
1348 fname.c_str(), desc.c_str(), cmd.c_str());
1349
1350 delete ft;
1351 }
1352 }
1353
1354 wxPuts(wxEmptyString);
1355 }
1356
1357 static void TestMimeAssociate()
1358 {
1359 wxPuts(_T("*** Testing creation of filetype association ***\n"));
1360
1361 wxFileTypeInfo ftInfo(
1362 _T("application/x-xyz"),
1363 _T("xyzview '%s'"), // open cmd
1364 _T(""), // print cmd
1365 _T("XYZ File"), // description
1366 _T(".xyz"), // extensions
1367 NULL // end of extensions
1368 );
1369 ftInfo.SetShortDesc(_T("XYZFile")); // used under Win32 only
1370
1371 wxFileType *ft = wxTheMimeTypesManager->Associate(ftInfo);
1372 if ( !ft )
1373 {
1374 wxPuts(_T("ERROR: failed to create association!"));
1375 }
1376 else
1377 {
1378 // TODO: read it back
1379 delete ft;
1380 }
1381
1382 wxPuts(wxEmptyString);
1383 }
1384
1385 #endif // TEST_MIME
1386
1387 // ----------------------------------------------------------------------------
1388 // module dependencies feature
1389 // ----------------------------------------------------------------------------
1390
1391 #ifdef TEST_MODULE
1392
1393 #include "wx/module.h"
1394
1395 class wxTestModule : public wxModule
1396 {
1397 protected:
1398 virtual bool OnInit() { wxPrintf(_T("Load module: %s\n"), GetClassInfo()->GetClassName()); return true; }
1399 virtual void OnExit() { wxPrintf(_T("Unload module: %s\n"), GetClassInfo()->GetClassName()); }
1400 };
1401
1402 class wxTestModuleA : public wxTestModule
1403 {
1404 public:
1405 wxTestModuleA();
1406 private:
1407 DECLARE_DYNAMIC_CLASS(wxTestModuleA)
1408 };
1409
1410 class wxTestModuleB : public wxTestModule
1411 {
1412 public:
1413 wxTestModuleB();
1414 private:
1415 DECLARE_DYNAMIC_CLASS(wxTestModuleB)
1416 };
1417
1418 class wxTestModuleC : public wxTestModule
1419 {
1420 public:
1421 wxTestModuleC();
1422 private:
1423 DECLARE_DYNAMIC_CLASS(wxTestModuleC)
1424 };
1425
1426 class wxTestModuleD : public wxTestModule
1427 {
1428 public:
1429 wxTestModuleD();
1430 private:
1431 DECLARE_DYNAMIC_CLASS(wxTestModuleD)
1432 };
1433
1434 IMPLEMENT_DYNAMIC_CLASS(wxTestModuleC, wxModule)
1435 wxTestModuleC::wxTestModuleC()
1436 {
1437 AddDependency(CLASSINFO(wxTestModuleD));
1438 }
1439
1440 IMPLEMENT_DYNAMIC_CLASS(wxTestModuleA, wxModule)
1441 wxTestModuleA::wxTestModuleA()
1442 {
1443 AddDependency(CLASSINFO(wxTestModuleB));
1444 AddDependency(CLASSINFO(wxTestModuleD));
1445 }
1446
1447 IMPLEMENT_DYNAMIC_CLASS(wxTestModuleD, wxModule)
1448 wxTestModuleD::wxTestModuleD()
1449 {
1450 }
1451
1452 IMPLEMENT_DYNAMIC_CLASS(wxTestModuleB, wxModule)
1453 wxTestModuleB::wxTestModuleB()
1454 {
1455 AddDependency(CLASSINFO(wxTestModuleD));
1456 AddDependency(CLASSINFO(wxTestModuleC));
1457 }
1458
1459 #endif // TEST_MODULE
1460
1461 // ----------------------------------------------------------------------------
1462 // misc information functions
1463 // ----------------------------------------------------------------------------
1464
1465 #ifdef TEST_INFO_FUNCTIONS
1466
1467 #include "wx/utils.h"
1468
1469 #if TEST_INTERACTIVE
1470 static void TestDiskInfo()
1471 {
1472 wxPuts(_T("*** Testing wxGetDiskSpace() ***"));
1473
1474 for ( ;; )
1475 {
1476 wxChar pathname[128];
1477 wxPrintf(_T("\nEnter a directory name: "));
1478 if ( !wxFgets(pathname, WXSIZEOF(pathname), stdin) )
1479 break;
1480
1481 // kill the last '\n'
1482 pathname[wxStrlen(pathname) - 1] = 0;
1483
1484 wxLongLong total, free;
1485 if ( !wxGetDiskSpace(pathname, &total, &free) )
1486 {
1487 wxPuts(_T("ERROR: wxGetDiskSpace failed."));
1488 }
1489 else
1490 {
1491 wxPrintf(_T("%sKb total, %sKb free on '%s'.\n"),
1492 (total / 1024).ToString().c_str(),
1493 (free / 1024).ToString().c_str(),
1494 pathname);
1495 }
1496 }
1497 }
1498 #endif // TEST_INTERACTIVE
1499
1500 static void TestOsInfo()
1501 {
1502 wxPuts(_T("*** Testing OS info functions ***\n"));
1503
1504 int major, minor;
1505 wxGetOsVersion(&major, &minor);
1506 wxPrintf(_T("Running under: %s, version %d.%d\n"),
1507 wxGetOsDescription().c_str(), major, minor);
1508
1509 wxPrintf(_T("%ld free bytes of memory left.\n"), wxGetFreeMemory().ToLong());
1510
1511 wxPrintf(_T("Host name is %s (%s).\n"),
1512 wxGetHostName().c_str(), wxGetFullHostName().c_str());
1513
1514 wxPuts(wxEmptyString);
1515 }
1516
1517 static void TestPlatformInfo()
1518 {
1519 wxPuts(_T("*** Testing wxPlatformInfo functions ***\n"));
1520
1521 // get this platform
1522 wxPlatformInfo plat;
1523
1524 wxPrintf(_T("Operating system family name is: %s\n"), plat.GetOperatingSystemFamilyName().c_str());
1525 wxPrintf(_T("Operating system name is: %s\n"), plat.GetOperatingSystemIdName().c_str());
1526 wxPrintf(_T("Port ID name is: %s\n"), plat.GetPortIdName().c_str());
1527 wxPrintf(_T("Port ID short name is: %s\n"), plat.GetPortIdShortName().c_str());
1528 wxPrintf(_T("Architecture is: %s\n"), plat.GetArchName().c_str());
1529 wxPrintf(_T("Endianness is: %s\n"), plat.GetEndiannessName().c_str());
1530
1531 wxPuts(wxEmptyString);
1532 }
1533
1534 static void TestUserInfo()
1535 {
1536 wxPuts(_T("*** Testing user info functions ***\n"));
1537
1538 wxPrintf(_T("User id is:\t%s\n"), wxGetUserId().c_str());
1539 wxPrintf(_T("User name is:\t%s\n"), wxGetUserName().c_str());
1540 wxPrintf(_T("Home dir is:\t%s\n"), wxGetHomeDir().c_str());
1541 wxPrintf(_T("Email address:\t%s\n"), wxGetEmailAddress().c_str());
1542
1543 wxPuts(wxEmptyString);
1544 }
1545
1546 #endif // TEST_INFO_FUNCTIONS
1547
1548 // ----------------------------------------------------------------------------
1549 // path list
1550 // ----------------------------------------------------------------------------
1551
1552 #ifdef TEST_PATHLIST
1553
1554 #ifdef __UNIX__
1555 #define CMD_IN_PATH _T("ls")
1556 #else
1557 #define CMD_IN_PATH _T("command.com")
1558 #endif
1559
1560 static void TestPathList()
1561 {
1562 wxPuts(_T("*** Testing wxPathList ***\n"));
1563
1564 wxPathList pathlist;
1565 pathlist.AddEnvList(_T("PATH"));
1566 wxString path = pathlist.FindValidPath(CMD_IN_PATH);
1567 if ( path.empty() )
1568 {
1569 wxPrintf(_T("ERROR: command not found in the path.\n"));
1570 }
1571 else
1572 {
1573 wxPrintf(_T("Command found in the path as '%s'.\n"), path.c_str());
1574 }
1575 }
1576
1577 #endif // TEST_PATHLIST
1578
1579 // ----------------------------------------------------------------------------
1580 // regular expressions
1581 // ----------------------------------------------------------------------------
1582
1583 #ifdef TEST_REGEX
1584
1585 #include "wx/regex.h"
1586
1587 static void TestRegExInteractive()
1588 {
1589 wxPuts(_T("*** Testing RE interactively ***"));
1590
1591 for ( ;; )
1592 {
1593 wxChar pattern[128];
1594 wxPrintf(_T("\nEnter a pattern: "));
1595 if ( !wxFgets(pattern, WXSIZEOF(pattern), stdin) )
1596 break;
1597
1598 // kill the last '\n'
1599 pattern[wxStrlen(pattern) - 1] = 0;
1600
1601 wxRegEx re;
1602 if ( !re.Compile(pattern) )
1603 {
1604 continue;
1605 }
1606
1607 wxChar text[128];
1608 for ( ;; )
1609 {
1610 wxPrintf(_T("Enter text to match: "));
1611 if ( !wxFgets(text, WXSIZEOF(text), stdin) )
1612 break;
1613
1614 // kill the last '\n'
1615 text[wxStrlen(text) - 1] = 0;
1616
1617 if ( !re.Matches(text) )
1618 {
1619 wxPrintf(_T("No match.\n"));
1620 }
1621 else
1622 {
1623 wxPrintf(_T("Pattern matches at '%s'\n"), re.GetMatch(text).c_str());
1624
1625 size_t start, len;
1626 for ( size_t n = 1; ; n++ )
1627 {
1628 if ( !re.GetMatch(&start, &len, n) )
1629 {
1630 break;
1631 }
1632
1633 wxPrintf(_T("Subexpr %u matched '%s'\n"),
1634 n, wxString(text + start, len).c_str());
1635 }
1636 }
1637 }
1638 }
1639 }
1640
1641 #endif // TEST_REGEX
1642
1643 // ----------------------------------------------------------------------------
1644 // database
1645 // ----------------------------------------------------------------------------
1646
1647 #if !wxUSE_ODBC
1648 #undef TEST_ODBC
1649 #endif
1650
1651 #ifdef TEST_ODBC
1652
1653 #include "wx/db.h"
1654
1655 static void TestDbOpen()
1656 {
1657 HENV henv;
1658 wxDb db(henv);
1659 }
1660
1661 #endif // TEST_ODBC
1662
1663 // ----------------------------------------------------------------------------
1664 // printf() tests
1665 // ----------------------------------------------------------------------------
1666
1667 /*
1668 NB: this stuff was taken from the glibc test suite and modified to build
1669 in wxWidgets: if I read the copyright below properly, this shouldn't
1670 be a problem
1671 */
1672
1673 #ifdef TEST_PRINTF
1674
1675 #ifdef wxTEST_PRINTF
1676 // use our functions from wxchar.cpp
1677 #undef wxPrintf
1678 #undef wxSprintf
1679
1680 // NB: do _not_ use ATTRIBUTE_PRINTF here, we have some invalid formats
1681 // in the tests below
1682 int wxPrintf( const wxChar *format, ... );
1683 int wxSprintf( wxChar *str, const wxChar *format, ... );
1684 #endif
1685
1686 #include "wx/longlong.h"
1687
1688 #include <float.h>
1689
1690 static void rfg1 (void);
1691 static void rfg2 (void);
1692
1693
1694 static void
1695 fmtchk (const wxChar *fmt)
1696 {
1697 (void) wxPrintf(_T("%s:\t`"), fmt);
1698 (void) wxPrintf(fmt, 0x12);
1699 (void) wxPrintf(_T("'\n"));
1700 }
1701
1702 static void
1703 fmtst1chk (const wxChar *fmt)
1704 {
1705 (void) wxPrintf(_T("%s:\t`"), fmt);
1706 (void) wxPrintf(fmt, 4, 0x12);
1707 (void) wxPrintf(_T("'\n"));
1708 }
1709
1710 static void
1711 fmtst2chk (const wxChar *fmt)
1712 {
1713 (void) wxPrintf(_T("%s:\t`"), fmt);
1714 (void) wxPrintf(fmt, 4, 4, 0x12);
1715 (void) wxPrintf(_T("'\n"));
1716 }
1717
1718 /* This page is covered by the following copyright: */
1719
1720 /* (C) Copyright C E Chew
1721 *
1722 * Feel free to copy, use and distribute this software provided:
1723 *
1724 * 1. you do not pretend that you wrote it
1725 * 2. you leave this copyright notice intact.
1726 */
1727
1728 /*
1729 * Extracted from exercise.c for glibc-1.05 bug report by Bruce Evans.
1730 */
1731
1732 #define DEC -123
1733 #define INT 255
1734 #define UNS (~0)
1735
1736 /* Formatted Output Test
1737 *
1738 * This exercises the output formatting code.
1739 */
1740
1741 wxChar *PointerNull = NULL;
1742
1743 static void
1744 fp_test (void)
1745 {
1746 int i, j, k, l;
1747 wxChar buf[7];
1748 wxChar *prefix = buf;
1749 wxChar tp[20];
1750
1751 wxPuts(_T("\nFormatted output test"));
1752 wxPrintf(_T("prefix 6d 6o 6x 6X 6u\n"));
1753 wxStrcpy(prefix, _T("%"));
1754 for (i = 0; i < 2; i++) {
1755 for (j = 0; j < 2; j++) {
1756 for (k = 0; k < 2; k++) {
1757 for (l = 0; l < 2; l++) {
1758 wxStrcpy(prefix, _T("%"));
1759 if (i == 0) wxStrcat(prefix, _T("-"));
1760 if (j == 0) wxStrcat(prefix, _T("+"));
1761 if (k == 0) wxStrcat(prefix, _T("#"));
1762 if (l == 0) wxStrcat(prefix, _T("0"));
1763 wxPrintf(_T("%5s |"), prefix);
1764 wxStrcpy(tp, prefix);
1765 wxStrcat(tp, _T("6d |"));
1766 wxPrintf(tp, DEC);
1767 wxStrcpy(tp, prefix);
1768 wxStrcat(tp, _T("6o |"));
1769 wxPrintf(tp, INT);
1770 wxStrcpy(tp, prefix);
1771 wxStrcat(tp, _T("6x |"));
1772 wxPrintf(tp, INT);
1773 wxStrcpy(tp, prefix);
1774 wxStrcat(tp, _T("6X |"));
1775 wxPrintf(tp, INT);
1776 wxStrcpy(tp, prefix);
1777 wxStrcat(tp, _T("6u |"));
1778 wxPrintf(tp, UNS);
1779 wxPrintf(_T("\n"));
1780 }
1781 }
1782 }
1783 }
1784 wxPrintf(_T("%10s\n"), PointerNull);
1785 wxPrintf(_T("%-10s\n"), PointerNull);
1786 }
1787
1788 static void TestPrintf()
1789 {
1790 static wxChar shortstr[] = _T("Hi, Z.");
1791 static wxChar longstr[] = _T("Good morning, Doctor Chandra. This is Hal. \
1792 I am ready for my first lesson today.");
1793 int result = 0;
1794 wxString test_format;
1795
1796 fmtchk(_T("%.4x"));
1797 fmtchk(_T("%04x"));
1798 fmtchk(_T("%4.4x"));
1799 fmtchk(_T("%04.4x"));
1800 fmtchk(_T("%4.3x"));
1801 fmtchk(_T("%04.3x"));
1802
1803 fmtst1chk(_T("%.*x"));
1804 fmtst1chk(_T("%0*x"));
1805 fmtst2chk(_T("%*.*x"));
1806 fmtst2chk(_T("%0*.*x"));
1807
1808 wxString bad_format = _T("bad format:\t\"%b\"\n");
1809 wxPrintf(bad_format.c_str());
1810 wxPrintf(_T("nil pointer (padded):\t\"%10p\"\n"), (void *) NULL);
1811
1812 wxPrintf(_T("decimal negative:\t\"%d\"\n"), -2345);
1813 wxPrintf(_T("octal negative:\t\"%o\"\n"), -2345);
1814 wxPrintf(_T("hex negative:\t\"%x\"\n"), -2345);
1815 wxPrintf(_T("long decimal number:\t\"%ld\"\n"), -123456L);
1816 wxPrintf(_T("long octal negative:\t\"%lo\"\n"), -2345L);
1817 wxPrintf(_T("long unsigned decimal number:\t\"%lu\"\n"), -123456L);
1818 wxPrintf(_T("zero-padded LDN:\t\"%010ld\"\n"), -123456L);
1819 test_format = _T("left-adjusted ZLDN:\t\"%-010ld\"\n");
1820 wxPrintf(test_format.c_str(), -123456);
1821 wxPrintf(_T("space-padded LDN:\t\"%10ld\"\n"), -123456L);
1822 wxPrintf(_T("left-adjusted SLDN:\t\"%-10ld\"\n"), -123456L);
1823
1824 test_format = _T("zero-padded string:\t\"%010s\"\n");
1825 wxPrintf(test_format.c_str(), shortstr);
1826 test_format = _T("left-adjusted Z string:\t\"%-010s\"\n");
1827 wxPrintf(test_format.c_str(), shortstr);
1828 wxPrintf(_T("space-padded string:\t\"%10s\"\n"), shortstr);
1829 wxPrintf(_T("left-adjusted S string:\t\"%-10s\"\n"), shortstr);
1830 wxPrintf(_T("null string:\t\"%s\"\n"), PointerNull);
1831 wxPrintf(_T("limited string:\t\"%.22s\"\n"), longstr);
1832
1833 wxPrintf(_T("e-style >= 1:\t\"%e\"\n"), 12.34);
1834 wxPrintf(_T("e-style >= .1:\t\"%e\"\n"), 0.1234);
1835 wxPrintf(_T("e-style < .1:\t\"%e\"\n"), 0.001234);
1836 wxPrintf(_T("e-style big:\t\"%.60e\"\n"), 1e20);
1837 wxPrintf(_T("e-style == .1:\t\"%e\"\n"), 0.1);
1838 wxPrintf(_T("f-style >= 1:\t\"%f\"\n"), 12.34);
1839 wxPrintf(_T("f-style >= .1:\t\"%f\"\n"), 0.1234);
1840 wxPrintf(_T("f-style < .1:\t\"%f\"\n"), 0.001234);
1841 wxPrintf(_T("g-style >= 1:\t\"%g\"\n"), 12.34);
1842 wxPrintf(_T("g-style >= .1:\t\"%g\"\n"), 0.1234);
1843 wxPrintf(_T("g-style < .1:\t\"%g\"\n"), 0.001234);
1844 wxPrintf(_T("g-style big:\t\"%.60g\"\n"), 1e20);
1845
1846 wxPrintf (_T(" %6.5f\n"), .099999999860301614);
1847 wxPrintf (_T(" %6.5f\n"), .1);
1848 wxPrintf (_T("x%5.4fx\n"), .5);
1849
1850 wxPrintf (_T("%#03x\n"), 1);
1851
1852 //wxPrintf (_T("something really insane: %.10000f\n"), 1.0);
1853
1854 {
1855 double d = FLT_MIN;
1856 int niter = 17;
1857
1858 while (niter-- != 0)
1859 wxPrintf (_T("%.17e\n"), d / 2);
1860 fflush (stdout);
1861 }
1862
1863 #ifndef __WATCOMC__
1864 // Open Watcom cause compiler error here
1865 // Error! E173: col(24) floating-point constant too small to represent
1866 wxPrintf (_T("%15.5e\n"), 4.9406564584124654e-324);
1867 #endif
1868
1869 #define FORMAT _T("|%12.4f|%12.4e|%12.4g|\n")
1870 wxPrintf (FORMAT, 0.0, 0.0, 0.0);
1871 wxPrintf (FORMAT, 1.0, 1.0, 1.0);
1872 wxPrintf (FORMAT, -1.0, -1.0, -1.0);
1873 wxPrintf (FORMAT, 100.0, 100.0, 100.0);
1874 wxPrintf (FORMAT, 1000.0, 1000.0, 1000.0);
1875 wxPrintf (FORMAT, 10000.0, 10000.0, 10000.0);
1876 wxPrintf (FORMAT, 12345.0, 12345.0, 12345.0);
1877 wxPrintf (FORMAT, 100000.0, 100000.0, 100000.0);
1878 wxPrintf (FORMAT, 123456.0, 123456.0, 123456.0);
1879 #undef FORMAT
1880
1881 {
1882 wxChar buf[20];
1883 int rc = wxSnprintf (buf, WXSIZEOF(buf), _T("%30s"), _T("foo"));
1884
1885 wxPrintf(_T("snprintf (\"%%30s\", \"foo\") == %d, \"%.*s\"\n"),
1886 rc, WXSIZEOF(buf), buf);
1887 #if 0
1888 wxChar buf2[512];
1889 wxPrintf ("snprintf (\"%%.999999u\", 10)\n",
1890 wxSnprintf(buf2, WXSIZEOFbuf2), "%.999999u", 10));
1891 #endif
1892 }
1893
1894 fp_test ();
1895
1896 wxPrintf (_T("%e should be 1.234568e+06\n"), 1234567.8);
1897 wxPrintf (_T("%f should be 1234567.800000\n"), 1234567.8);
1898 wxPrintf (_T("%g should be 1.23457e+06\n"), 1234567.8);
1899 wxPrintf (_T("%g should be 123.456\n"), 123.456);
1900 wxPrintf (_T("%g should be 1e+06\n"), 1000000.0);
1901 wxPrintf (_T("%g should be 10\n"), 10.0);
1902 wxPrintf (_T("%g should be 0.02\n"), 0.02);
1903
1904 {
1905 double x=1.0;
1906 wxPrintf(_T("%.17f\n"),(1.0/x/10.0+1.0)*x-x);
1907 }
1908
1909 {
1910 wxChar buf[200];
1911
1912 wxSprintf(buf,_T("%*s%*s%*s"),-1,_T("one"),-20,_T("two"),-30,_T("three"));
1913
1914 result |= wxStrcmp (buf,
1915 _T("onetwo three "));
1916
1917 wxPuts (result != 0 ? _T("Test failed!") : _T("Test ok."));
1918 }
1919
1920 #ifdef wxLongLong_t
1921 {
1922 wxChar buf[200];
1923
1924 wxSprintf(buf, _T("%07") wxLongLongFmtSpec _T("o"), wxLL(040000000000));
1925 #if 0
1926 // for some reason below line fails under Borland
1927 wxPrintf (_T("sprintf (buf, \"%%07Lo\", 040000000000ll) = %s"), buf);
1928 #endif
1929
1930 if (wxStrcmp (buf, _T("40000000000")) != 0)
1931 {
1932 result = 1;
1933 wxPuts (_T("\tFAILED"));
1934 }
1935 wxUnusedVar(result);
1936 wxPuts (wxEmptyString);
1937 }
1938 #endif // wxLongLong_t
1939
1940 wxPrintf (_T("printf (\"%%hhu\", %u) = %hhu\n"), UCHAR_MAX + 2, UCHAR_MAX + 2);
1941 wxPrintf (_T("printf (\"%%hu\", %u) = %hu\n"), USHRT_MAX + 2, USHRT_MAX + 2);
1942
1943 wxPuts (_T("--- Should be no further output. ---"));
1944 rfg1 ();
1945 rfg2 ();
1946
1947 #if 0
1948 {
1949 wxChar bytes[7];
1950 wxChar buf[20];
1951
1952 memset (bytes, '\xff', sizeof bytes);
1953 wxSprintf (buf, _T("foo%hhn\n"), &bytes[3]);
1954 if (bytes[0] != '\xff' || bytes[1] != '\xff' || bytes[2] != '\xff'
1955 || bytes[4] != '\xff' || bytes[5] != '\xff' || bytes[6] != '\xff')
1956 {
1957 wxPuts (_T("%hhn overwrite more bytes"));
1958 result = 1;
1959 }
1960 if (bytes[3] != 3)
1961 {
1962 wxPuts (_T("%hhn wrote incorrect value"));
1963 result = 1;
1964 }
1965 }
1966 #endif
1967 }
1968
1969 static void
1970 rfg1 (void)
1971 {
1972 wxChar buf[100];
1973
1974 wxSprintf (buf, _T("%5.s"), _T("xyz"));
1975 if (wxStrcmp (buf, _T(" ")) != 0)
1976 wxPrintf (_T("got: '%s', expected: '%s'\n"), buf, _T(" "));
1977 wxSprintf (buf, _T("%5.f"), 33.3);
1978 if (wxStrcmp (buf, _T(" 33")) != 0)
1979 wxPrintf (_T("got: '%s', expected: '%s'\n"), buf, _T(" 33"));
1980 wxSprintf (buf, _T("%8.e"), 33.3e7);
1981 if (wxStrcmp (buf, _T(" 3e+08")) != 0)
1982 wxPrintf (_T("got: '%s', expected: '%s'\n"), buf, _T(" 3e+08"));
1983 wxSprintf (buf, _T("%8.E"), 33.3e7);
1984 if (wxStrcmp (buf, _T(" 3E+08")) != 0)
1985 wxPrintf (_T("got: '%s', expected: '%s'\n"), buf, _T(" 3E+08"));
1986 wxSprintf (buf, _T("%.g"), 33.3);
1987 if (wxStrcmp (buf, _T("3e+01")) != 0)
1988 wxPrintf (_T("got: '%s', expected: '%s'\n"), buf, _T("3e+01"));
1989 wxSprintf (buf, _T("%.G"), 33.3);
1990 if (wxStrcmp (buf, _T("3E+01")) != 0)
1991 wxPrintf (_T("got: '%s', expected: '%s'\n"), buf, _T("3E+01"));
1992 }
1993
1994 static void
1995 rfg2 (void)
1996 {
1997 int prec;
1998 wxChar buf[100];
1999 wxString test_format;
2000
2001 prec = 0;
2002 wxSprintf (buf, _T("%.*g"), prec, 3.3);
2003 if (wxStrcmp (buf, _T("3")) != 0)
2004 wxPrintf (_T("got: '%s', expected: '%s'\n"), buf, _T("3"));
2005 prec = 0;
2006 wxSprintf (buf, _T("%.*G"), prec, 3.3);
2007 if (wxStrcmp (buf, _T("3")) != 0)
2008 wxPrintf (_T("got: '%s', expected: '%s'\n"), buf, _T("3"));
2009 prec = 0;
2010 wxSprintf (buf, _T("%7.*G"), prec, 3.33);
2011 if (wxStrcmp (buf, _T(" 3")) != 0)
2012 wxPrintf (_T("got: '%s', expected: '%s'\n"), buf, _T(" 3"));
2013 prec = 3;
2014 test_format = _T("%04.*o");
2015 wxSprintf (buf, test_format.c_str(), prec, 33);
2016 if (wxStrcmp (buf, _T(" 041")) != 0)
2017 wxPrintf (_T("got: '%s', expected: '%s'\n"), buf, _T(" 041"));
2018 prec = 7;
2019 test_format = _T("%09.*u");
2020 wxSprintf (buf, test_format.c_str(), prec, 33);
2021 if (wxStrcmp (buf, _T(" 0000033")) != 0)
2022 wxPrintf (_T("got: '%s', expected: '%s'\n"), buf, _T(" 0000033"));
2023 prec = 3;
2024 test_format = _T("%04.*x");
2025 wxSprintf (buf, test_format.c_str(), prec, 33);
2026 if (wxStrcmp (buf, _T(" 021")) != 0)
2027 wxPrintf (_T("got: '%s', expected: '%s'\n"), buf, _T(" 021"));
2028 prec = 3;
2029 test_format = _T("%04.*X");
2030 wxSprintf (buf, test_format.c_str(), prec, 33);
2031 if (wxStrcmp (buf, _T(" 021")) != 0)
2032 wxPrintf (_T("got: '%s', expected: '%s'\n"), buf, _T(" 021"));
2033 }
2034
2035 #endif // TEST_PRINTF
2036
2037 // ----------------------------------------------------------------------------
2038 // registry and related stuff
2039 // ----------------------------------------------------------------------------
2040
2041 // this is for MSW only
2042 #ifndef __WXMSW__
2043 #undef TEST_REGCONF
2044 #undef TEST_REGISTRY
2045 #endif
2046
2047 #ifdef TEST_REGCONF
2048
2049 #include "wx/confbase.h"
2050 #include "wx/msw/regconf.h"
2051
2052 #if 0
2053 static void TestRegConfWrite()
2054 {
2055 wxConfig *config = new wxConfig(_T("myapp"));
2056 config->SetPath(_T("/group1"));
2057 config->Write(_T("entry1"), _T("foo"));
2058 config->SetPath(_T("/group2"));
2059 config->Write(_T("entry1"), _T("bar"));
2060 }
2061 #endif
2062
2063 static void TestRegConfRead()
2064 {
2065 wxConfig *config = new wxConfig(_T("myapp"));
2066
2067 wxString str;
2068 long dummy;
2069 config->SetPath(_T("/"));
2070 wxPuts(_T("Enumerating / subgroups:"));
2071 bool bCont = config->GetFirstGroup(str, dummy);
2072 while(bCont)
2073 {
2074 wxPuts(str);
2075 bCont = config->GetNextGroup(str, dummy);
2076 }
2077 }
2078
2079 #endif // TEST_REGCONF
2080
2081 #ifdef TEST_REGISTRY
2082
2083 #include "wx/msw/registry.h"
2084
2085 // I chose this one because I liked its name, but it probably only exists under
2086 // NT
2087 static const wxChar *TESTKEY =
2088 _T("HKEY_LOCAL_MACHINE\\SYSTEM\\ControlSet001\\Control\\CrashControl");
2089
2090 static void TestRegistryRead()
2091 {
2092 wxPuts(_T("*** testing registry reading ***"));
2093
2094 wxRegKey key(TESTKEY);
2095 wxPrintf(_T("The test key name is '%s'.\n"), key.GetName().c_str());
2096 if ( !key.Open() )
2097 {
2098 wxPuts(_T("ERROR: test key can't be opened, aborting test."));
2099
2100 return;
2101 }
2102
2103 size_t nSubKeys, nValues;
2104 if ( key.GetKeyInfo(&nSubKeys, NULL, &nValues, NULL) )
2105 {
2106 wxPrintf(_T("It has %u subkeys and %u values.\n"), nSubKeys, nValues);
2107 }
2108
2109 wxPrintf(_T("Enumerating values:\n"));
2110
2111 long dummy;
2112 wxString value;
2113 bool cont = key.GetFirstValue(value, dummy);
2114 while ( cont )
2115 {
2116 wxPrintf(_T("Value '%s': type "), value.c_str());
2117 switch ( key.GetValueType(value) )
2118 {
2119 case wxRegKey::Type_None: wxPrintf(_T("ERROR (none)")); break;
2120 case wxRegKey::Type_String: wxPrintf(_T("SZ")); break;
2121 case wxRegKey::Type_Expand_String: wxPrintf(_T("EXPAND_SZ")); break;
2122 case wxRegKey::Type_Binary: wxPrintf(_T("BINARY")); break;
2123 case wxRegKey::Type_Dword: wxPrintf(_T("DWORD")); break;
2124 case wxRegKey::Type_Multi_String: wxPrintf(_T("MULTI_SZ")); break;
2125 default: wxPrintf(_T("other (unknown)")); break;
2126 }
2127
2128 wxPrintf(_T(", value = "));
2129 if ( key.IsNumericValue(value) )
2130 {
2131 long val;
2132 key.QueryValue(value, &val);
2133 wxPrintf(_T("%ld"), val);
2134 }
2135 else // string
2136 {
2137 wxString val;
2138 key.QueryValue(value, val);
2139 wxPrintf(_T("'%s'"), val.c_str());
2140
2141 key.QueryRawValue(value, val);
2142 wxPrintf(_T(" (raw value '%s')"), val.c_str());
2143 }
2144
2145 wxPutchar('\n');
2146
2147 cont = key.GetNextValue(value, dummy);
2148 }
2149 }
2150
2151 static void TestRegistryAssociation()
2152 {
2153 /*
2154 The second call to deleteself genertaes an error message, with a
2155 messagebox saying .flo is crucial to system operation, while the .ddf
2156 call also fails, but with no error message
2157 */
2158
2159 wxRegKey key;
2160
2161 key.SetName(_T("HKEY_CLASSES_ROOT\\.ddf") );
2162 key.Create();
2163 key = _T("ddxf_auto_file") ;
2164 key.SetName(_T("HKEY_CLASSES_ROOT\\.flo") );
2165 key.Create();
2166 key = _T("ddxf_auto_file") ;
2167 key.SetName(_T("HKEY_CLASSES_ROOT\\ddxf_auto_file\\DefaultIcon"));
2168 key.Create();
2169 key = _T("program,0") ;
2170 key.SetName(_T("HKEY_CLASSES_ROOT\\ddxf_auto_file\\shell\\open\\command"));
2171 key.Create();
2172 key = _T("program \"%1\"") ;
2173
2174 key.SetName(_T("HKEY_CLASSES_ROOT\\.ddf") );
2175 key.DeleteSelf();
2176 key.SetName(_T("HKEY_CLASSES_ROOT\\.flo") );
2177 key.DeleteSelf();
2178 key.SetName(_T("HKEY_CLASSES_ROOT\\ddxf_auto_file\\DefaultIcon"));
2179 key.DeleteSelf();
2180 key.SetName(_T("HKEY_CLASSES_ROOT\\ddxf_auto_file\\shell\\open\\command"));
2181 key.DeleteSelf();
2182 }
2183
2184 #endif // TEST_REGISTRY
2185
2186 // ----------------------------------------------------------------------------
2187 // scope guard
2188 // ----------------------------------------------------------------------------
2189
2190 #ifdef TEST_SCOPEGUARD
2191
2192 #include "wx/scopeguard.h"
2193
2194 static void function0() { puts("function0()"); }
2195 static void function1(int n) { printf("function1(%d)\n", n); }
2196 static void function2(double x, char c) { printf("function2(%g, %c)\n", x, c); }
2197
2198 struct Object
2199 {
2200 void method0() { printf("method0()\n"); }
2201 void method1(int n) { printf("method1(%d)\n", n); }
2202 void method2(double x, char c) { printf("method2(%g, %c)\n", x, c); }
2203 };
2204
2205 static void TestScopeGuard()
2206 {
2207 wxON_BLOCK_EXIT0(function0);
2208 wxON_BLOCK_EXIT1(function1, 17);
2209 wxON_BLOCK_EXIT2(function2, 3.14, 'p');
2210
2211 Object obj;
2212 wxON_BLOCK_EXIT_OBJ0(obj, Object::method0);
2213 wxON_BLOCK_EXIT_OBJ1(obj, Object::method1, 7);
2214 wxON_BLOCK_EXIT_OBJ2(obj, Object::method2, 2.71, 'e');
2215
2216 wxScopeGuard dismissed = wxMakeGuard(function0);
2217 dismissed.Dismiss();
2218 }
2219
2220 #endif
2221
2222 // ----------------------------------------------------------------------------
2223 // sockets
2224 // ----------------------------------------------------------------------------
2225
2226 #ifdef TEST_SOCKETS
2227
2228 #include "wx/socket.h"
2229 #include "wx/protocol/protocol.h"
2230 #include "wx/protocol/http.h"
2231
2232 static void TestSocketServer()
2233 {
2234 wxPuts(_T("*** Testing wxSocketServer ***\n"));
2235
2236 static const int PORT = 3000;
2237
2238 wxIPV4address addr;
2239 addr.Service(PORT);
2240
2241 wxSocketServer *server = new wxSocketServer(addr);
2242 if ( !server->Ok() )
2243 {
2244 wxPuts(_T("ERROR: failed to bind"));
2245
2246 return;
2247 }
2248
2249 bool quit = false;
2250 while ( !quit )
2251 {
2252 wxPrintf(_T("Server: waiting for connection on port %d...\n"), PORT);
2253
2254 wxSocketBase *socket = server->Accept();
2255 if ( !socket )
2256 {
2257 wxPuts(_T("ERROR: wxSocketServer::Accept() failed."));
2258 break;
2259 }
2260
2261 wxPuts(_T("Server: got a client."));
2262
2263 server->SetTimeout(60); // 1 min
2264
2265 bool close = false;
2266 while ( !close && socket->IsConnected() )
2267 {
2268 wxString s;
2269 wxChar ch = _T('\0');
2270 for ( ;; )
2271 {
2272 if ( socket->Read(&ch, sizeof(ch)).Error() )
2273 {
2274 // don't log error if the client just close the connection
2275 if ( socket->IsConnected() )
2276 {
2277 wxPuts(_T("ERROR: in wxSocket::Read."));
2278 }
2279
2280 break;
2281 }
2282
2283 if ( ch == '\r' )
2284 continue;
2285
2286 if ( ch == '\n' )
2287 break;
2288
2289 s += ch;
2290 }
2291
2292 if ( ch != '\n' )
2293 {
2294 break;
2295 }
2296
2297 wxPrintf(_T("Server: got '%s'.\n"), s.c_str());
2298 if ( s == _T("close") )
2299 {
2300 wxPuts(_T("Closing connection"));
2301
2302 close = true;
2303 }
2304 else if ( s == _T("quit") )
2305 {
2306 close =
2307 quit = true;
2308
2309 wxPuts(_T("Shutting down the server"));
2310 }
2311 else // not a special command
2312 {
2313 socket->Write(s.MakeUpper().c_str(), s.length());
2314 socket->Write("\r\n", 2);
2315 wxPrintf(_T("Server: wrote '%s'.\n"), s.c_str());
2316 }
2317 }
2318
2319 if ( !close )
2320 {
2321 wxPuts(_T("Server: lost a client unexpectedly."));
2322 }
2323
2324 socket->Destroy();
2325 }
2326
2327 // same as "delete server" but is consistent with GUI programs
2328 server->Destroy();
2329 }
2330
2331 static void TestSocketClient()
2332 {
2333 wxPuts(_T("*** Testing wxSocketClient ***\n"));
2334
2335 static const wxChar *hostname = _T("www.wxwidgets.org");
2336
2337 wxIPV4address addr;
2338 addr.Hostname(hostname);
2339 addr.Service(80);
2340
2341 wxPrintf(_T("--- Attempting to connect to %s:80...\n"), hostname);
2342
2343 wxSocketClient client;
2344 if ( !client.Connect(addr) )
2345 {
2346 wxPrintf(_T("ERROR: failed to connect to %s\n"), hostname);
2347 }
2348 else
2349 {
2350 wxPrintf(_T("--- Connected to %s:%u...\n"),
2351 addr.Hostname().c_str(), addr.Service());
2352
2353 wxChar buf[8192];
2354
2355 // could use simply "GET" here I suppose
2356 wxString cmdGet =
2357 wxString::Format(_T("GET http://%s/\r\n"), hostname);
2358 client.Write(cmdGet, cmdGet.length());
2359 wxPrintf(_T("--- Sent command '%s' to the server\n"),
2360 MakePrintable(cmdGet).c_str());
2361 client.Read(buf, WXSIZEOF(buf));
2362 wxPrintf(_T("--- Server replied:\n%s"), buf);
2363 }
2364 }
2365
2366 #endif // TEST_SOCKETS
2367
2368 // ----------------------------------------------------------------------------
2369 // FTP
2370 // ----------------------------------------------------------------------------
2371
2372 #ifdef TEST_FTP
2373
2374 #include "wx/protocol/ftp.h"
2375
2376 static wxFTP ftp;
2377
2378 #define FTP_ANONYMOUS
2379
2380 #ifdef FTP_ANONYMOUS
2381 static const wxChar *directory = _T("/pub");
2382 static const wxChar *filename = _T("welcome.msg");
2383 #else
2384 static const wxChar *directory = _T("/etc");
2385 static const wxChar *filename = _T("issue");
2386 #endif
2387
2388 static bool TestFtpConnect()
2389 {
2390 wxPuts(_T("*** Testing FTP connect ***"));
2391
2392 #ifdef FTP_ANONYMOUS
2393 static const wxChar *hostname = _T("ftp.wxwidgets.org");
2394
2395 wxPrintf(_T("--- Attempting to connect to %s:21 anonymously...\n"), hostname);
2396 #else // !FTP_ANONYMOUS
2397 static const wxChar *hostname = "localhost";
2398
2399 wxChar user[256];
2400 wxFgets(user, WXSIZEOF(user), stdin);
2401 user[wxStrlen(user) - 1] = '\0'; // chop off '\n'
2402 ftp.SetUser(user);
2403
2404 wxChar password[256];
2405 wxPrintf(_T("Password for %s: "), password);
2406 wxFgets(password, WXSIZEOF(password), stdin);
2407 password[wxStrlen(password) - 1] = '\0'; // chop off '\n'
2408 ftp.SetPassword(password);
2409
2410 wxPrintf(_T("--- Attempting to connect to %s:21 as %s...\n"), hostname, user);
2411 #endif // FTP_ANONYMOUS/!FTP_ANONYMOUS
2412
2413 if ( !ftp.Connect(hostname) )
2414 {
2415 wxPrintf(_T("ERROR: failed to connect to %s\n"), hostname);
2416
2417 return false;
2418 }
2419 else
2420 {
2421 wxPrintf(_T("--- Connected to %s, current directory is '%s'\n"),
2422 hostname, ftp.Pwd().c_str());
2423 ftp.Close();
2424 }
2425
2426 return true;
2427 }
2428
2429 // test (fixed?) wxFTP bug with wu-ftpd >= 2.6.0?
2430 static void TestFtpWuFtpd()
2431 {
2432 wxFTP ftp;
2433 static const wxChar *hostname = _T("ftp.eudora.com");
2434 if ( !ftp.Connect(hostname) )
2435 {
2436 wxPrintf(_T("ERROR: failed to connect to %s\n"), hostname);
2437 }
2438 else
2439 {
2440 static const wxChar *filename = _T("eudora/pubs/draft-gellens-submit-09.txt");
2441 wxInputStream *in = ftp.GetInputStream(filename);
2442 if ( !in )
2443 {
2444 wxPrintf(_T("ERROR: couldn't get input stream for %s\n"), filename);
2445 }
2446 else
2447 {
2448 size_t size = in->GetSize();
2449 wxPrintf(_T("Reading file %s (%u bytes)..."), filename, size);
2450
2451 wxChar *data = new wxChar[size];
2452 if ( !in->Read(data, size) )
2453 {
2454 wxPuts(_T("ERROR: read error"));
2455 }
2456 else
2457 {
2458 wxPrintf(_T("Successfully retrieved the file.\n"));
2459 }
2460
2461 delete [] data;
2462 delete in;
2463 }
2464 }
2465 }
2466
2467 static void TestFtpList()
2468 {
2469 wxPuts(_T("*** Testing wxFTP file listing ***\n"));
2470
2471 // test CWD
2472 if ( !ftp.ChDir(directory) )
2473 {
2474 wxPrintf(_T("ERROR: failed to cd to %s\n"), directory);
2475 }
2476
2477 wxPrintf(_T("Current directory is '%s'\n"), ftp.Pwd().c_str());
2478
2479 // test NLIST and LIST
2480 wxArrayString files;
2481 if ( !ftp.GetFilesList(files) )
2482 {
2483 wxPuts(_T("ERROR: failed to get NLIST of files"));
2484 }
2485 else
2486 {
2487 wxPrintf(_T("Brief list of files under '%s':\n"), ftp.Pwd().c_str());
2488 size_t count = files.GetCount();
2489 for ( size_t n = 0; n < count; n++ )
2490 {
2491 wxPrintf(_T("\t%s\n"), files[n].c_str());
2492 }
2493 wxPuts(_T("End of the file list"));
2494 }
2495
2496 if ( !ftp.GetDirList(files) )
2497 {
2498 wxPuts(_T("ERROR: failed to get LIST of files"));
2499 }
2500 else
2501 {
2502 wxPrintf(_T("Detailed list of files under '%s':\n"), ftp.Pwd().c_str());
2503 size_t count = files.GetCount();
2504 for ( size_t n = 0; n < count; n++ )
2505 {
2506 wxPrintf(_T("\t%s\n"), files[n].c_str());
2507 }
2508 wxPuts(_T("End of the file list"));
2509 }
2510
2511 if ( !ftp.ChDir(_T("..")) )
2512 {
2513 wxPuts(_T("ERROR: failed to cd to .."));
2514 }
2515
2516 wxPrintf(_T("Current directory is '%s'\n"), ftp.Pwd().c_str());
2517 }
2518
2519 static void TestFtpDownload()
2520 {
2521 wxPuts(_T("*** Testing wxFTP download ***\n"));
2522
2523 // test RETR
2524 wxInputStream *in = ftp.GetInputStream(filename);
2525 if ( !in )
2526 {
2527 wxPrintf(_T("ERROR: couldn't get input stream for %s\n"), filename);
2528 }
2529 else
2530 {
2531 size_t size = in->GetSize();
2532 wxPrintf(_T("Reading file %s (%u bytes)..."), filename, size);
2533 fflush(stdout);
2534
2535 wxChar *data = new wxChar[size];
2536 if ( !in->Read(data, size) )
2537 {
2538 wxPuts(_T("ERROR: read error"));
2539 }
2540 else
2541 {
2542 wxPrintf(_T("\nContents of %s:\n%s\n"), filename, data);
2543 }
2544
2545 delete [] data;
2546 delete in;
2547 }
2548 }
2549
2550 static void TestFtpFileSize()
2551 {
2552 wxPuts(_T("*** Testing FTP SIZE command ***"));
2553
2554 if ( !ftp.ChDir(directory) )
2555 {
2556 wxPrintf(_T("ERROR: failed to cd to %s\n"), directory);
2557 }
2558
2559 wxPrintf(_T("Current directory is '%s'\n"), ftp.Pwd().c_str());
2560
2561 if ( ftp.FileExists(filename) )
2562 {
2563 int size = ftp.GetFileSize(filename);
2564 if ( size == -1 )
2565 wxPrintf(_T("ERROR: couldn't get size of '%s'\n"), filename);
2566 else
2567 wxPrintf(_T("Size of '%s' is %d bytes.\n"), filename, size);
2568 }
2569 else
2570 {
2571 wxPrintf(_T("ERROR: '%s' doesn't exist\n"), filename);
2572 }
2573 }
2574
2575 static void TestFtpMisc()
2576 {
2577 wxPuts(_T("*** Testing miscellaneous wxFTP functions ***"));
2578
2579 if ( ftp.SendCommand(_T("STAT")) != '2' )
2580 {
2581 wxPuts(_T("ERROR: STAT failed"));
2582 }
2583 else
2584 {
2585 wxPrintf(_T("STAT returned:\n\n%s\n"), ftp.GetLastResult().c_str());
2586 }
2587
2588 if ( ftp.SendCommand(_T("HELP SITE")) != '2' )
2589 {
2590 wxPuts(_T("ERROR: HELP SITE failed"));
2591 }
2592 else
2593 {
2594 wxPrintf(_T("The list of site-specific commands:\n\n%s\n"),
2595 ftp.GetLastResult().c_str());
2596 }
2597 }
2598
2599 static void TestFtpInteractive()
2600 {
2601 wxPuts(_T("\n*** Interactive wxFTP test ***"));
2602
2603 wxChar buf[128];
2604
2605 for ( ;; )
2606 {
2607 wxPrintf(_T("Enter FTP command: "));
2608 if ( !wxFgets(buf, WXSIZEOF(buf), stdin) )
2609 break;
2610
2611 // kill the last '\n'
2612 buf[wxStrlen(buf) - 1] = 0;
2613
2614 // special handling of LIST and NLST as they require data connection
2615 wxString start(buf, 4);
2616 start.MakeUpper();
2617 if ( start == _T("LIST") || start == _T("NLST") )
2618 {
2619 wxString wildcard;
2620 if ( wxStrlen(buf) > 4 )
2621 wildcard = buf + 5;
2622
2623 wxArrayString files;
2624 if ( !ftp.GetList(files, wildcard, start == _T("LIST")) )
2625 {
2626 wxPrintf(_T("ERROR: failed to get %s of files\n"), start.c_str());
2627 }
2628 else
2629 {
2630 wxPrintf(_T("--- %s of '%s' under '%s':\n"),
2631 start.c_str(), wildcard.c_str(), ftp.Pwd().c_str());
2632 size_t count = files.GetCount();
2633 for ( size_t n = 0; n < count; n++ )
2634 {
2635 wxPrintf(_T("\t%s\n"), files[n].c_str());
2636 }
2637 wxPuts(_T("--- End of the file list"));
2638 }
2639 }
2640 else // !list
2641 {
2642 wxChar ch = ftp.SendCommand(buf);
2643 wxPrintf(_T("Command %s"), ch ? _T("succeeded") : _T("failed"));
2644 if ( ch )
2645 {
2646 wxPrintf(_T(" (return code %c)"), ch);
2647 }
2648
2649 wxPrintf(_T(", server reply:\n%s\n\n"), ftp.GetLastResult().c_str());
2650 }
2651 }
2652
2653 wxPuts(_T("\n*** done ***"));
2654 }
2655
2656 static void TestFtpUpload()
2657 {
2658 wxPuts(_T("*** Testing wxFTP uploading ***\n"));
2659
2660 // upload a file
2661 static const wxChar *file1 = _T("test1");
2662 static const wxChar *file2 = _T("test2");
2663 wxOutputStream *out = ftp.GetOutputStream(file1);
2664 if ( out )
2665 {
2666 wxPrintf(_T("--- Uploading to %s ---\n"), file1);
2667 out->Write("First hello", 11);
2668 delete out;
2669 }
2670
2671 // send a command to check the remote file
2672 if ( ftp.SendCommand(wxString(_T("STAT ")) + file1) != '2' )
2673 {
2674 wxPrintf(_T("ERROR: STAT %s failed\n"), file1);
2675 }
2676 else
2677 {
2678 wxPrintf(_T("STAT %s returned:\n\n%s\n"),
2679 file1, ftp.GetLastResult().c_str());
2680 }
2681
2682 out = ftp.GetOutputStream(file2);
2683 if ( out )
2684 {
2685 wxPrintf(_T("--- Uploading to %s ---\n"), file1);
2686 out->Write("Second hello", 12);
2687 delete out;
2688 }
2689 }
2690
2691 #endif // TEST_FTP
2692
2693 // ----------------------------------------------------------------------------
2694 // stack backtrace
2695 // ----------------------------------------------------------------------------
2696
2697 #ifdef TEST_STACKWALKER
2698
2699 #if wxUSE_STACKWALKER
2700
2701 #include "wx/stackwalk.h"
2702
2703 class StackDump : public wxStackWalker
2704 {
2705 public:
2706 StackDump(const char *argv0)
2707 : wxStackWalker(argv0)
2708 {
2709 }
2710
2711 virtual void Walk(size_t skip = 1)
2712 {
2713 wxPuts(_T("Stack dump:"));
2714
2715 wxStackWalker::Walk(skip);
2716 }
2717
2718 protected:
2719 virtual void OnStackFrame(const wxStackFrame& frame)
2720 {
2721 printf("[%2d] ", frame.GetLevel());
2722
2723 wxString name = frame.GetName();
2724 if ( !name.empty() )
2725 {
2726 printf("%-20.40s", name.mb_str());
2727 }
2728 else
2729 {
2730 printf("0x%08lx", (unsigned long)frame.GetAddress());
2731 }
2732
2733 if ( frame.HasSourceLocation() )
2734 {
2735 printf("\t%s:%d",
2736 frame.GetFileName().mb_str(),
2737 frame.GetLine());
2738 }
2739
2740 puts("");
2741
2742 wxString type, val;
2743 for ( size_t n = 0; frame.GetParam(n, &type, &name, &val); n++ )
2744 {
2745 printf("\t%s %s = %s\n", type.mb_str(), name.mb_str(), val.mb_str());
2746 }
2747 }
2748 };
2749
2750 static void TestStackWalk(const char *argv0)
2751 {
2752 wxPuts(_T("*** Testing wxStackWalker ***\n"));
2753
2754 StackDump dump(argv0);
2755 dump.Walk();
2756 }
2757
2758 #endif // wxUSE_STACKWALKER
2759
2760 #endif // TEST_STACKWALKER
2761
2762 // ----------------------------------------------------------------------------
2763 // standard paths
2764 // ----------------------------------------------------------------------------
2765
2766 #ifdef TEST_STDPATHS
2767
2768 #include "wx/stdpaths.h"
2769
2770 static void TestStandardPaths()
2771 {
2772 wxPuts(_T("*** Testing wxStandardPaths ***\n"));
2773
2774 wxTheApp->SetAppName(_T("console"));
2775
2776 wxStandardPathsBase& stdp = wxStandardPaths::Get();
2777 wxPrintf(_T("Config dir (sys):\t%s\n"), stdp.GetConfigDir().c_str());
2778 wxPrintf(_T("Config dir (user):\t%s\n"), stdp.GetUserConfigDir().c_str());
2779 wxPrintf(_T("Data dir (sys):\t\t%s\n"), stdp.GetDataDir().c_str());
2780 wxPrintf(_T("Data dir (sys local):\t%s\n"), stdp.GetLocalDataDir().c_str());
2781 wxPrintf(_T("Data dir (user):\t%s\n"), stdp.GetUserDataDir().c_str());
2782 wxPrintf(_T("Data dir (user local):\t%s\n"), stdp.GetUserLocalDataDir().c_str());
2783 wxPrintf(_T("Documents dir:\t\t%s\n"), stdp.GetDocumentsDir().c_str());
2784 wxPrintf(_T("Plugins dir:\t\t%s\n"), stdp.GetPluginsDir().c_str());
2785 wxPrintf(_T("Resources dir:\t\t%s\n"), stdp.GetResourcesDir().c_str());
2786 wxPrintf(_T("Localized res. dir:\t%s\n"),
2787 stdp.GetLocalizedResourcesDir(_T("fr")).c_str());
2788 wxPrintf(_T("Message catalogs dir:\t%s\n"),
2789 stdp.GetLocalizedResourcesDir
2790 (
2791 _T("fr"),
2792 wxStandardPaths::ResourceCat_Messages
2793 ).c_str());
2794 }
2795
2796 #endif // TEST_STDPATHS
2797
2798 // ----------------------------------------------------------------------------
2799 // streams
2800 // ----------------------------------------------------------------------------
2801
2802 #ifdef TEST_STREAMS
2803
2804 #include "wx/wfstream.h"
2805 #include "wx/mstream.h"
2806
2807 static void TestFileStream()
2808 {
2809 wxPuts(_T("*** Testing wxFileInputStream ***"));
2810
2811 static const wxString filename = _T("testdata.fs");
2812 {
2813 wxFileOutputStream fsOut(filename);
2814 fsOut.Write("foo", 3);
2815 }
2816
2817 wxFileInputStream fsIn(filename);
2818 wxPrintf(_T("File stream size: %u\n"), fsIn.GetSize());
2819 while ( !fsIn.Eof() )
2820 {
2821 wxPutchar(fsIn.GetC());
2822 }
2823
2824 if ( !wxRemoveFile(filename) )
2825 {
2826 wxPrintf(_T("ERROR: failed to remove the file '%s'.\n"), filename.c_str());
2827 }
2828
2829 wxPuts(_T("\n*** wxFileInputStream test done ***"));
2830 }
2831
2832 static void TestMemoryStream()
2833 {
2834 wxPuts(_T("*** Testing wxMemoryOutputStream ***"));
2835
2836 wxMemoryOutputStream memOutStream;
2837 wxPrintf(_T("Initially out stream offset: %lu\n"),
2838 (unsigned long)memOutStream.TellO());
2839
2840 for ( const wxChar *p = _T("Hello, stream!"); *p; p++ )
2841 {
2842 memOutStream.PutC(*p);
2843 }
2844
2845 wxPrintf(_T("Final out stream offset: %lu\n"),
2846 (unsigned long)memOutStream.TellO());
2847
2848 wxPuts(_T("*** Testing wxMemoryInputStream ***"));
2849
2850 wxChar buf[1024];
2851 size_t len = memOutStream.CopyTo(buf, WXSIZEOF(buf));
2852
2853 wxMemoryInputStream memInpStream(buf, len);
2854 wxPrintf(_T("Memory stream size: %u\n"), memInpStream.GetSize());
2855 while ( !memInpStream.Eof() )
2856 {
2857 wxPutchar(memInpStream.GetC());
2858 }
2859
2860 wxPuts(_T("\n*** wxMemoryInputStream test done ***"));
2861 }
2862
2863 #endif // TEST_STREAMS
2864
2865 // ----------------------------------------------------------------------------
2866 // timers
2867 // ----------------------------------------------------------------------------
2868
2869 #ifdef TEST_TIMER
2870
2871 #include "wx/stopwatch.h"
2872 #include "wx/utils.h"
2873
2874 static void TestStopWatch()
2875 {
2876 wxPuts(_T("*** Testing wxStopWatch ***\n"));
2877
2878 wxStopWatch sw;
2879 sw.Pause();
2880 wxPrintf(_T("Initially paused, after 2 seconds time is..."));
2881 fflush(stdout);
2882 wxSleep(2);
2883 wxPrintf(_T("\t%ldms\n"), sw.Time());
2884
2885 wxPrintf(_T("Resuming stopwatch and sleeping 3 seconds..."));
2886 fflush(stdout);
2887 sw.Resume();
2888 wxSleep(3);
2889 wxPrintf(_T("\telapsed time: %ldms\n"), sw.Time());
2890
2891 sw.Pause();
2892 wxPrintf(_T("Pausing agan and sleeping 2 more seconds..."));
2893 fflush(stdout);
2894 wxSleep(2);
2895 wxPrintf(_T("\telapsed time: %ldms\n"), sw.Time());
2896
2897 sw.Resume();
2898 wxPrintf(_T("Finally resuming and sleeping 2 more seconds..."));
2899 fflush(stdout);
2900 wxSleep(2);
2901 wxPrintf(_T("\telapsed time: %ldms\n"), sw.Time());
2902
2903 wxStopWatch sw2;
2904 wxPuts(_T("\nChecking for 'backwards clock' bug..."));
2905 for ( size_t n = 0; n < 70; n++ )
2906 {
2907 sw2.Start();
2908
2909 for ( size_t m = 0; m < 100000; m++ )
2910 {
2911 if ( sw.Time() < 0 || sw2.Time() < 0 )
2912 {
2913 wxPuts(_T("\ntime is negative - ERROR!"));
2914 }
2915 }
2916
2917 wxPutchar('.');
2918 fflush(stdout);
2919 }
2920
2921 wxPuts(_T(", ok."));
2922 }
2923
2924 #endif // TEST_TIMER
2925
2926 // ----------------------------------------------------------------------------
2927 // vCard support
2928 // ----------------------------------------------------------------------------
2929
2930 #ifdef TEST_VCARD
2931
2932 #include "wx/vcard.h"
2933
2934 static void DumpVObject(size_t level, const wxVCardObject& vcard)
2935 {
2936 void *cookie;
2937 wxVCardObject *vcObj = vcard.GetFirstProp(&cookie);
2938 while ( vcObj )
2939 {
2940 wxPrintf(_T("%s%s"),
2941 wxString(_T('\t'), level).c_str(),
2942 vcObj->GetName().c_str());
2943
2944 wxString value;
2945 switch ( vcObj->GetType() )
2946 {
2947 case wxVCardObject::String:
2948 case wxVCardObject::UString:
2949 {
2950 wxString val;
2951 vcObj->GetValue(&val);
2952 value << _T('"') << val << _T('"');
2953 }
2954 break;
2955
2956 case wxVCardObject::Int:
2957 {
2958 unsigned int i;
2959 vcObj->GetValue(&i);
2960 value.Printf(_T("%u"), i);
2961 }
2962 break;
2963
2964 case wxVCardObject::Long:
2965 {
2966 unsigned long l;
2967 vcObj->GetValue(&l);
2968 value.Printf(_T("%lu"), l);
2969 }
2970 break;
2971
2972 case wxVCardObject::None:
2973 break;
2974
2975 case wxVCardObject::Object:
2976 value = _T("<node>");
2977 break;
2978
2979 default:
2980 value = _T("<unknown value type>");
2981 }
2982
2983 if ( !!value )
2984 wxPrintf(_T(" = %s"), value.c_str());
2985 wxPutchar('\n');
2986
2987 DumpVObject(level + 1, *vcObj);
2988
2989 delete vcObj;
2990 vcObj = vcard.GetNextProp(&cookie);
2991 }
2992 }
2993
2994 static void DumpVCardAddresses(const wxVCard& vcard)
2995 {
2996 wxPuts(_T("\nShowing all addresses from vCard:\n"));
2997
2998 size_t nAdr = 0;
2999 void *cookie;
3000 wxVCardAddress *addr = vcard.GetFirstAddress(&cookie);
3001 while ( addr )
3002 {
3003 wxString flagsStr;
3004 int flags = addr->GetFlags();
3005 if ( flags & wxVCardAddress::Domestic )
3006 {
3007 flagsStr << _T("domestic ");
3008 }
3009 if ( flags & wxVCardAddress::Intl )
3010 {
3011 flagsStr << _T("international ");
3012 }
3013 if ( flags & wxVCardAddress::Postal )
3014 {
3015 flagsStr << _T("postal ");
3016 }
3017 if ( flags & wxVCardAddress::Parcel )
3018 {
3019 flagsStr << _T("parcel ");
3020 }
3021 if ( flags & wxVCardAddress::Home )
3022 {
3023 flagsStr << _T("home ");
3024 }
3025 if ( flags & wxVCardAddress::Work )
3026 {
3027 flagsStr << _T("work ");
3028 }
3029
3030 wxPrintf(_T("Address %u:\n")
3031 "\tflags = %s\n"
3032 "\tvalue = %s;%s;%s;%s;%s;%s;%s\n",
3033 ++nAdr,
3034 flagsStr.c_str(),
3035 addr->GetPostOffice().c_str(),
3036 addr->GetExtAddress().c_str(),
3037 addr->GetStreet().c_str(),
3038 addr->GetLocality().c_str(),
3039 addr->GetRegion().c_str(),
3040 addr->GetPostalCode().c_str(),
3041 addr->GetCountry().c_str()
3042 );
3043
3044 delete addr;
3045 addr = vcard.GetNextAddress(&cookie);
3046 }
3047 }
3048
3049 static void DumpVCardPhoneNumbers(const wxVCard& vcard)
3050 {
3051 wxPuts(_T("\nShowing all phone numbers from vCard:\n"));
3052
3053 size_t nPhone = 0;
3054 void *cookie;
3055 wxVCardPhoneNumber *phone = vcard.GetFirstPhoneNumber(&cookie);
3056 while ( phone )
3057 {
3058 wxString flagsStr;
3059 int flags = phone->GetFlags();
3060 if ( flags & wxVCardPhoneNumber::Voice )
3061 {
3062 flagsStr << _T("voice ");
3063 }
3064 if ( flags & wxVCardPhoneNumber::Fax )
3065 {
3066 flagsStr << _T("fax ");
3067 }
3068 if ( flags & wxVCardPhoneNumber::Cellular )
3069 {
3070 flagsStr << _T("cellular ");
3071 }
3072 if ( flags & wxVCardPhoneNumber::Modem )
3073 {
3074 flagsStr << _T("modem ");
3075 }
3076 if ( flags & wxVCardPhoneNumber::Home )
3077 {
3078 flagsStr << _T("home ");
3079 }
3080 if ( flags & wxVCardPhoneNumber::Work )
3081 {
3082 flagsStr << _T("work ");
3083 }
3084
3085 wxPrintf(_T("Phone number %u:\n")
3086 "\tflags = %s\n"
3087 "\tvalue = %s\n",
3088 ++nPhone,
3089 flagsStr.c_str(),
3090 phone->GetNumber().c_str()
3091 );
3092
3093 delete phone;
3094 phone = vcard.GetNextPhoneNumber(&cookie);
3095 }
3096 }
3097
3098 static void TestVCardRead()
3099 {
3100 wxPuts(_T("*** Testing wxVCard reading ***\n"));
3101
3102 wxVCard vcard(_T("vcard.vcf"));
3103 if ( !vcard.IsOk() )
3104 {
3105 wxPuts(_T("ERROR: couldn't load vCard."));
3106 }
3107 else
3108 {
3109 // read individual vCard properties
3110 wxVCardObject *vcObj = vcard.GetProperty("FN");
3111 wxString value;
3112 if ( vcObj )
3113 {
3114 vcObj->GetValue(&value);
3115 delete vcObj;
3116 }
3117 else
3118 {
3119 value = _T("<none>");
3120 }
3121
3122 wxPrintf(_T("Full name retrieved directly: %s\n"), value.c_str());
3123
3124
3125 if ( !vcard.GetFullName(&value) )
3126 {
3127 value = _T("<none>");
3128 }
3129
3130 wxPrintf(_T("Full name from wxVCard API: %s\n"), value.c_str());
3131
3132 // now show how to deal with multiply occurring properties
3133 DumpVCardAddresses(vcard);
3134 DumpVCardPhoneNumbers(vcard);
3135
3136 // and finally show all
3137 wxPuts(_T("\nNow dumping the entire vCard:\n")
3138 "-----------------------------\n");
3139
3140 DumpVObject(0, vcard);
3141 }
3142 }
3143
3144 static void TestVCardWrite()
3145 {
3146 wxPuts(_T("*** Testing wxVCard writing ***\n"));
3147
3148 wxVCard vcard;
3149 if ( !vcard.IsOk() )
3150 {
3151 wxPuts(_T("ERROR: couldn't create vCard."));
3152 }
3153 else
3154 {
3155 // set some fields
3156 vcard.SetName("Zeitlin", "Vadim");
3157 vcard.SetFullName("Vadim Zeitlin");
3158 vcard.SetOrganization("wxWidgets", "R&D");
3159
3160 // just dump the vCard back
3161 wxPuts(_T("Entire vCard follows:\n"));
3162 wxPuts(vcard.Write());
3163 }
3164 }
3165
3166 #endif // TEST_VCARD
3167
3168 // ----------------------------------------------------------------------------
3169 // wxVolume tests
3170 // ----------------------------------------------------------------------------
3171
3172 #if !defined(__WIN32__) || !wxUSE_FSVOLUME
3173 #undef TEST_VOLUME
3174 #endif
3175
3176 #ifdef TEST_VOLUME
3177
3178 #include "wx/volume.h"
3179
3180 static const wxChar *volumeKinds[] =
3181 {
3182 _T("floppy"),
3183 _T("hard disk"),
3184 _T("CD-ROM"),
3185 _T("DVD-ROM"),
3186 _T("network volume"),
3187 _T("other volume"),
3188 };
3189
3190 static void TestFSVolume()
3191 {
3192 wxPuts(_T("*** Testing wxFSVolume class ***"));
3193
3194 wxArrayString volumes = wxFSVolume::GetVolumes();
3195 size_t count = volumes.GetCount();
3196
3197 if ( !count )
3198 {
3199 wxPuts(_T("ERROR: no mounted volumes?"));
3200 return;
3201 }
3202
3203 wxPrintf(_T("%u mounted volumes found:\n"), count);
3204
3205 for ( size_t n = 0; n < count; n++ )
3206 {
3207 wxFSVolume vol(volumes[n]);
3208 if ( !vol.IsOk() )
3209 {
3210 wxPuts(_T("ERROR: couldn't create volume"));
3211 continue;
3212 }
3213
3214 wxPrintf(_T("%u: %s (%s), %s, %s, %s\n"),
3215 n + 1,
3216 vol.GetDisplayName().c_str(),
3217 vol.GetName().c_str(),
3218 volumeKinds[vol.GetKind()],
3219 vol.IsWritable() ? _T("rw") : _T("ro"),
3220 vol.GetFlags() & wxFS_VOL_REMOVABLE ? _T("removable")
3221 : _T("fixed"));
3222 }
3223 }
3224
3225 #endif // TEST_VOLUME
3226
3227 // ----------------------------------------------------------------------------
3228 // wide char and Unicode support
3229 // ----------------------------------------------------------------------------
3230
3231 #ifdef TEST_WCHAR
3232
3233 #include "wx/strconv.h"
3234 #include "wx/fontenc.h"
3235 #include "wx/encconv.h"
3236 #include "wx/buffer.h"
3237
3238 static const unsigned char utf8koi8r[] =
3239 {
3240 208, 157, 208, 181, 209, 129, 208, 186, 208, 176, 208, 183, 208, 176,
3241 208, 189, 208, 189, 208, 190, 32, 208, 191, 208, 190, 209, 128, 208,
3242 176, 208, 180, 208, 190, 208, 178, 208, 176, 208, 187, 32, 208, 188,
3243 208, 181, 208, 189, 209, 143, 32, 209, 129, 208, 178, 208, 190, 208,
3244 181, 208, 185, 32, 208, 186, 209, 128, 209, 131, 209, 130, 208, 181,
3245 208, 185, 209, 136, 208, 181, 208, 185, 32, 208, 189, 208, 190, 208,
3246 178, 208, 190, 209, 129, 209, 130, 209, 140, 209, 142, 0
3247 };
3248
3249 static const unsigned char utf8iso8859_1[] =
3250 {
3251 0x53, 0x79, 0x73, 0x74, 0xc3, 0xa8, 0x6d, 0x65, 0x73, 0x20, 0x49, 0x6e,
3252 0x74, 0xc3, 0xa9, 0x67, 0x72, 0x61, 0x62, 0x6c, 0x65, 0x73, 0x20, 0x65,
3253 0x6e, 0x20, 0x4d, 0xc3, 0xa9, 0x63, 0x61, 0x6e, 0x69, 0x71, 0x75, 0x65,
3254 0x20, 0x43, 0x6c, 0x61, 0x73, 0x73, 0x69, 0x71, 0x75, 0x65, 0x20, 0x65,
3255 0x74, 0x20, 0x51, 0x75, 0x61, 0x6e, 0x74, 0x69, 0x71, 0x75, 0x65, 0
3256 };
3257
3258 static const unsigned char utf8Invalid[] =
3259 {
3260 0x3c, 0x64, 0x69, 0x73, 0x70, 0x6c, 0x61, 0x79, 0x3e, 0x32, 0x30, 0x30,
3261 0x32, 0xe5, 0xb9, 0xb4, 0x30, 0x39, 0xe6, 0x9c, 0x88, 0x32, 0x35, 0xe6,
3262 0x97, 0xa5, 0x20, 0x30, 0x37, 0xe6, 0x99, 0x82, 0x33, 0x39, 0xe5, 0x88,
3263 0x86, 0x35, 0x37, 0xe7, 0xa7, 0x92, 0x3c, 0x2f, 0x64, 0x69, 0x73, 0x70,
3264 0x6c, 0x61, 0x79, 0
3265 };
3266
3267 static const struct Utf8Data
3268 {
3269 const unsigned char *text;
3270 size_t len;
3271 const wxChar *charset;
3272 wxFontEncoding encoding;
3273 } utf8data[] =
3274 {
3275 { utf8Invalid, WXSIZEOF(utf8Invalid), _T("iso8859-1"), wxFONTENCODING_ISO8859_1 },
3276 { utf8koi8r, WXSIZEOF(utf8koi8r), _T("koi8-r"), wxFONTENCODING_KOI8 },
3277 { utf8iso8859_1, WXSIZEOF(utf8iso8859_1), _T("iso8859-1"), wxFONTENCODING_ISO8859_1 },
3278 };
3279
3280 static void TestUtf8()
3281 {
3282 wxPuts(_T("*** Testing UTF8 support ***\n"));
3283
3284 char buf[1024];
3285 wchar_t wbuf[1024];
3286
3287 for ( size_t n = 0; n < WXSIZEOF(utf8data); n++ )
3288 {
3289 const Utf8Data& u8d = utf8data[n];
3290 if ( wxConvUTF8.MB2WC(wbuf, (const char *)u8d.text,
3291 WXSIZEOF(wbuf)) == (size_t)-1 )
3292 {
3293 wxPuts(_T("ERROR: UTF-8 decoding failed."));
3294 }
3295 else
3296 {
3297 wxCSConv conv(u8d.charset);
3298 if ( conv.WC2MB(buf, wbuf, WXSIZEOF(buf)) == (size_t)-1 )
3299 {
3300 wxPrintf(_T("ERROR: conversion to %s failed.\n"), u8d.charset);
3301 }
3302 else
3303 {
3304 wxPrintf(_T("String in %s: %s\n"), u8d.charset, buf);
3305 }
3306 }
3307
3308 wxString s(wxConvUTF8.cMB2WC((const char *)u8d.text));
3309 if ( s.empty() )
3310 s = _T("<< conversion failed >>");
3311 wxPrintf(_T("String in current cset: %s\n"), s.c_str());
3312
3313 }
3314
3315 wxPuts(wxEmptyString);
3316 }
3317
3318 static void TestEncodingConverter()
3319 {
3320 wxPuts(_T("*** Testing wxEncodingConverter ***\n"));
3321
3322 // using wxEncodingConverter should give the same result as above
3323 char buf[1024];
3324 wchar_t wbuf[1024];
3325 if ( wxConvUTF8.MB2WC(wbuf, (const char *)utf8koi8r,
3326 WXSIZEOF(utf8koi8r)) == (size_t)-1 )
3327 {
3328 wxPuts(_T("ERROR: UTF-8 decoding failed."));
3329 }
3330 else
3331 {
3332 wxEncodingConverter ec;
3333 ec.Init(wxFONTENCODING_UNICODE, wxFONTENCODING_KOI8);
3334 ec.Convert(wbuf, buf);
3335 wxPrintf(_T("The same KOI8-R string using wxEC: %s\n"), buf);
3336 }
3337
3338 wxPuts(wxEmptyString);
3339 }
3340
3341 #endif // TEST_WCHAR
3342
3343 // ----------------------------------------------------------------------------
3344 // ZIP stream
3345 // ----------------------------------------------------------------------------
3346
3347 #ifdef TEST_ZIP
3348
3349 #include "wx/filesys.h"
3350 #include "wx/fs_zip.h"
3351 #include "wx/zipstrm.h"
3352
3353 static const wxChar *TESTFILE_ZIP = _T("testdata.zip");
3354
3355 static void TestZipStreamRead()
3356 {
3357 wxPuts(_T("*** Testing ZIP reading ***\n"));
3358
3359 static const wxString filename = _T("foo");
3360 wxZipInputStream istr(TESTFILE_ZIP, filename);
3361 wxPrintf(_T("Archive size: %u\n"), istr.GetSize());
3362
3363 wxPrintf(_T("Dumping the file '%s':\n"), filename.c_str());
3364 while ( !istr.Eof() )
3365 {
3366 wxPutchar(istr.GetC());
3367 fflush(stdout);
3368 }
3369
3370 wxPuts(_T("\n----- done ------"));
3371 }
3372
3373 static void DumpZipDirectory(wxFileSystem& fs,
3374 const wxString& dir,
3375 const wxString& indent)
3376 {
3377 wxString prefix = wxString::Format(_T("%s#zip:%s"),
3378 TESTFILE_ZIP, dir.c_str());
3379 wxString wildcard = prefix + _T("/*");
3380
3381 wxString dirname = fs.FindFirst(wildcard, wxDIR);
3382 while ( !dirname.empty() )
3383 {
3384 if ( !dirname.StartsWith(prefix + _T('/'), &dirname) )
3385 {
3386 wxPrintf(_T("ERROR: unexpected wxFileSystem::FindNext result\n"));
3387
3388 break;
3389 }
3390
3391 wxPrintf(_T("%s%s\n"), indent.c_str(), dirname.c_str());
3392
3393 DumpZipDirectory(fs, dirname,
3394 indent + wxString(_T(' '), 4));
3395
3396 dirname = fs.FindNext();
3397 }
3398
3399 wxString filename = fs.FindFirst(wildcard, wxFILE);
3400 while ( !filename.empty() )
3401 {
3402 if ( !filename.StartsWith(prefix, &filename) )
3403 {
3404 wxPrintf(_T("ERROR: unexpected wxFileSystem::FindNext result\n"));
3405
3406 break;
3407 }
3408
3409 wxPrintf(_T("%s%s\n"), indent.c_str(), filename.c_str());
3410
3411 filename = fs.FindNext();
3412 }
3413 }
3414
3415 static void TestZipFileSystem()
3416 {
3417 wxPuts(_T("*** Testing ZIP file system ***\n"));
3418
3419 wxFileSystem::AddHandler(new wxZipFSHandler);
3420 wxFileSystem fs;
3421 wxPrintf(_T("Dumping all files in the archive %s:\n"), TESTFILE_ZIP);
3422
3423 DumpZipDirectory(fs, _T(""), wxString(_T(' '), 4));
3424 }
3425
3426 #endif // TEST_ZIP
3427
3428 // ----------------------------------------------------------------------------
3429 // date time
3430 // ----------------------------------------------------------------------------
3431
3432 #ifdef TEST_DATETIME
3433
3434 #include "wx/math.h"
3435 #include "wx/datetime.h"
3436
3437 // this test miscellaneous static wxDateTime functions
3438
3439 #if TEST_ALL
3440
3441 static void TestTimeStatic()
3442 {
3443 wxPuts(_T("\n*** wxDateTime static methods test ***"));
3444
3445 // some info about the current date
3446 int year = wxDateTime::GetCurrentYear();
3447 wxPrintf(_T("Current year %d is %sa leap one and has %d days.\n"),
3448 year,
3449 wxDateTime::IsLeapYear(year) ? "" : "not ",
3450 wxDateTime::GetNumberOfDays(year));
3451
3452 wxDateTime::Month month = wxDateTime::GetCurrentMonth();
3453 wxPrintf(_T("Current month is '%s' ('%s') and it has %d days\n"),
3454 wxDateTime::GetMonthName(month, wxDateTime::Name_Abbr).c_str(),
3455 wxDateTime::GetMonthName(month).c_str(),
3456 wxDateTime::GetNumberOfDays(month));
3457 }
3458
3459 // test time zones stuff
3460 static void TestTimeZones()
3461 {
3462 wxPuts(_T("\n*** wxDateTime timezone test ***"));
3463
3464 wxDateTime now = wxDateTime::Now();
3465
3466 wxPrintf(_T("Current GMT time:\t%s\n"), now.Format(_T("%c"), wxDateTime::GMT0).c_str());
3467 wxPrintf(_T("Unix epoch (GMT):\t%s\n"), wxDateTime((time_t)0).Format(_T("%c"), wxDateTime::GMT0).c_str());
3468 wxPrintf(_T("Unix epoch (EST):\t%s\n"), wxDateTime((time_t)0).Format(_T("%c"), wxDateTime::EST).c_str());
3469 wxPrintf(_T("Current time in Paris:\t%s\n"), now.Format(_T("%c"), wxDateTime::CET).c_str());
3470 wxPrintf(_T(" Moscow:\t%s\n"), now.Format(_T("%c"), wxDateTime::MSK).c_str());
3471 wxPrintf(_T(" New York:\t%s\n"), now.Format(_T("%c"), wxDateTime::EST).c_str());
3472
3473 wxPrintf(_T("%s\n"), wxDateTime::Now().Format(_T("Our timezone is %Z")).c_str());
3474
3475 wxDateTime::Tm tm = now.GetTm();
3476 if ( wxDateTime(tm) != now )
3477 {
3478 wxPrintf(_T("ERROR: got %s instead of %s\n"),
3479 wxDateTime(tm).Format().c_str(), now.Format().c_str());
3480 }
3481 }
3482
3483 // test some minimal support for the dates outside the standard range
3484 static void TestTimeRange()
3485 {
3486 wxPuts(_T("\n*** wxDateTime out-of-standard-range dates test ***"));
3487
3488 static const wxChar *fmt = _T("%d-%b-%Y %H:%M:%S");
3489
3490 wxPrintf(_T("Unix epoch:\t%s\n"),
3491 wxDateTime(2440587.5).Format(fmt).c_str());
3492 wxPrintf(_T("Feb 29, 0: \t%s\n"),
3493 wxDateTime(29, wxDateTime::Feb, 0).Format(fmt).c_str());
3494 wxPrintf(_T("JDN 0: \t%s\n"),
3495 wxDateTime(0.0).Format(fmt).c_str());
3496 wxPrintf(_T("Jan 1, 1AD:\t%s\n"),
3497 wxDateTime(1, wxDateTime::Jan, 1).Format(fmt).c_str());
3498 wxPrintf(_T("May 29, 2099:\t%s\n"),
3499 wxDateTime(29, wxDateTime::May, 2099).Format(fmt).c_str());
3500 }
3501
3502 // test DST calculations
3503 static void TestTimeDST()
3504 {
3505 wxPuts(_T("\n*** wxDateTime DST test ***"));
3506
3507 wxPrintf(_T("DST is%s in effect now.\n\n"),
3508 wxDateTime::Now().IsDST() ? wxEmptyString : _T(" not"));
3509
3510 for ( int year = 1990; year < 2005; year++ )
3511 {
3512 wxPrintf(_T("DST period in Europe for year %d: from %s to %s\n"),
3513 year,
3514 wxDateTime::GetBeginDST(year, wxDateTime::Country_EEC).Format().c_str(),
3515 wxDateTime::GetEndDST(year, wxDateTime::Country_EEC).Format().c_str());
3516 }
3517 }
3518
3519 #endif // TEST_ALL
3520
3521 #if TEST_INTERACTIVE
3522
3523 static void TestDateTimeInteractive()
3524 {
3525 wxPuts(_T("\n*** interactive wxDateTime tests ***"));
3526
3527 wxChar buf[128];
3528
3529 for ( ;; )
3530 {
3531 wxPrintf(_T("Enter a date: "));
3532 if ( !wxFgets(buf, WXSIZEOF(buf), stdin) )
3533 break;
3534
3535 // kill the last '\n'
3536 buf[wxStrlen(buf) - 1] = 0;
3537
3538 wxDateTime dt;
3539 const wxChar *p = dt.ParseDate(buf);
3540 if ( !p )
3541 {
3542 wxPrintf(_T("ERROR: failed to parse the date '%s'.\n"), buf);
3543
3544 continue;
3545 }
3546 else if ( *p )
3547 {
3548 wxPrintf(_T("WARNING: parsed only first %u characters.\n"), p - buf);
3549 }
3550
3551 wxPrintf(_T("%s: day %u, week of month %u/%u, week of year %u\n"),
3552 dt.Format(_T("%b %d, %Y")).c_str(),
3553 dt.GetDayOfYear(),
3554 dt.GetWeekOfMonth(wxDateTime::Monday_First),
3555 dt.GetWeekOfMonth(wxDateTime::Sunday_First),
3556 dt.GetWeekOfYear(wxDateTime::Monday_First));
3557 }
3558
3559 wxPuts(_T("\n*** done ***"));
3560 }
3561
3562 #endif // TEST_INTERACTIVE
3563
3564 #if TEST_ALL
3565
3566 static void TestTimeMS()
3567 {
3568 wxPuts(_T("*** testing millisecond-resolution support in wxDateTime ***"));
3569
3570 wxDateTime dt1 = wxDateTime::Now(),
3571 dt2 = wxDateTime::UNow();
3572
3573 wxPrintf(_T("Now = %s\n"), dt1.Format(_T("%H:%M:%S:%l")).c_str());
3574 wxPrintf(_T("UNow = %s\n"), dt2.Format(_T("%H:%M:%S:%l")).c_str());
3575 wxPrintf(_T("Dummy loop: "));
3576 for ( int i = 0; i < 6000; i++ )
3577 {
3578 //for ( int j = 0; j < 10; j++ )
3579 {
3580 wxString s;
3581 s.Printf(_T("%g"), sqrt((float)i));
3582 }
3583
3584 if ( !(i % 100) )
3585 wxPutchar('.');
3586 }
3587 wxPuts(_T(", done"));
3588
3589 dt1 = dt2;
3590 dt2 = wxDateTime::UNow();
3591 wxPrintf(_T("UNow = %s\n"), dt2.Format(_T("%H:%M:%S:%l")).c_str());
3592
3593 wxPrintf(_T("Loop executed in %s ms\n"), (dt2 - dt1).Format(_T("%l")).c_str());
3594
3595 wxPuts(_T("\n*** done ***"));
3596 }
3597
3598 static void TestTimeHolidays()
3599 {
3600 wxPuts(_T("\n*** testing wxDateTimeHolidayAuthority ***\n"));
3601
3602 wxDateTime::Tm tm = wxDateTime(29, wxDateTime::May, 2000).GetTm();
3603 wxDateTime dtStart(1, tm.mon, tm.year),
3604 dtEnd = dtStart.GetLastMonthDay();
3605
3606 wxDateTimeArray hol;
3607 wxDateTimeHolidayAuthority::GetHolidaysInRange(dtStart, dtEnd, hol);
3608
3609 const wxChar *format = _T("%d-%b-%Y (%a)");
3610
3611 wxPrintf(_T("All holidays between %s and %s:\n"),
3612 dtStart.Format(format).c_str(), dtEnd.Format(format).c_str());
3613
3614 size_t count = hol.GetCount();
3615 for ( size_t n = 0; n < count; n++ )
3616 {
3617 wxPrintf(_T("\t%s\n"), hol[n].Format(format).c_str());
3618 }
3619
3620 wxPuts(wxEmptyString);
3621 }
3622
3623 static void TestTimeZoneBug()
3624 {
3625 wxPuts(_T("\n*** testing for DST/timezone bug ***\n"));
3626
3627 wxDateTime date = wxDateTime(1, wxDateTime::Mar, 2000);
3628 for ( int i = 0; i < 31; i++ )
3629 {
3630 wxPrintf(_T("Date %s: week day %s.\n"),
3631 date.Format(_T("%d-%m-%Y")).c_str(),
3632 date.GetWeekDayName(date.GetWeekDay()).c_str());
3633
3634 date += wxDateSpan::Day();
3635 }
3636
3637 wxPuts(wxEmptyString);
3638 }
3639
3640 static void TestTimeSpanFormat()
3641 {
3642 wxPuts(_T("\n*** wxTimeSpan tests ***"));
3643
3644 static const wxChar *formats[] =
3645 {
3646 _T("(default) %H:%M:%S"),
3647 _T("%E weeks and %D days"),
3648 _T("%l milliseconds"),
3649 _T("(with ms) %H:%M:%S:%l"),
3650 _T("100%% of minutes is %M"), // test "%%"
3651 _T("%D days and %H hours"),
3652 _T("or also %S seconds"),
3653 };
3654
3655 wxTimeSpan ts1(1, 2, 3, 4),
3656 ts2(111, 222, 333);
3657 for ( size_t n = 0; n < WXSIZEOF(formats); n++ )
3658 {
3659 wxPrintf(_T("ts1 = %s\tts2 = %s\n"),
3660 ts1.Format(formats[n]).c_str(),
3661 ts2.Format(formats[n]).c_str());
3662 }
3663
3664 wxPuts(wxEmptyString);
3665 }
3666
3667 #endif // TEST_ALL
3668
3669 #endif // TEST_DATETIME
3670
3671 // ----------------------------------------------------------------------------
3672 // wxTextInput/OutputStream
3673 // ----------------------------------------------------------------------------
3674
3675 #ifdef TEST_TEXTSTREAM
3676
3677 #include "wx/txtstrm.h"
3678 #include "wx/wfstream.h"
3679
3680 static void TestTextInputStream()
3681 {
3682 wxPuts(_T("\n*** wxTextInputStream test ***"));
3683
3684 wxString filename = _T("testdata.fc");
3685 wxFileInputStream fsIn(filename);
3686 if ( !fsIn.Ok() )
3687 {
3688 wxPuts(_T("ERROR: couldn't open file."));
3689 }
3690 else
3691 {
3692 wxTextInputStream tis(fsIn);
3693
3694 size_t line = 1;
3695 for ( ;; )
3696 {
3697 const wxString s = tis.ReadLine();
3698
3699 // line could be non empty if the last line of the file isn't
3700 // terminated with EOL
3701 if ( fsIn.Eof() && s.empty() )
3702 break;
3703
3704 wxPrintf(_T("Line %d: %s\n"), line++, s.c_str());
3705 }
3706 }
3707 }
3708
3709 #endif // TEST_TEXTSTREAM
3710
3711 // ----------------------------------------------------------------------------
3712 // threads
3713 // ----------------------------------------------------------------------------
3714
3715 #ifdef TEST_THREADS
3716
3717 #include "wx/thread.h"
3718
3719 static size_t gs_counter = (size_t)-1;
3720 static wxCriticalSection gs_critsect;
3721 static wxSemaphore gs_cond;
3722
3723 class MyJoinableThread : public wxThread
3724 {
3725 public:
3726 MyJoinableThread(size_t n) : wxThread(wxTHREAD_JOINABLE)
3727 { m_n = n; Create(); }
3728
3729 // thread execution starts here
3730 virtual ExitCode Entry();
3731
3732 private:
3733 size_t m_n;
3734 };
3735
3736 wxThread::ExitCode MyJoinableThread::Entry()
3737 {
3738 unsigned long res = 1;
3739 for ( size_t n = 1; n < m_n; n++ )
3740 {
3741 res *= n;
3742
3743 // it's a loooong calculation :-)
3744 Sleep(100);
3745 }
3746
3747 return (ExitCode)res;
3748 }
3749
3750 class MyDetachedThread : public wxThread
3751 {
3752 public:
3753 MyDetachedThread(size_t n, wxChar ch)
3754 {
3755 m_n = n;
3756 m_ch = ch;
3757 m_cancelled = false;
3758
3759 Create();
3760 }
3761
3762 // thread execution starts here
3763 virtual ExitCode Entry();
3764
3765 // and stops here
3766 virtual void OnExit();
3767
3768 private:
3769 size_t m_n; // number of characters to write
3770 wxChar m_ch; // character to write
3771
3772 bool m_cancelled; // false if we exit normally
3773 };
3774
3775 wxThread::ExitCode MyDetachedThread::Entry()
3776 {
3777 {
3778 wxCriticalSectionLocker lock(gs_critsect);
3779 if ( gs_counter == (size_t)-1 )
3780 gs_counter = 1;
3781 else
3782 gs_counter++;
3783 }
3784
3785 for ( size_t n = 0; n < m_n; n++ )
3786 {
3787 if ( TestDestroy() )
3788 {
3789 m_cancelled = true;
3790
3791 break;
3792 }
3793
3794 wxPutchar(m_ch);
3795 fflush(stdout);
3796
3797 wxThread::Sleep(100);
3798 }
3799
3800 return 0;
3801 }
3802
3803 void MyDetachedThread::OnExit()
3804 {
3805 wxLogTrace(_T("thread"), _T("Thread %ld is in OnExit"), GetId());
3806
3807 wxCriticalSectionLocker lock(gs_critsect);
3808 if ( !--gs_counter && !m_cancelled )
3809 gs_cond.Post();
3810 }
3811
3812 static void TestDetachedThreads()
3813 {
3814 wxPuts(_T("\n*** Testing detached threads ***"));
3815
3816 static const size_t nThreads = 3;
3817 MyDetachedThread *threads[nThreads];
3818 size_t n;
3819 for ( n = 0; n < nThreads; n++ )
3820 {
3821 threads[n] = new MyDetachedThread(10, 'A' + n);
3822 }
3823
3824 threads[0]->SetPriority(WXTHREAD_MIN_PRIORITY);
3825 threads[1]->SetPriority(WXTHREAD_MAX_PRIORITY);
3826
3827 for ( n = 0; n < nThreads; n++ )
3828 {
3829 threads[n]->Run();
3830 }
3831
3832 // wait until all threads terminate
3833 gs_cond.Wait();
3834
3835 wxPuts(wxEmptyString);
3836 }
3837
3838 static void TestJoinableThreads()
3839 {
3840 wxPuts(_T("\n*** Testing a joinable thread (a loooong calculation...) ***"));
3841
3842 // calc 10! in the background
3843 MyJoinableThread thread(10);
3844 thread.Run();
3845
3846 wxPrintf(_T("\nThread terminated with exit code %lu.\n"),
3847 (unsigned long)thread.Wait());
3848 }
3849
3850 static void TestThreadSuspend()
3851 {
3852 wxPuts(_T("\n*** Testing thread suspend/resume functions ***"));
3853
3854 MyDetachedThread *thread = new MyDetachedThread(15, 'X');
3855
3856 thread->Run();
3857
3858 // this is for this demo only, in a real life program we'd use another
3859 // condition variable which would be signaled from wxThread::Entry() to
3860 // tell us that the thread really started running - but here just wait a
3861 // bit and hope that it will be enough (the problem is, of course, that
3862 // the thread might still not run when we call Pause() which will result
3863 // in an error)
3864 wxThread::Sleep(300);
3865
3866 for ( size_t n = 0; n < 3; n++ )
3867 {
3868 thread->Pause();
3869
3870 wxPuts(_T("\nThread suspended"));
3871 if ( n > 0 )
3872 {
3873 // don't sleep but resume immediately the first time
3874 wxThread::Sleep(300);
3875 }
3876 wxPuts(_T("Going to resume the thread"));
3877
3878 thread->Resume();
3879 }
3880
3881 wxPuts(_T("Waiting until it terminates now"));
3882
3883 // wait until the thread terminates
3884 gs_cond.Wait();
3885
3886 wxPuts(wxEmptyString);
3887 }
3888
3889 static void TestThreadDelete()
3890 {
3891 // As above, using Sleep() is only for testing here - we must use some
3892 // synchronisation object instead to ensure that the thread is still
3893 // running when we delete it - deleting a detached thread which already
3894 // terminated will lead to a crash!
3895
3896 wxPuts(_T("\n*** Testing thread delete function ***"));
3897
3898 MyDetachedThread *thread0 = new MyDetachedThread(30, 'W');
3899
3900 thread0->Delete();
3901
3902 wxPuts(_T("\nDeleted a thread which didn't start to run yet."));
3903
3904 MyDetachedThread *thread1 = new MyDetachedThread(30, 'Y');
3905
3906 thread1->Run();
3907
3908 wxThread::Sleep(300);
3909
3910 thread1->Delete();
3911
3912 wxPuts(_T("\nDeleted a running thread."));
3913
3914 MyDetachedThread *thread2 = new MyDetachedThread(30, 'Z');
3915
3916 thread2->Run();
3917
3918 wxThread::Sleep(300);
3919
3920 thread2->Pause();
3921
3922 thread2->Delete();
3923
3924 wxPuts(_T("\nDeleted a sleeping thread."));
3925
3926 MyJoinableThread thread3(20);
3927 thread3.Run();
3928
3929 thread3.Delete();
3930
3931 wxPuts(_T("\nDeleted a joinable thread."));
3932
3933 MyJoinableThread thread4(2);
3934 thread4.Run();
3935
3936 wxThread::Sleep(300);
3937
3938 thread4.Delete();
3939
3940 wxPuts(_T("\nDeleted a joinable thread which already terminated."));
3941
3942 wxPuts(wxEmptyString);
3943 }
3944
3945 class MyWaitingThread : public wxThread
3946 {
3947 public:
3948 MyWaitingThread( wxMutex *mutex, wxCondition *condition )
3949 {
3950 m_mutex = mutex;
3951 m_condition = condition;
3952
3953 Create();
3954 }
3955
3956 virtual ExitCode Entry()
3957 {
3958 wxPrintf(_T("Thread %lu has started running.\n"), GetId());
3959 fflush(stdout);
3960
3961 gs_cond.Post();
3962
3963 wxPrintf(_T("Thread %lu starts to wait...\n"), GetId());
3964 fflush(stdout);
3965
3966 m_mutex->Lock();
3967 m_condition->Wait();
3968 m_mutex->Unlock();
3969
3970 wxPrintf(_T("Thread %lu finished to wait, exiting.\n"), GetId());
3971 fflush(stdout);
3972
3973 return 0;
3974 }
3975
3976 private:
3977 wxMutex *m_mutex;
3978 wxCondition *m_condition;
3979 };
3980
3981 static void TestThreadConditions()
3982 {
3983 wxMutex mutex;
3984 wxCondition condition(mutex);
3985
3986 // otherwise its difficult to understand which log messages pertain to
3987 // which condition
3988 //wxLogTrace(_T("thread"), _T("Local condition var is %08x, gs_cond = %08x"),
3989 // condition.GetId(), gs_cond.GetId());
3990
3991 // create and launch threads
3992 MyWaitingThread *threads[10];
3993
3994 size_t n;
3995 for ( n = 0; n < WXSIZEOF(threads); n++ )
3996 {
3997 threads[n] = new MyWaitingThread( &mutex, &condition );
3998 }
3999
4000 for ( n = 0; n < WXSIZEOF(threads); n++ )
4001 {
4002 threads[n]->Run();
4003 }
4004
4005 // wait until all threads run
4006 wxPuts(_T("Main thread is waiting for the other threads to start"));
4007 fflush(stdout);
4008
4009 size_t nRunning = 0;
4010 while ( nRunning < WXSIZEOF(threads) )
4011 {
4012 gs_cond.Wait();
4013
4014 nRunning++;
4015
4016 wxPrintf(_T("Main thread: %u already running\n"), nRunning);
4017 fflush(stdout);
4018 }
4019
4020 wxPuts(_T("Main thread: all threads started up."));
4021 fflush(stdout);
4022
4023 wxThread::Sleep(500);
4024
4025 #if 1
4026 // now wake one of them up
4027 wxPrintf(_T("Main thread: about to signal the condition.\n"));
4028 fflush(stdout);
4029 condition.Signal();
4030 #endif
4031
4032 wxThread::Sleep(200);
4033
4034 // wake all the (remaining) threads up, so that they can exit
4035 wxPrintf(_T("Main thread: about to broadcast the condition.\n"));
4036 fflush(stdout);
4037 condition.Broadcast();
4038
4039 // give them time to terminate (dirty!)
4040 wxThread::Sleep(500);
4041 }
4042
4043 #include "wx/utils.h"
4044
4045 class MyExecThread : public wxThread
4046 {
4047 public:
4048 MyExecThread(const wxString& command) : wxThread(wxTHREAD_JOINABLE),
4049 m_command(command)
4050 {
4051 Create();
4052 }
4053
4054 virtual ExitCode Entry()
4055 {
4056 return (ExitCode)wxExecute(m_command, wxEXEC_SYNC);
4057 }
4058
4059 private:
4060 wxString m_command;
4061 };
4062
4063 static void TestThreadExec()
4064 {
4065 wxPuts(_T("*** Testing wxExecute interaction with threads ***\n"));
4066
4067 MyExecThread thread(_T("true"));
4068 thread.Run();
4069
4070 wxPrintf(_T("Main program exit code: %ld.\n"),
4071 wxExecute(_T("false"), wxEXEC_SYNC));
4072
4073 wxPrintf(_T("Thread exit code: %ld.\n"), (long)thread.Wait());
4074 }
4075
4076 // semaphore tests
4077 #include "wx/datetime.h"
4078
4079 class MySemaphoreThread : public wxThread
4080 {
4081 public:
4082 MySemaphoreThread(int i, wxSemaphore *sem)
4083 : wxThread(wxTHREAD_JOINABLE),
4084 m_sem(sem),
4085 m_i(i)
4086 {
4087 Create();
4088 }
4089
4090 virtual ExitCode Entry()
4091 {
4092 wxPrintf(_T("%s: Thread #%d (%ld) starting to wait for semaphore...\n"),
4093 wxDateTime::Now().FormatTime().c_str(), m_i, (long)GetId());
4094
4095 m_sem->Wait();
4096
4097 wxPrintf(_T("%s: Thread #%d (%ld) acquired the semaphore.\n"),
4098 wxDateTime::Now().FormatTime().c_str(), m_i, (long)GetId());
4099
4100 Sleep(1000);
4101
4102 wxPrintf(_T("%s: Thread #%d (%ld) releasing the semaphore.\n"),
4103 wxDateTime::Now().FormatTime().c_str(), m_i, (long)GetId());
4104
4105 m_sem->Post();
4106
4107 return 0;
4108 }
4109
4110 private:
4111 wxSemaphore *m_sem;
4112 int m_i;
4113 };
4114
4115 WX_DEFINE_ARRAY_PTR(wxThread *, ArrayThreads);
4116
4117 static void TestSemaphore()
4118 {
4119 wxPuts(_T("*** Testing wxSemaphore class. ***"));
4120
4121 static const int SEM_LIMIT = 3;
4122
4123 wxSemaphore sem(SEM_LIMIT, SEM_LIMIT);
4124 ArrayThreads threads;
4125
4126 for ( int i = 0; i < 3*SEM_LIMIT; i++ )
4127 {
4128 threads.Add(new MySemaphoreThread(i, &sem));
4129 threads.Last()->Run();
4130 }
4131
4132 for ( size_t n = 0; n < threads.GetCount(); n++ )
4133 {
4134 threads[n]->Wait();
4135 delete threads[n];
4136 }
4137 }
4138
4139 #endif // TEST_THREADS
4140
4141 // ----------------------------------------------------------------------------
4142 // entry point
4143 // ----------------------------------------------------------------------------
4144
4145 #ifdef TEST_SNGLINST
4146 #include "wx/snglinst.h"
4147 #endif // TEST_SNGLINST
4148
4149 int main(int argc, char **argv)
4150 {
4151 #if wxUSE_UNICODE
4152 wxChar **wxArgv = new wxChar *[argc + 1];
4153
4154 {
4155 int n;
4156
4157 for (n = 0; n < argc; n++ )
4158 {
4159 wxMB2WXbuf warg = wxConvertMB2WX(argv[n]);
4160 wxArgv[n] = wxStrdup(warg);
4161 }
4162
4163 wxArgv[n] = NULL;
4164 }
4165 #else // !wxUSE_UNICODE
4166 #define wxArgv argv
4167 #endif // wxUSE_UNICODE/!wxUSE_UNICODE
4168
4169 wxApp::CheckBuildOptions(WX_BUILD_OPTIONS_SIGNATURE, "program");
4170
4171 wxInitializer initializer;
4172 if ( !initializer )
4173 {
4174 fprintf(stderr, "Failed to initialize the wxWidgets library, aborting.");
4175
4176 return -1;
4177 }
4178
4179 #ifdef TEST_SNGLINST
4180 wxSingleInstanceChecker checker;
4181 if ( checker.Create(_T(".wxconsole.lock")) )
4182 {
4183 if ( checker.IsAnotherRunning() )
4184 {
4185 wxPrintf(_T("Another instance of the program is running, exiting.\n"));
4186
4187 return 1;
4188 }
4189
4190 // wait some time to give time to launch another instance
4191 wxPrintf(_T("Press \"Enter\" to continue..."));
4192 wxFgetc(stdin);
4193 }
4194 else // failed to create
4195 {
4196 wxPrintf(_T("Failed to init wxSingleInstanceChecker.\n"));
4197 }
4198 #endif // TEST_SNGLINST
4199
4200 #ifdef TEST_CMDLINE
4201 TestCmdLineConvert();
4202
4203 #if wxUSE_CMDLINE_PARSER
4204 static const wxCmdLineEntryDesc cmdLineDesc[] =
4205 {
4206 { wxCMD_LINE_SWITCH, _T("h"), _T("help"), _T("show this help message"),
4207 wxCMD_LINE_VAL_NONE, wxCMD_LINE_OPTION_HELP },
4208 { wxCMD_LINE_SWITCH, _T("v"), _T("verbose"), _T("be verbose") },
4209 { wxCMD_LINE_SWITCH, _T("q"), _T("quiet"), _T("be quiet") },
4210
4211 { wxCMD_LINE_OPTION, _T("o"), _T("output"), _T("output file") },
4212 { wxCMD_LINE_OPTION, _T("i"), _T("input"), _T("input dir") },
4213 { wxCMD_LINE_OPTION, _T("s"), _T("size"), _T("output block size"),
4214 wxCMD_LINE_VAL_NUMBER },
4215 { wxCMD_LINE_OPTION, _T("d"), _T("date"), _T("output file date"),
4216 wxCMD_LINE_VAL_DATE },
4217
4218 { wxCMD_LINE_PARAM, NULL, NULL, _T("input file"),
4219 wxCMD_LINE_VAL_STRING, wxCMD_LINE_PARAM_MULTIPLE },
4220
4221 { wxCMD_LINE_NONE }
4222 };
4223
4224 wxCmdLineParser parser(cmdLineDesc, argc, wxArgv);
4225
4226 parser.AddOption(_T("project_name"), _T(""), _T("full path to project file"),
4227 wxCMD_LINE_VAL_STRING,
4228 wxCMD_LINE_OPTION_MANDATORY | wxCMD_LINE_NEEDS_SEPARATOR);
4229
4230 switch ( parser.Parse() )
4231 {
4232 case -1:
4233 wxLogMessage(_T("Help was given, terminating."));
4234 break;
4235
4236 case 0:
4237 ShowCmdLine(parser);
4238 break;
4239
4240 default:
4241 wxLogMessage(_T("Syntax error detected, aborting."));
4242 break;
4243 }
4244 #endif // wxUSE_CMDLINE_PARSER
4245
4246 #endif // TEST_CMDLINE
4247
4248 #ifdef TEST_DIR
4249 #if TEST_ALL
4250 TestDirExists();
4251 TestDirEnum();
4252 #endif
4253 TestDirTraverse();
4254 #endif // TEST_DIR
4255
4256 #ifdef TEST_DYNLIB
4257 TestDllLoad();
4258 TestDllListLoaded();
4259 #endif // TEST_DYNLIB
4260
4261 #ifdef TEST_ENVIRON
4262 TestEnvironment();
4263 #endif // TEST_ENVIRON
4264
4265 #ifdef TEST_EXECUTE
4266 TestExecute();
4267 #endif // TEST_EXECUTE
4268
4269 #ifdef TEST_FILECONF
4270 TestFileConfRead();
4271 #endif // TEST_FILECONF
4272
4273 #ifdef TEST_LOCALE
4274 TestDefaultLang();
4275 #endif // TEST_LOCALE
4276
4277 #ifdef TEST_LOG
4278 wxPuts(_T("*** Testing wxLog ***"));
4279
4280 wxString s;
4281 for ( size_t n = 0; n < 8000; n++ )
4282 {
4283 s << (wxChar)(_T('A') + (n % 26));
4284 }
4285
4286 wxLogWarning(_T("The length of the string is %lu"),
4287 (unsigned long)s.length());
4288
4289 wxString msg;
4290 msg.Printf(_T("A very very long message: '%s', the end!\n"), s.c_str());
4291
4292 // this one shouldn't be truncated
4293 wxPrintf(msg);
4294
4295 // but this one will because log functions use fixed size buffer
4296 // (note that it doesn't need '\n' at the end neither - will be added
4297 // by wxLog anyhow)
4298 wxLogMessage(_T("A very very long message 2: '%s', the end!"), s.c_str());
4299 #endif // TEST_LOG
4300
4301 #ifdef TEST_FILE
4302 TestFileRead();
4303 TestTextFileRead();
4304 TestFileCopy();
4305 #endif // TEST_FILE
4306
4307 #ifdef TEST_FILENAME
4308 TestFileNameTemp();
4309 TestFileNameCwd();
4310 TestFileNameDirManip();
4311 TestFileNameComparison();
4312 TestFileNameOperations();
4313 #endif // TEST_FILENAME
4314
4315 #ifdef TEST_FILETIME
4316 TestFileGetTimes();
4317 #if 0
4318 TestFileSetTimes();
4319 #endif
4320 #endif // TEST_FILETIME
4321
4322 #ifdef TEST_FTP
4323 wxLog::AddTraceMask(FTP_TRACE_MASK);
4324 if ( TestFtpConnect() )
4325 {
4326 #if TEST_ALL
4327 TestFtpList();
4328 TestFtpDownload();
4329 TestFtpMisc();
4330 TestFtpFileSize();
4331 TestFtpUpload();
4332 #endif // TEST_ALL
4333
4334 #if TEST_INTERACTIVE
4335 TestFtpInteractive();
4336 #endif
4337 }
4338 //else: connecting to the FTP server failed
4339
4340 #if 0
4341 TestFtpWuFtpd();
4342 #endif
4343 #endif // TEST_FTP
4344
4345 #ifdef TEST_MIME
4346 wxLog::AddTraceMask(_T("mime"));
4347 #if TEST_ALL
4348 TestMimeEnum();
4349 TestMimeOverride();
4350 TestMimeAssociate();
4351 #endif
4352 TestMimeFilename();
4353 #endif // TEST_MIME
4354
4355 #ifdef TEST_INFO_FUNCTIONS
4356 TestOsInfo();
4357 TestPlatformInfo();
4358 TestUserInfo();
4359
4360 #if TEST_INTERACTIVE
4361 TestDiskInfo();
4362 #endif
4363 #endif // TEST_INFO_FUNCTIONS
4364
4365 #ifdef TEST_PATHLIST
4366 TestPathList();
4367 #endif // TEST_PATHLIST
4368
4369 #ifdef TEST_ODBC
4370 TestDbOpen();
4371 #endif // TEST_ODBC
4372
4373 #ifdef TEST_PRINTF
4374 TestPrintf();
4375 #endif // TEST_PRINTF
4376
4377 #ifdef TEST_REGCONF
4378 #if 0
4379 TestRegConfWrite();
4380 #endif
4381 TestRegConfRead();
4382 #endif // TEST_REGCONF
4383
4384 #if defined TEST_REGEX && TEST_INTERACTIVE
4385 TestRegExInteractive();
4386 #endif // defined TEST_REGEX && TEST_INTERACTIVE
4387
4388 #ifdef TEST_REGISTRY
4389 TestRegistryRead();
4390 TestRegistryAssociation();
4391 #endif // TEST_REGISTRY
4392
4393 #ifdef TEST_SOCKETS
4394 TestSocketServer();
4395 TestSocketClient();
4396 #endif // TEST_SOCKETS
4397
4398 #ifdef TEST_STREAMS
4399 #if TEST_ALL
4400 TestFileStream();
4401 #endif
4402 TestMemoryStream();
4403 #endif // TEST_STREAMS
4404
4405 #ifdef TEST_TEXTSTREAM
4406 TestTextInputStream();
4407 #endif // TEST_TEXTSTREAM
4408
4409 #ifdef TEST_THREADS
4410 int nCPUs = wxThread::GetCPUCount();
4411 wxPrintf(_T("This system has %d CPUs\n"), nCPUs);
4412 if ( nCPUs != -1 )
4413 wxThread::SetConcurrency(nCPUs);
4414
4415 TestJoinableThreads();
4416
4417 #if TEST_ALL
4418 TestJoinableThreads();
4419 TestDetachedThreads();
4420 TestThreadSuspend();
4421 TestThreadDelete();
4422 TestThreadConditions();
4423 TestThreadExec();
4424 TestSemaphore();
4425 #endif
4426 #endif // TEST_THREADS
4427
4428 #ifdef TEST_TIMER
4429 TestStopWatch();
4430 #endif // TEST_TIMER
4431
4432 #ifdef TEST_DATETIME
4433 #if TEST_ALL
4434 TestTimeStatic();
4435 TestTimeRange();
4436 TestTimeZones();
4437 TestTimeDST();
4438 TestTimeHolidays();
4439 TestTimeSpanFormat();
4440 TestTimeMS();
4441
4442 TestTimeZoneBug();
4443 #endif
4444
4445 #if TEST_INTERACTIVE
4446 TestDateTimeInteractive();
4447 #endif
4448 #endif // TEST_DATETIME
4449
4450 #ifdef TEST_SCOPEGUARD
4451 TestScopeGuard();
4452 #endif
4453
4454 #ifdef TEST_STACKWALKER
4455 #if wxUSE_STACKWALKER
4456 TestStackWalk(argv[0]);
4457 #endif
4458 #endif // TEST_STACKWALKER
4459
4460 #ifdef TEST_STDPATHS
4461 TestStandardPaths();
4462 #endif
4463
4464 #ifdef TEST_USLEEP
4465 wxPuts(_T("Sleeping for 3 seconds... z-z-z-z-z..."));
4466 wxUsleep(3000);
4467 #endif // TEST_USLEEP
4468
4469 #ifdef TEST_VCARD
4470 TestVCardRead();
4471 TestVCardWrite();
4472 #endif // TEST_VCARD
4473
4474 #ifdef TEST_VOLUME
4475 TestFSVolume();
4476 #endif // TEST_VOLUME
4477
4478 #ifdef TEST_WCHAR
4479 TestUtf8();
4480 TestEncodingConverter();
4481 #endif // TEST_WCHAR
4482
4483 #ifdef TEST_ZIP
4484 TestZipStreamRead();
4485 TestZipFileSystem();
4486 #endif // TEST_ZIP
4487
4488 #if wxUSE_UNICODE
4489 {
4490 for ( int n = 0; n < argc; n++ )
4491 free(wxArgv[n]);
4492
4493 delete [] wxArgv;
4494 }
4495 #endif // wxUSE_UNICODE
4496
4497 wxUnusedVar(argc);
4498 wxUnusedVar(argv);
4499 return 0;
4500 }