1 /////////////////////////////////////////////////////////////////////////////
2 // Name: samples/console/console.cpp
3 // Purpose: a sample console (as opposed to GUI) progam using wxWindows
4 // Author: Vadim Zeitlin
8 // Copyright: (c) 1999 Vadim Zeitlin <zeitlin@dptmaths.ens-cachan.fr>
9 // Licence: wxWindows license
10 /////////////////////////////////////////////////////////////////////////////
12 // ============================================================================
14 // ============================================================================
16 // ----------------------------------------------------------------------------
18 // ----------------------------------------------------------------------------
23 #error "This sample can't be compiled in GUI mode."
28 #include "wx/string.h"
32 // without this pragma, the stupid compiler precompiles #defines below so that
33 // changing them doesn't "take place" later!
38 // ----------------------------------------------------------------------------
39 // conditional compilation
40 // ----------------------------------------------------------------------------
43 A note about all these conditional compilation macros: this file is used
44 both as a test suite for various non-GUI wxWindows classes and as a
45 scratchpad for quick tests. So there are two compilation modes: if you
46 define TEST_ALL all tests are run, otherwise you may enable the individual
47 tests individually in the "#else" branch below.
50 // what to test (in alphabetic order)? uncomment the line below to do all tests
58 #define TEST_DLLLOADER
68 #define TEST_INFO_FUNCTIONS
86 // #define TEST_VCARD -- don't enable this (VZ)
93 static const bool TEST_ALL
= TRUE
;
95 #define TEST_DLLLOADER
97 static const bool TEST_ALL
= FALSE
;
100 // some tests are interactive, define this to run them
101 #ifdef TEST_INTERACTIVE
102 #undef TEST_INTERACTIVE
104 static const bool TEST_INTERACTIVE
= TRUE
;
106 static const bool TEST_INTERACTIVE
= FALSE
;
109 // ----------------------------------------------------------------------------
110 // test class for container objects
111 // ----------------------------------------------------------------------------
113 #if defined(TEST_ARRAYS) || defined(TEST_LIST)
115 class Bar
// Foo is already taken in the hash test
118 Bar(const wxString
& name
) : m_name(name
) { ms_bars
++; }
119 Bar(const Bar
& bar
) : m_name(bar
.m_name
) { ms_bars
++; }
120 ~Bar() { ms_bars
--; }
122 static size_t GetNumber() { return ms_bars
; }
124 const wxChar
*GetName() const { return m_name
; }
129 static size_t ms_bars
;
132 size_t Bar::ms_bars
= 0;
134 #endif // defined(TEST_ARRAYS) || defined(TEST_LIST)
136 // ============================================================================
138 // ============================================================================
140 // ----------------------------------------------------------------------------
142 // ----------------------------------------------------------------------------
144 #if defined(TEST_STRINGS) || defined(TEST_SOCKETS)
146 // replace TABs with \t and CRs with \n
147 static wxString
MakePrintable(const wxChar
*s
)
150 (void)str
.Replace(_T("\t"), _T("\\t"));
151 (void)str
.Replace(_T("\n"), _T("\\n"));
152 (void)str
.Replace(_T("\r"), _T("\\r"));
157 #endif // MakePrintable() is used
159 // ----------------------------------------------------------------------------
160 // wxFontMapper::CharsetToEncoding
161 // ----------------------------------------------------------------------------
165 #include "wx/fontmap.h"
167 static void TestCharset()
169 static const wxChar
*charsets
[] =
171 // some vali charsets
180 // and now some bogus ones
187 for ( size_t n
= 0; n
< WXSIZEOF(charsets
); n
++ )
189 wxFontEncoding enc
= wxFontMapper::Get()->CharsetToEncoding(charsets
[n
]);
190 wxPrintf(_T("Charset: %s\tEncoding: %s (%s)\n"),
192 wxFontMapper::Get()->GetEncodingName(enc
).c_str(),
193 wxFontMapper::Get()->GetEncodingDescription(enc
).c_str());
197 #endif // TEST_CHARSET
199 // ----------------------------------------------------------------------------
201 // ----------------------------------------------------------------------------
205 #include "wx/cmdline.h"
206 #include "wx/datetime.h"
209 #if wxUSE_CMDLINE_PARSER
211 static void ShowCmdLine(const wxCmdLineParser
& parser
)
213 wxString s
= _T("Input files: ");
215 size_t count
= parser
.GetParamCount();
216 for ( size_t param
= 0; param
< count
; param
++ )
218 s
<< parser
.GetParam(param
) << ' ';
222 << _T("Verbose:\t") << (parser
.Found(_T("v")) ? _T("yes") : _T("no")) << '\n'
223 << _T("Quiet:\t") << (parser
.Found(_T("q")) ? _T("yes") : _T("no")) << '\n';
228 if ( parser
.Found(_T("o"), &strVal
) )
229 s
<< _T("Output file:\t") << strVal
<< '\n';
230 if ( parser
.Found(_T("i"), &strVal
) )
231 s
<< _T("Input dir:\t") << strVal
<< '\n';
232 if ( parser
.Found(_T("s"), &lVal
) )
233 s
<< _T("Size:\t") << lVal
<< '\n';
234 if ( parser
.Found(_T("d"), &dt
) )
235 s
<< _T("Date:\t") << dt
.FormatISODate() << '\n';
236 if ( parser
.Found(_T("project_name"), &strVal
) )
237 s
<< _T("Project:\t") << strVal
<< '\n';
242 #endif // wxUSE_CMDLINE_PARSER
244 static void TestCmdLineConvert()
246 static const wxChar
*cmdlines
[] =
249 _T("-a \"-bstring 1\" -c\"string 2\" \"string 3\""),
250 _T("literal \\\" and \"\""),
253 for ( size_t n
= 0; n
< WXSIZEOF(cmdlines
); n
++ )
255 const wxChar
*cmdline
= cmdlines
[n
];
256 wxPrintf(_T("Parsing: %s\n"), cmdline
);
257 wxArrayString args
= wxCmdLineParser::ConvertStringToArgs(cmdline
);
259 size_t count
= args
.GetCount();
260 wxPrintf(_T("\targc = %u\n"), count
);
261 for ( size_t arg
= 0; arg
< count
; arg
++ )
263 wxPrintf(_T("\targv[%u] = %s\n"), arg
, args
[arg
].c_str());
268 #endif // TEST_CMDLINE
270 // ----------------------------------------------------------------------------
272 // ----------------------------------------------------------------------------
279 static const wxChar
*ROOTDIR
= _T("/");
280 static const wxChar
*TESTDIR
= _T("/usr");
281 #elif defined(__WXMSW__)
282 static const wxChar
*ROOTDIR
= _T("c:\\");
283 static const wxChar
*TESTDIR
= _T("d:\\");
285 #error "don't know where the root directory is"
288 static void TestDirEnumHelper(wxDir
& dir
,
289 int flags
= wxDIR_DEFAULT
,
290 const wxString
& filespec
= wxEmptyString
)
294 if ( !dir
.IsOpened() )
297 bool cont
= dir
.GetFirst(&filename
, filespec
, flags
);
300 wxPrintf(_T("\t%s\n"), filename
.c_str());
302 cont
= dir
.GetNext(&filename
);
308 static void TestDirEnum()
310 wxPuts(_T("*** Testing wxDir::GetFirst/GetNext ***"));
312 wxString cwd
= wxGetCwd();
313 if ( !wxDir::Exists(cwd
) )
315 wxPrintf(_T("ERROR: current directory '%s' doesn't exist?\n"), cwd
.c_str());
319 wxDir
dir(_T("s:/tmp/foo"));
320 if ( !dir
.IsOpened() )
322 wxPrintf(_T("ERROR: failed to open current directory '%s'.\n"), cwd
.c_str());
326 wxPuts(_T("Enumerating everything in current directory:"));
327 TestDirEnumHelper(dir
);
329 wxPuts(_T("Enumerating really everything in current directory:"));
330 TestDirEnumHelper(dir
, wxDIR_DEFAULT
| wxDIR_DOTDOT
);
332 wxPuts(_T("Enumerating object files in current directory:"));
333 TestDirEnumHelper(dir
, wxDIR_DEFAULT
, "*.o");
335 wxPuts(_T("Enumerating directories in current directory:"));
336 TestDirEnumHelper(dir
, wxDIR_DIRS
);
338 wxPuts(_T("Enumerating files in current directory:"));
339 TestDirEnumHelper(dir
, wxDIR_FILES
);
341 wxPuts(_T("Enumerating files including hidden in current directory:"));
342 TestDirEnumHelper(dir
, wxDIR_FILES
| wxDIR_HIDDEN
);
346 wxPuts(_T("Enumerating everything in root directory:"));
347 TestDirEnumHelper(dir
, wxDIR_DEFAULT
);
349 wxPuts(_T("Enumerating directories in root directory:"));
350 TestDirEnumHelper(dir
, wxDIR_DIRS
);
352 wxPuts(_T("Enumerating files in root directory:"));
353 TestDirEnumHelper(dir
, wxDIR_FILES
);
355 wxPuts(_T("Enumerating files including hidden in root directory:"));
356 TestDirEnumHelper(dir
, wxDIR_FILES
| wxDIR_HIDDEN
);
358 wxPuts(_T("Enumerating files in non existing directory:"));
359 wxDir
dirNo("nosuchdir");
360 TestDirEnumHelper(dirNo
);
363 class DirPrintTraverser
: public wxDirTraverser
366 virtual wxDirTraverseResult
OnFile(const wxString
& filename
)
368 return wxDIR_CONTINUE
;
371 virtual wxDirTraverseResult
OnDir(const wxString
& dirname
)
373 wxString path
, name
, ext
;
374 wxSplitPath(dirname
, &path
, &name
, &ext
);
377 name
<< _T('.') << ext
;
380 for ( const wxChar
*p
= path
.c_str(); *p
; p
++ )
382 if ( wxIsPathSeparator(*p
) )
386 wxPrintf(_T("%s%s\n"), indent
.c_str(), name
.c_str());
388 return wxDIR_CONTINUE
;
392 static void TestDirTraverse()
394 wxPuts(_T("*** Testing wxDir::Traverse() ***"));
398 size_t n
= wxDir::GetAllFiles(TESTDIR
, &files
);
399 wxPrintf(_T("There are %u files under '%s'\n"), n
, TESTDIR
);
402 wxPrintf(_T("First one is '%s'\n"), files
[0u].c_str());
403 wxPrintf(_T(" last one is '%s'\n"), files
[n
- 1].c_str());
406 // enum again with custom traverser
408 DirPrintTraverser traverser
;
409 dir
.Traverse(traverser
, _T(""), wxDIR_DIRS
| wxDIR_HIDDEN
);
412 static void TestDirExists()
414 wxPuts(_T("*** Testing wxDir::Exists() ***"));
416 static const wxChar
*dirnames
[] =
419 #if defined(__WXMSW__)
422 _T("\\\\share\\file"),
426 _T("c:\\autoexec.bat"),
427 #elif defined(__UNIX__)
436 for ( size_t n
= 0; n
< WXSIZEOF(dirnames
); n
++ )
438 wxPrintf(_T("%-40s: %s\n"),
440 wxDir::Exists(dirnames
[n
]) ? _T("exists")
441 : _T("doesn't exist"));
447 // ----------------------------------------------------------------------------
449 // ----------------------------------------------------------------------------
451 #ifdef TEST_DLLLOADER
453 #include "wx/dynlib.h"
455 static void TestDllLoad()
457 #if defined(__WXMSW__)
458 static const wxChar
*LIB_NAME
= _T("kernel32.dll");
459 static const wxChar
*FUNC_NAME
= _T("lstrlenA");
460 #elif defined(__UNIX__)
461 // weird: using just libc.so does *not* work!
462 static const wxChar
*LIB_NAME
= _T("/lib/libc-2.0.7.so");
463 static const wxChar
*FUNC_NAME
= _T("strlen");
465 #error "don't know how to test wxDllLoader on this platform"
468 wxPuts(_T("*** testing wxDllLoader ***\n"));
470 wxDynamicLibrary
lib(LIB_NAME
);
471 if ( !lib
.IsLoaded() )
473 wxPrintf(_T("ERROR: failed to load '%s'.\n"), LIB_NAME
);
477 typedef int (*wxStrlenType
)(const char *);
478 wxStrlenType pfnStrlen
= (wxStrlenType
)lib
.GetSymbol(FUNC_NAME
);
481 wxPrintf(_T("ERROR: function '%s' wasn't found in '%s'.\n"),
482 FUNC_NAME
, LIB_NAME
);
486 if ( pfnStrlen("foo") != 3 )
488 wxPrintf(_T("ERROR: loaded function is not wxStrlen()!\n"));
492 wxPuts(_T("... ok"));
498 #endif // TEST_DLLLOADER
500 // ----------------------------------------------------------------------------
502 // ----------------------------------------------------------------------------
506 #include "wx/utils.h"
508 static wxString
MyGetEnv(const wxString
& var
)
511 if ( !wxGetEnv(var
, &val
) )
514 val
= wxString(_T('\'')) + val
+ _T('\'');
519 static void TestEnvironment()
521 const wxChar
*var
= _T("wxTestVar");
523 wxPuts(_T("*** testing environment access functions ***"));
525 wxPrintf(_T("Initially getenv(%s) = %s\n"), var
, MyGetEnv(var
).c_str());
526 wxSetEnv(var
, _T("value for wxTestVar"));
527 wxPrintf(_T("After wxSetEnv: getenv(%s) = %s\n"), var
, MyGetEnv(var
).c_str());
528 wxSetEnv(var
, _T("another value"));
529 wxPrintf(_T("After 2nd wxSetEnv: getenv(%s) = %s\n"), var
, MyGetEnv(var
).c_str());
531 wxPrintf(_T("After wxUnsetEnv: getenv(%s) = %s\n"), var
, MyGetEnv(var
).c_str());
532 wxPrintf(_T("PATH = %s\n"), MyGetEnv(_T("PATH")).c_str());
535 #endif // TEST_ENVIRON
537 // ----------------------------------------------------------------------------
539 // ----------------------------------------------------------------------------
543 #include "wx/utils.h"
545 static void TestExecute()
547 wxPuts(_T("*** testing wxExecute ***"));
550 #define COMMAND "cat -n ../../Makefile" // "echo hi"
551 #define SHELL_COMMAND "echo hi from shell"
552 #define REDIRECT_COMMAND COMMAND // "date"
553 #elif defined(__WXMSW__)
554 #define COMMAND "command.com -c 'echo hi'"
555 #define SHELL_COMMAND "echo hi"
556 #define REDIRECT_COMMAND COMMAND
558 #error "no command to exec"
561 wxPrintf(_T("Testing wxShell: "));
563 if ( wxShell(SHELL_COMMAND
) )
566 wxPuts(_T("ERROR."));
568 wxPrintf(_T("Testing wxExecute: "));
570 if ( wxExecute(COMMAND
, TRUE
/* sync */) == 0 )
573 wxPuts(_T("ERROR."));
575 #if 0 // no, it doesn't work (yet?)
576 wxPrintf(_T("Testing async wxExecute: "));
578 if ( wxExecute(COMMAND
) != 0 )
579 wxPuts(_T("Ok (command launched)."));
581 wxPuts(_T("ERROR."));
584 wxPrintf(_T("Testing wxExecute with redirection:\n"));
585 wxArrayString output
;
586 if ( wxExecute(REDIRECT_COMMAND
, output
) != 0 )
588 wxPuts(_T("ERROR."));
592 size_t count
= output
.GetCount();
593 for ( size_t n
= 0; n
< count
; n
++ )
595 wxPrintf(_T("\t%s\n"), output
[n
].c_str());
602 #endif // TEST_EXECUTE
604 // ----------------------------------------------------------------------------
606 // ----------------------------------------------------------------------------
611 #include "wx/ffile.h"
612 #include "wx/textfile.h"
614 static void TestFileRead()
616 wxPuts(_T("*** wxFile read test ***"));
618 wxFile
file(_T("testdata.fc"));
619 if ( file
.IsOpened() )
621 wxPrintf(_T("File length: %lu\n"), file
.Length());
623 wxPuts(_T("File dump:\n----------"));
625 static const off_t len
= 1024;
629 off_t nRead
= file
.Read(buf
, len
);
630 if ( nRead
== wxInvalidOffset
)
632 wxPrintf(_T("Failed to read the file."));
636 fwrite(buf
, nRead
, 1, stdout
);
642 wxPuts(_T("----------"));
646 wxPrintf(_T("ERROR: can't open test file.\n"));
652 static void TestTextFileRead()
654 wxPuts(_T("*** wxTextFile read test ***"));
656 wxTextFile
file(_T("testdata.fc"));
659 wxPrintf(_T("Number of lines: %u\n"), file
.GetLineCount());
660 wxPrintf(_T("Last line: '%s'\n"), file
.GetLastLine().c_str());
664 wxPuts(_T("\nDumping the entire file:"));
665 for ( s
= file
.GetFirstLine(); !file
.Eof(); s
= file
.GetNextLine() )
667 wxPrintf(_T("%6u: %s\n"), file
.GetCurrentLine() + 1, s
.c_str());
669 wxPrintf(_T("%6u: %s\n"), file
.GetCurrentLine() + 1, s
.c_str());
671 wxPuts(_T("\nAnd now backwards:"));
672 for ( s
= file
.GetLastLine();
673 file
.GetCurrentLine() != 0;
674 s
= file
.GetPrevLine() )
676 wxPrintf(_T("%6u: %s\n"), file
.GetCurrentLine() + 1, s
.c_str());
678 wxPrintf(_T("%6u: %s\n"), file
.GetCurrentLine() + 1, s
.c_str());
682 wxPrintf(_T("ERROR: can't open '%s'\n"), file
.GetName());
688 static void TestFileCopy()
690 wxPuts(_T("*** Testing wxCopyFile ***"));
692 static const wxChar
*filename1
= _T("testdata.fc");
693 static const wxChar
*filename2
= _T("test2");
694 if ( !wxCopyFile(filename1
, filename2
) )
696 wxPuts(_T("ERROR: failed to copy file"));
700 wxFFile
f1(filename1
, "rb"),
703 if ( !f1
.IsOpened() || !f2
.IsOpened() )
705 wxPuts(_T("ERROR: failed to open file(s)"));
710 if ( !f1
.ReadAll(&s1
) || !f2
.ReadAll(&s2
) )
712 wxPuts(_T("ERROR: failed to read file(s)"));
716 if ( (s1
.length() != s2
.length()) ||
717 (memcmp(s1
.c_str(), s2
.c_str(), s1
.length()) != 0) )
719 wxPuts(_T("ERROR: copy error!"));
723 wxPuts(_T("File was copied ok."));
729 if ( !wxRemoveFile(filename2
) )
731 wxPuts(_T("ERROR: failed to remove the file"));
739 // ----------------------------------------------------------------------------
741 // ----------------------------------------------------------------------------
745 #include "wx/confbase.h"
746 #include "wx/fileconf.h"
748 static const struct FileConfTestData
750 const wxChar
*name
; // value name
751 const wxChar
*value
; // the value from the file
754 { _T("value1"), _T("one") },
755 { _T("value2"), _T("two") },
756 { _T("novalue"), _T("default") },
759 static void TestFileConfRead()
761 wxPuts(_T("*** testing wxFileConfig loading/reading ***"));
763 wxFileConfig
fileconf(_T("test"), wxEmptyString
,
764 _T("testdata.fc"), wxEmptyString
,
765 wxCONFIG_USE_RELATIVE_PATH
);
767 // test simple reading
768 wxPuts(_T("\nReading config file:"));
769 wxString
defValue(_T("default")), value
;
770 for ( size_t n
= 0; n
< WXSIZEOF(fcTestData
); n
++ )
772 const FileConfTestData
& data
= fcTestData
[n
];
773 value
= fileconf
.Read(data
.name
, defValue
);
774 wxPrintf(_T("\t%s = %s "), data
.name
, value
.c_str());
775 if ( value
== data
.value
)
781 wxPrintf(_T("(ERROR: should be %s)\n"), data
.value
);
785 // test enumerating the entries
786 wxPuts(_T("\nEnumerating all root entries:"));
789 bool cont
= fileconf
.GetFirstEntry(name
, dummy
);
792 wxPrintf(_T("\t%s = %s\n"),
794 fileconf
.Read(name
.c_str(), _T("ERROR")).c_str());
796 cont
= fileconf
.GetNextEntry(name
, dummy
);
800 #endif // TEST_FILECONF
802 // ----------------------------------------------------------------------------
804 // ----------------------------------------------------------------------------
808 #include "wx/filename.h"
810 static void DumpFileName(const wxFileName
& fn
)
812 wxString full
= fn
.GetFullPath();
814 wxString vol
, path
, name
, ext
;
815 wxFileName::SplitPath(full
, &vol
, &path
, &name
, &ext
);
817 wxPrintf(_T("'%s'-> vol '%s', path '%s', name '%s', ext '%s'\n"),
818 full
.c_str(), vol
.c_str(), path
.c_str(), name
.c_str(), ext
.c_str());
820 wxFileName::SplitPath(full
, &path
, &name
, &ext
);
821 wxPrintf(_T("or\t\t-> path '%s', name '%s', ext '%s'\n"),
822 path
.c_str(), name
.c_str(), ext
.c_str());
824 wxPrintf(_T("path is also:\t'%s'\n"), fn
.GetPath().c_str());
825 wxPrintf(_T("with volume: \t'%s'\n"),
826 fn
.GetPath(wxPATH_GET_VOLUME
).c_str());
827 wxPrintf(_T("with separator:\t'%s'\n"),
828 fn
.GetPath(wxPATH_GET_SEPARATOR
).c_str());
829 wxPrintf(_T("with both: \t'%s'\n"),
830 fn
.GetPath(wxPATH_GET_SEPARATOR
| wxPATH_GET_VOLUME
).c_str());
832 wxPuts(_T("The directories in the path are:"));
833 wxArrayString dirs
= fn
.GetDirs();
834 size_t count
= dirs
.GetCount();
835 for ( size_t n
= 0; n
< count
; n
++ )
837 wxPrintf(_T("\t%u: %s\n"), n
, dirs
[n
].c_str());
841 static struct FileNameInfo
843 const wxChar
*fullname
;
844 const wxChar
*volume
;
853 { _T("/usr/bin/ls"), _T(""), _T("/usr/bin"), _T("ls"), _T(""), TRUE
, wxPATH_UNIX
},
854 { _T("/usr/bin/"), _T(""), _T("/usr/bin"), _T(""), _T(""), TRUE
, wxPATH_UNIX
},
855 { _T("~/.zshrc"), _T(""), _T("~"), _T(".zshrc"), _T(""), TRUE
, wxPATH_UNIX
},
856 { _T("../../foo"), _T(""), _T("../.."), _T("foo"), _T(""), FALSE
, wxPATH_UNIX
},
857 { _T("foo.bar"), _T(""), _T(""), _T("foo"), _T("bar"), FALSE
, wxPATH_UNIX
},
858 { _T("~/foo.bar"), _T(""), _T("~"), _T("foo"), _T("bar"), TRUE
, wxPATH_UNIX
},
859 { _T("/foo"), _T(""), _T("/"), _T("foo"), _T(""), TRUE
, wxPATH_UNIX
},
860 { _T("Mahogany-0.60/foo.bar"), _T(""), _T("Mahogany-0.60"), _T("foo"), _T("bar"), FALSE
, wxPATH_UNIX
},
861 { _T("/tmp/wxwin.tar.bz"), _T(""), _T("/tmp"), _T("wxwin.tar"), _T("bz"), TRUE
, wxPATH_UNIX
},
863 // Windows file names
864 { _T("foo.bar"), _T(""), _T(""), _T("foo"), _T("bar"), FALSE
, wxPATH_DOS
},
865 { _T("\\foo.bar"), _T(""), _T("\\"), _T("foo"), _T("bar"), FALSE
, wxPATH_DOS
},
866 { _T("c:foo.bar"), _T("c"), _T(""), _T("foo"), _T("bar"), FALSE
, wxPATH_DOS
},
867 { _T("c:\\foo.bar"), _T("c"), _T("\\"), _T("foo"), _T("bar"), TRUE
, wxPATH_DOS
},
868 { _T("c:\\Windows\\command.com"), _T("c"), _T("\\Windows"), _T("command"), _T("com"), TRUE
, wxPATH_DOS
},
869 { _T("\\\\server\\foo.bar"), _T("server"), _T("\\"), _T("foo"), _T("bar"), TRUE
, wxPATH_DOS
},
870 { _T("\\\\server\\dir\\foo.bar"), _T("server"), _T("\\dir"), _T("foo"), _T("bar"), TRUE
, wxPATH_DOS
},
872 // wxFileName support for Mac file names is broken currently
875 { _T("Volume:Dir:File"), _T("Volume"), _T("Dir"), _T("File"), _T(""), TRUE
, wxPATH_MAC
},
876 { _T("Volume:Dir:Subdir:File"), _T("Volume"), _T("Dir:Subdir"), _T("File"), _T(""), TRUE
, wxPATH_MAC
},
877 { _T("Volume:"), _T("Volume"), _T(""), _T(""), _T(""), TRUE
, wxPATH_MAC
},
878 { _T(":Dir:File"), _T(""), _T("Dir"), _T("File"), _T(""), FALSE
, wxPATH_MAC
},
879 { _T(":File.Ext"), _T(""), _T(""), _T("File"), _T(".Ext"), FALSE
, wxPATH_MAC
},
880 { _T("File.Ext"), _T(""), _T(""), _T("File"), _T(".Ext"), FALSE
, wxPATH_MAC
},
884 { _T("device:[dir1.dir2.dir3]file.txt"), _T("device"), _T("dir1.dir2.dir3"), _T("file"), _T("txt"), TRUE
, wxPATH_VMS
},
885 { _T("file.txt"), _T(""), _T(""), _T("file"), _T("txt"), FALSE
, wxPATH_VMS
},
888 static void TestFileNameConstruction()
890 wxPuts(_T("*** testing wxFileName construction ***"));
892 for ( size_t n
= 0; n
< WXSIZEOF(filenames
); n
++ )
894 const FileNameInfo
& fni
= filenames
[n
];
896 wxFileName
fn(fni
.fullname
, fni
.format
);
898 wxString fullname
= fn
.GetFullPath(fni
.format
);
899 if ( fullname
!= fni
.fullname
)
901 wxPrintf(_T("ERROR: fullname should be '%s'\n"), fni
.fullname
);
904 bool isAbsolute
= fn
.IsAbsolute(fni
.format
);
905 wxPrintf(_T("'%s' is %s (%s)\n\t"),
907 isAbsolute
? "absolute" : "relative",
908 isAbsolute
== fni
.isAbsolute
? "ok" : "ERROR");
910 if ( !fn
.Normalize(wxPATH_NORM_ALL
, _T(""), fni
.format
) )
912 wxPuts(_T("ERROR (couldn't be normalized)"));
916 wxPrintf(_T("normalized: '%s'\n"), fn
.GetFullPath(fni
.format
).c_str());
923 static void TestFileNameSplit()
925 wxPuts(_T("*** testing wxFileName splitting ***"));
927 for ( size_t n
= 0; n
< WXSIZEOF(filenames
); n
++ )
929 const FileNameInfo
& fni
= filenames
[n
];
930 wxString volume
, path
, name
, ext
;
931 wxFileName::SplitPath(fni
.fullname
,
932 &volume
, &path
, &name
, &ext
, fni
.format
);
934 wxPrintf(_T("%s -> volume = '%s', path = '%s', name = '%s', ext = '%s'"),
936 volume
.c_str(), path
.c_str(), name
.c_str(), ext
.c_str());
938 if ( volume
!= fni
.volume
)
939 wxPrintf(_T(" (ERROR: volume = '%s')"), fni
.volume
);
940 if ( path
!= fni
.path
)
941 wxPrintf(_T(" (ERROR: path = '%s')"), fni
.path
);
942 if ( name
!= fni
.name
)
943 wxPrintf(_T(" (ERROR: name = '%s')"), fni
.name
);
944 if ( ext
!= fni
.ext
)
945 wxPrintf(_T(" (ERROR: ext = '%s')"), fni
.ext
);
951 static void TestFileNameTemp()
953 wxPuts(_T("*** testing wxFileName temp file creation ***"));
955 static const wxChar
*tmpprefixes
[] =
963 _T("/tmp/foo/bar"), // this one must be an error
967 for ( size_t n
= 0; n
< WXSIZEOF(tmpprefixes
); n
++ )
969 wxString path
= wxFileName::CreateTempFileName(tmpprefixes
[n
]);
972 // "error" is not in upper case because it may be ok
973 wxPrintf(_T("Prefix '%s'\t-> error\n"), tmpprefixes
[n
]);
977 wxPrintf(_T("Prefix '%s'\t-> temp file '%s'\n"),
978 tmpprefixes
[n
], path
.c_str());
980 if ( !wxRemoveFile(path
) )
982 wxLogWarning(_T("Failed to remove temp file '%s'"),
989 static void TestFileNameMakeRelative()
991 wxPuts(_T("*** testing wxFileName::MakeRelativeTo() ***"));
993 for ( size_t n
= 0; n
< WXSIZEOF(filenames
); n
++ )
995 const FileNameInfo
& fni
= filenames
[n
];
997 wxFileName
fn(fni
.fullname
, fni
.format
);
999 // choose the base dir of the same format
1001 switch ( fni
.format
)
1013 // TODO: I don't know how this is supposed to work there
1016 case wxPATH_NATIVE
: // make gcc happy
1018 wxFAIL_MSG( "unexpected path format" );
1021 wxPrintf(_T("'%s' relative to '%s': "),
1022 fn
.GetFullPath(fni
.format
).c_str(), base
.c_str());
1024 if ( !fn
.MakeRelativeTo(base
, fni
.format
) )
1026 wxPuts(_T("unchanged"));
1030 wxPrintf(_T("'%s'\n"), fn
.GetFullPath(fni
.format
).c_str());
1035 static void TestFileNameComparison()
1040 static void TestFileNameOperations()
1045 static void TestFileNameCwd()
1050 #endif // TEST_FILENAME
1052 // ----------------------------------------------------------------------------
1053 // wxFileName time functions
1054 // ----------------------------------------------------------------------------
1056 #ifdef TEST_FILETIME
1058 #include <wx/filename.h>
1059 #include <wx/datetime.h>
1061 static void TestFileGetTimes()
1063 wxFileName
fn(_T("testdata.fc"));
1065 wxDateTime dtAccess
, dtMod
, dtCreate
;
1066 if ( !fn
.GetTimes(&dtAccess
, &dtMod
, &dtCreate
) )
1068 wxPrintf(_T("ERROR: GetTimes() failed.\n"));
1072 static const wxChar
*fmt
= _T("%Y-%b-%d %H:%M:%S");
1074 wxPrintf(_T("File times for '%s':\n"), fn
.GetFullPath().c_str());
1075 wxPrintf(_T("Creation: \t%s\n"), dtCreate
.Format(fmt
).c_str());
1076 wxPrintf(_T("Last read: \t%s\n"), dtAccess
.Format(fmt
).c_str());
1077 wxPrintf(_T("Last write: \t%s\n"), dtMod
.Format(fmt
).c_str());
1081 static void TestFileSetTimes()
1083 wxFileName
fn(_T("testdata.fc"));
1087 wxPrintf(_T("ERROR: Touch() failed.\n"));
1091 #endif // TEST_FILETIME
1093 // ----------------------------------------------------------------------------
1095 // ----------------------------------------------------------------------------
1099 #include "wx/hash.h"
1103 Foo(int n_
) { n
= n_
; count
++; }
1108 static size_t count
;
1111 size_t Foo::count
= 0;
1113 WX_DECLARE_LIST(Foo
, wxListFoos
);
1114 WX_DECLARE_HASH(Foo
, wxListFoos
, wxHashFoos
);
1116 #include "wx/listimpl.cpp"
1118 WX_DEFINE_LIST(wxListFoos
);
1120 static void TestHash()
1122 wxPuts(_T("*** Testing wxHashTable ***\n"));
1126 hash
.DeleteContents(TRUE
);
1128 wxPrintf(_T("Hash created: %u foos in hash, %u foos totally\n"),
1129 hash
.GetCount(), Foo::count
);
1131 static const int hashTestData
[] =
1133 0, 1, 17, -2, 2, 4, -4, 345, 3, 3, 2, 1,
1137 for ( n
= 0; n
< WXSIZEOF(hashTestData
); n
++ )
1139 hash
.Put(hashTestData
[n
], n
, new Foo(n
));
1142 wxPrintf(_T("Hash filled: %u foos in hash, %u foos totally\n"),
1143 hash
.GetCount(), Foo::count
);
1145 wxPuts(_T("Hash access test:"));
1146 for ( n
= 0; n
< WXSIZEOF(hashTestData
); n
++ )
1148 wxPrintf(_T("\tGetting element with key %d, value %d: "),
1149 hashTestData
[n
], n
);
1150 Foo
*foo
= hash
.Get(hashTestData
[n
], n
);
1153 wxPrintf(_T("ERROR, not found.\n"));
1157 wxPrintf(_T("%d (%s)\n"), foo
->n
,
1158 (size_t)foo
->n
== n
? "ok" : "ERROR");
1162 wxPrintf(_T("\nTrying to get an element not in hash: "));
1164 if ( hash
.Get(1234) || hash
.Get(1, 0) )
1166 wxPuts(_T("ERROR: found!"));
1170 wxPuts(_T("ok (not found)"));
1174 wxPrintf(_T("Hash destroyed: %u foos left\n"), Foo::count
);
1179 // ----------------------------------------------------------------------------
1181 // ----------------------------------------------------------------------------
1185 #include "wx/hashmap.h"
1187 // test compilation of basic map types
1188 WX_DECLARE_HASH_MAP( int*, int*, wxPointerHash
, wxPointerEqual
, myPtrHashMap
);
1189 WX_DECLARE_HASH_MAP( long, long, wxIntegerHash
, wxIntegerEqual
, myLongHashMap
);
1190 WX_DECLARE_HASH_MAP( unsigned long, unsigned, wxIntegerHash
, wxIntegerEqual
,
1191 myUnsignedHashMap
);
1192 WX_DECLARE_HASH_MAP( unsigned int, unsigned, wxIntegerHash
, wxIntegerEqual
,
1194 WX_DECLARE_HASH_MAP( int, unsigned, wxIntegerHash
, wxIntegerEqual
,
1196 WX_DECLARE_HASH_MAP( short, unsigned, wxIntegerHash
, wxIntegerEqual
,
1198 WX_DECLARE_HASH_MAP( unsigned short, unsigned, wxIntegerHash
, wxIntegerEqual
,
1202 // WX_DECLARE_HASH_MAP( wxString, wxString, wxStringHash, wxStringEqual,
1203 // myStringHashMap );
1204 WX_DECLARE_STRING_HASH_MAP(wxString
, myStringHashMap
);
1206 typedef myStringHashMap::iterator Itor
;
1208 static void TestHashMap()
1210 wxPuts(_T("*** Testing wxHashMap ***\n"));
1211 myStringHashMap
sh(0); // as small as possible
1214 const size_t count
= 10000;
1216 // init with some data
1217 for( i
= 0; i
< count
; ++i
)
1219 buf
.Printf(wxT("%d"), i
);
1220 sh
[buf
] = wxT("A") + buf
+ wxT("C");
1223 // test that insertion worked
1224 if( sh
.size() != count
)
1226 wxPrintf(_T("*** ERROR: %u ELEMENTS, SHOULD BE %u ***\n"), sh
.size(), count
);
1229 for( i
= 0; i
< count
; ++i
)
1231 buf
.Printf(wxT("%d"), i
);
1232 if( sh
[buf
] != wxT("A") + buf
+ wxT("C") )
1234 wxPrintf(_T("*** ERROR INSERTION BROKEN! STOPPING NOW! ***\n"));
1239 // check that iterators work
1241 for( i
= 0, it
= sh
.begin(); it
!= sh
.end(); ++it
, ++i
)
1245 wxPrintf(_T("*** ERROR ITERATORS DO NOT TERMINATE! STOPPING NOW! ***\n"));
1249 if( it
->second
!= sh
[it
->first
] )
1251 wxPrintf(_T("*** ERROR ITERATORS BROKEN! STOPPING NOW! ***\n"));
1256 if( sh
.size() != i
)
1258 wxPrintf(_T("*** ERROR: %u ELEMENTS ITERATED, SHOULD BE %u ***\n"), i
, count
);
1261 // test copy ctor, assignment operator
1262 myStringHashMap
h1( sh
), h2( 0 );
1265 for( i
= 0, it
= sh
.begin(); it
!= sh
.end(); ++it
, ++i
)
1267 if( h1
[it
->first
] != it
->second
)
1269 wxPrintf(_T("*** ERROR: COPY CTOR BROKEN %s ***\n"), it
->first
.c_str());
1272 if( h2
[it
->first
] != it
->second
)
1274 wxPrintf(_T("*** ERROR: OPERATOR= BROKEN %s ***\n"), it
->first
.c_str());
1279 for( i
= 0; i
< count
; ++i
)
1281 buf
.Printf(wxT("%d"), i
);
1282 size_t sz
= sh
.size();
1284 // test find() and erase(it)
1287 it
= sh
.find( buf
);
1288 if( it
!= sh
.end() )
1292 if( sh
.find( buf
) != sh
.end() )
1294 wxPrintf(_T("*** ERROR: FOUND DELETED ELEMENT %u ***\n"), i
);
1298 wxPrintf(_T("*** ERROR: CANT FIND ELEMENT %u ***\n"), i
);
1303 size_t c
= sh
.erase( buf
);
1305 wxPrintf(_T("*** ERROR: SHOULD RETURN 1 ***\n"));
1307 if( sh
.find( buf
) != sh
.end() )
1309 wxPrintf(_T("*** ERROR: FOUND DELETED ELEMENT %u ***\n"), i
);
1313 // count should decrease
1314 if( sh
.size() != sz
- 1 )
1316 wxPrintf(_T("*** ERROR: COUNT DID NOT DECREASE ***\n"));
1320 wxPrintf(_T("*** Finished testing wxHashMap ***\n"));
1323 #endif // TEST_HASHMAP
1325 // ----------------------------------------------------------------------------
1327 // ----------------------------------------------------------------------------
1331 #include "wx/list.h"
1333 WX_DECLARE_LIST(Bar
, wxListBars
);
1334 #include "wx/listimpl.cpp"
1335 WX_DEFINE_LIST(wxListBars
);
1337 static void TestListCtor()
1339 wxPuts(_T("*** Testing wxList construction ***\n"));
1343 list1
.Append(new Bar(_T("first")));
1344 list1
.Append(new Bar(_T("second")));
1346 wxPrintf(_T("After 1st list creation: %u objects in the list, %u objects total.\n"),
1347 list1
.GetCount(), Bar::GetNumber());
1352 wxPrintf(_T("After 2nd list creation: %u and %u objects in the lists, %u objects total.\n"),
1353 list1
.GetCount(), list2
.GetCount(), Bar::GetNumber());
1355 list1
.DeleteContents(TRUE
);
1358 wxPrintf(_T("After list destruction: %u objects left.\n"), Bar::GetNumber());
1363 // ----------------------------------------------------------------------------
1365 // ----------------------------------------------------------------------------
1369 #include "wx/intl.h"
1370 #include "wx/utils.h" // for wxSetEnv
1372 static wxLocale
gs_localeDefault(wxLANGUAGE_ENGLISH
);
1374 // find the name of the language from its value
1375 static const wxChar
*GetLangName(int lang
)
1377 static const wxChar
*languageNames
[] =
1387 _T("ARABIC_ALGERIA"),
1388 _T("ARABIC_BAHRAIN"),
1391 _T("ARABIC_JORDAN"),
1392 _T("ARABIC_KUWAIT"),
1393 _T("ARABIC_LEBANON"),
1395 _T("ARABIC_MOROCCO"),
1398 _T("ARABIC_SAUDI_ARABIA"),
1401 _T("ARABIC_TUNISIA"),
1408 _T("AZERI_CYRILLIC"),
1423 _T("CHINESE_SIMPLIFIED"),
1424 _T("CHINESE_TRADITIONAL"),
1425 _T("CHINESE_HONGKONG"),
1426 _T("CHINESE_MACAU"),
1427 _T("CHINESE_SINGAPORE"),
1428 _T("CHINESE_TAIWAN"),
1434 _T("DUTCH_BELGIAN"),
1438 _T("ENGLISH_AUSTRALIA"),
1439 _T("ENGLISH_BELIZE"),
1440 _T("ENGLISH_BOTSWANA"),
1441 _T("ENGLISH_CANADA"),
1442 _T("ENGLISH_CARIBBEAN"),
1443 _T("ENGLISH_DENMARK"),
1445 _T("ENGLISH_JAMAICA"),
1446 _T("ENGLISH_NEW_ZEALAND"),
1447 _T("ENGLISH_PHILIPPINES"),
1448 _T("ENGLISH_SOUTH_AFRICA"),
1449 _T("ENGLISH_TRINIDAD"),
1450 _T("ENGLISH_ZIMBABWE"),
1458 _T("FRENCH_BELGIAN"),
1459 _T("FRENCH_CANADIAN"),
1460 _T("FRENCH_LUXEMBOURG"),
1461 _T("FRENCH_MONACO"),
1467 _T("GERMAN_AUSTRIAN"),
1468 _T("GERMAN_BELGIUM"),
1469 _T("GERMAN_LIECHTENSTEIN"),
1470 _T("GERMAN_LUXEMBOURG"),
1488 _T("ITALIAN_SWISS"),
1493 _T("KASHMIRI_INDIA"),
1511 _T("MALAY_BRUNEI_DARUSSALAM"),
1512 _T("MALAY_MALAYSIA"),
1522 _T("NORWEGIAN_BOKMAL"),
1523 _T("NORWEGIAN_NYNORSK"),
1530 _T("PORTUGUESE_BRAZILIAN"),
1533 _T("RHAETO_ROMANCE"),
1536 _T("RUSSIAN_UKRAINE"),
1542 _T("SERBIAN_CYRILLIC"),
1543 _T("SERBIAN_LATIN"),
1544 _T("SERBO_CROATIAN"),
1555 _T("SPANISH_ARGENTINA"),
1556 _T("SPANISH_BOLIVIA"),
1557 _T("SPANISH_CHILE"),
1558 _T("SPANISH_COLOMBIA"),
1559 _T("SPANISH_COSTA_RICA"),
1560 _T("SPANISH_DOMINICAN_REPUBLIC"),
1561 _T("SPANISH_ECUADOR"),
1562 _T("SPANISH_EL_SALVADOR"),
1563 _T("SPANISH_GUATEMALA"),
1564 _T("SPANISH_HONDURAS"),
1565 _T("SPANISH_MEXICAN"),
1566 _T("SPANISH_MODERN"),
1567 _T("SPANISH_NICARAGUA"),
1568 _T("SPANISH_PANAMA"),
1569 _T("SPANISH_PARAGUAY"),
1571 _T("SPANISH_PUERTO_RICO"),
1572 _T("SPANISH_URUGUAY"),
1574 _T("SPANISH_VENEZUELA"),
1578 _T("SWEDISH_FINLAND"),
1596 _T("URDU_PAKISTAN"),
1598 _T("UZBEK_CYRILLIC"),
1611 if ( (size_t)lang
< WXSIZEOF(languageNames
) )
1612 return languageNames
[lang
];
1614 return _T("INVALID");
1617 static void TestDefaultLang()
1619 wxPuts(_T("*** Testing wxLocale::GetSystemLanguage ***"));
1621 static const wxChar
*langStrings
[] =
1623 NULL
, // system default
1630 _T("de_DE.iso88591"),
1632 _T("?"), // invalid lang spec
1633 _T("klingonese"), // I bet on some systems it does exist...
1636 wxPrintf(_T("The default system encoding is %s (%d)\n"),
1637 wxLocale::GetSystemEncodingName().c_str(),
1638 wxLocale::GetSystemEncoding());
1640 for ( size_t n
= 0; n
< WXSIZEOF(langStrings
); n
++ )
1642 const wxChar
*langStr
= langStrings
[n
];
1645 // FIXME: this doesn't do anything at all under Windows, we need
1646 // to create a new wxLocale!
1647 wxSetEnv(_T("LC_ALL"), langStr
);
1650 int lang
= gs_localeDefault
.GetSystemLanguage();
1651 wxPrintf(_T("Locale for '%s' is %s.\n"),
1652 langStr
? langStr
: _T("system default"), GetLangName(lang
));
1656 #endif // TEST_LOCALE
1658 // ----------------------------------------------------------------------------
1660 // ----------------------------------------------------------------------------
1664 #include "wx/mimetype.h"
1666 static void TestMimeEnum()
1668 wxPuts(_T("*** Testing wxMimeTypesManager::EnumAllFileTypes() ***\n"));
1670 wxArrayString mimetypes
;
1672 size_t count
= wxTheMimeTypesManager
->EnumAllFileTypes(mimetypes
);
1674 wxPrintf(_T("*** All %u known filetypes: ***\n"), count
);
1679 for ( size_t n
= 0; n
< count
; n
++ )
1681 wxFileType
*filetype
=
1682 wxTheMimeTypesManager
->GetFileTypeFromMimeType(mimetypes
[n
]);
1685 wxPrintf(_T("nothing known about the filetype '%s'!\n"),
1686 mimetypes
[n
].c_str());
1690 filetype
->GetDescription(&desc
);
1691 filetype
->GetExtensions(exts
);
1693 filetype
->GetIcon(NULL
);
1696 for ( size_t e
= 0; e
< exts
.GetCount(); e
++ )
1699 extsAll
<< _T(", ");
1703 wxPrintf(_T("\t%s: %s (%s)\n"),
1704 mimetypes
[n
].c_str(), desc
.c_str(), extsAll
.c_str());
1710 static void TestMimeOverride()
1712 wxPuts(_T("*** Testing wxMimeTypesManager additional files loading ***\n"));
1714 static const wxChar
*mailcap
= _T("/tmp/mailcap");
1715 static const wxChar
*mimetypes
= _T("/tmp/mime.types");
1717 if ( wxFile::Exists(mailcap
) )
1718 wxPrintf(_T("Loading mailcap from '%s': %s\n"),
1720 wxTheMimeTypesManager
->ReadMailcap(mailcap
) ? _T("ok") : _T("ERROR"));
1722 wxPrintf(_T("WARN: mailcap file '%s' doesn't exist, not loaded.\n"),
1725 if ( wxFile::Exists(mimetypes
) )
1726 wxPrintf(_T("Loading mime.types from '%s': %s\n"),
1728 wxTheMimeTypesManager
->ReadMimeTypes(mimetypes
) ? _T("ok") : _T("ERROR"));
1730 wxPrintf(_T("WARN: mime.types file '%s' doesn't exist, not loaded.\n"),
1736 static void TestMimeFilename()
1738 wxPuts(_T("*** Testing MIME type from filename query ***\n"));
1740 static const wxChar
*filenames
[] =
1748 for ( size_t n
= 0; n
< WXSIZEOF(filenames
); n
++ )
1750 const wxString fname
= filenames
[n
];
1751 wxString ext
= fname
.AfterLast(_T('.'));
1752 wxFileType
*ft
= wxTheMimeTypesManager
->GetFileTypeFromExtension(ext
);
1755 wxPrintf(_T("WARNING: extension '%s' is unknown.\n"), ext
.c_str());
1760 if ( !ft
->GetDescription(&desc
) )
1761 desc
= _T("<no description>");
1764 if ( !ft
->GetOpenCommand(&cmd
,
1765 wxFileType::MessageParameters(fname
, _T(""))) )
1766 cmd
= _T("<no command available>");
1768 wxPrintf(_T("To open %s (%s) do '%s'.\n"),
1769 fname
.c_str(), desc
.c_str(), cmd
.c_str());
1778 static void TestMimeAssociate()
1780 wxPuts(_T("*** Testing creation of filetype association ***\n"));
1782 wxFileTypeInfo
ftInfo(
1783 _T("application/x-xyz"),
1784 _T("xyzview '%s'"), // open cmd
1785 _T(""), // print cmd
1786 _T("XYZ File"), // description
1787 _T(".xyz"), // extensions
1788 NULL
// end of extensions
1790 ftInfo
.SetShortDesc(_T("XYZFile")); // used under Win32 only
1792 wxFileType
*ft
= wxTheMimeTypesManager
->Associate(ftInfo
);
1795 wxPuts(_T("ERROR: failed to create association!"));
1799 // TODO: read it back
1808 // ----------------------------------------------------------------------------
1809 // misc information functions
1810 // ----------------------------------------------------------------------------
1812 #ifdef TEST_INFO_FUNCTIONS
1814 #include "wx/utils.h"
1816 static void TestDiskInfo()
1818 wxPuts(_T("*** Testing wxGetDiskSpace() ***"));
1822 wxChar pathname
[128];
1823 wxPrintf(_T("\nEnter a directory name: "));
1824 if ( !wxFgets(pathname
, WXSIZEOF(pathname
), stdin
) )
1827 // kill the last '\n'
1828 pathname
[wxStrlen(pathname
) - 1] = 0;
1830 wxLongLong total
, free
;
1831 if ( !wxGetDiskSpace(pathname
, &total
, &free
) )
1833 wxPuts(_T("ERROR: wxGetDiskSpace failed."));
1837 wxPrintf(_T("%sKb total, %sKb free on '%s'.\n"),
1838 (total
/ 1024).ToString().c_str(),
1839 (free
/ 1024).ToString().c_str(),
1845 static void TestOsInfo()
1847 wxPuts(_T("*** Testing OS info functions ***\n"));
1850 wxGetOsVersion(&major
, &minor
);
1851 wxPrintf(_T("Running under: %s, version %d.%d\n"),
1852 wxGetOsDescription().c_str(), major
, minor
);
1854 wxPrintf(_T("%ld free bytes of memory left.\n"), wxGetFreeMemory());
1856 wxPrintf(_T("Host name is %s (%s).\n"),
1857 wxGetHostName().c_str(), wxGetFullHostName().c_str());
1862 static void TestUserInfo()
1864 wxPuts(_T("*** Testing user info functions ***\n"));
1866 wxPrintf(_T("User id is:\t%s\n"), wxGetUserId().c_str());
1867 wxPrintf(_T("User name is:\t%s\n"), wxGetUserName().c_str());
1868 wxPrintf(_T("Home dir is:\t%s\n"), wxGetHomeDir().c_str());
1869 wxPrintf(_T("Email address:\t%s\n"), wxGetEmailAddress().c_str());
1874 #endif // TEST_INFO_FUNCTIONS
1876 // ----------------------------------------------------------------------------
1878 // ----------------------------------------------------------------------------
1880 #ifdef TEST_LONGLONG
1882 #include "wx/longlong.h"
1883 #include "wx/timer.h"
1885 // make a 64 bit number from 4 16 bit ones
1886 #define MAKE_LL(x1, x2, x3, x4) wxLongLong((x1 << 16) | x2, (x3 << 16) | x3)
1888 // get a random 64 bit number
1889 #define RAND_LL() MAKE_LL(rand(), rand(), rand(), rand())
1891 static const long testLongs
[] =
1902 #if wxUSE_LONGLONG_WX
1903 inline bool operator==(const wxLongLongWx
& a
, const wxLongLongNative
& b
)
1904 { return a
.GetHi() == b
.GetHi() && a
.GetLo() == b
.GetLo(); }
1905 inline bool operator==(const wxLongLongNative
& a
, const wxLongLongWx
& b
)
1906 { return a
.GetHi() == b
.GetHi() && a
.GetLo() == b
.GetLo(); }
1907 #endif // wxUSE_LONGLONG_WX
1909 static void TestSpeed()
1911 static const long max
= 100000000;
1918 for ( n
= 0; n
< max
; n
++ )
1923 wxPrintf(_T("Summing longs took %ld milliseconds.\n"), sw
.Time());
1926 #if wxUSE_LONGLONG_NATIVE
1931 for ( n
= 0; n
< max
; n
++ )
1936 wxPrintf(_T("Summing wxLongLong_t took %ld milliseconds.\n"), sw
.Time());
1938 #endif // wxUSE_LONGLONG_NATIVE
1944 for ( n
= 0; n
< max
; n
++ )
1949 wxPrintf(_T("Summing wxLongLongs took %ld milliseconds.\n"), sw
.Time());
1953 static void TestLongLongConversion()
1955 wxPuts(_T("*** Testing wxLongLong conversions ***\n"));
1959 for ( size_t n
= 0; n
< 100000; n
++ )
1963 #if wxUSE_LONGLONG_NATIVE
1964 wxLongLongNative
b(a
.GetHi(), a
.GetLo());
1966 wxASSERT_MSG( a
== b
, "conversions failure" );
1968 wxPuts(_T("Can't do it without native long long type, test skipped."));
1971 #endif // wxUSE_LONGLONG_NATIVE
1973 if ( !(nTested
% 1000) )
1982 wxPuts(_T(" done!"));
1985 static void TestMultiplication()
1987 wxPuts(_T("*** Testing wxLongLong multiplication ***\n"));
1991 for ( size_t n
= 0; n
< 100000; n
++ )
1996 #if wxUSE_LONGLONG_NATIVE
1997 wxLongLongNative
aa(a
.GetHi(), a
.GetLo());
1998 wxLongLongNative
bb(b
.GetHi(), b
.GetLo());
2000 wxASSERT_MSG( a
*b
== aa
*bb
, "multiplication failure" );
2001 #else // !wxUSE_LONGLONG_NATIVE
2002 wxPuts(_T("Can't do it without native long long type, test skipped."));
2005 #endif // wxUSE_LONGLONG_NATIVE
2007 if ( !(nTested
% 1000) )
2016 wxPuts(_T(" done!"));
2019 static void TestDivision()
2021 wxPuts(_T("*** Testing wxLongLong division ***\n"));
2025 for ( size_t n
= 0; n
< 100000; n
++ )
2027 // get a random wxLongLong (shifting by 12 the MSB ensures that the
2028 // multiplication will not overflow)
2029 wxLongLong ll
= MAKE_LL((rand() >> 12), rand(), rand(), rand());
2031 // get a random (but non null) long (not wxLongLong for now) to divide
2043 #if wxUSE_LONGLONG_NATIVE
2044 wxLongLongNative
m(ll
.GetHi(), ll
.GetLo());
2046 wxLongLongNative p
= m
/ l
, s
= m
% l
;
2047 wxASSERT_MSG( q
== p
&& r
== s
, "division failure" );
2048 #else // !wxUSE_LONGLONG_NATIVE
2049 // verify the result
2050 wxASSERT_MSG( ll
== q
*l
+ r
, "division failure" );
2051 #endif // wxUSE_LONGLONG_NATIVE
2053 if ( !(nTested
% 1000) )
2062 wxPuts(_T(" done!"));
2065 static void TestAddition()
2067 wxPuts(_T("*** Testing wxLongLong addition ***\n"));
2071 for ( size_t n
= 0; n
< 100000; n
++ )
2077 #if wxUSE_LONGLONG_NATIVE
2078 wxASSERT_MSG( c
== wxLongLongNative(a
.GetHi(), a
.GetLo()) +
2079 wxLongLongNative(b
.GetHi(), b
.GetLo()),
2080 "addition failure" );
2081 #else // !wxUSE_LONGLONG_NATIVE
2082 wxASSERT_MSG( c
- b
== a
, "addition failure" );
2083 #endif // wxUSE_LONGLONG_NATIVE
2085 if ( !(nTested
% 1000) )
2094 wxPuts(_T(" done!"));
2097 static void TestBitOperations()
2099 wxPuts(_T("*** Testing wxLongLong bit operation ***\n"));
2103 for ( size_t n
= 0; n
< 100000; n
++ )
2107 #if wxUSE_LONGLONG_NATIVE
2108 for ( size_t n
= 0; n
< 33; n
++ )
2111 #else // !wxUSE_LONGLONG_NATIVE
2112 wxPuts(_T("Can't do it without native long long type, test skipped."));
2115 #endif // wxUSE_LONGLONG_NATIVE
2117 if ( !(nTested
% 1000) )
2126 wxPuts(_T(" done!"));
2129 static void TestLongLongComparison()
2131 #if wxUSE_LONGLONG_WX
2132 wxPuts(_T("*** Testing wxLongLong comparison ***\n"));
2134 static const long ls
[2] =
2140 wxLongLongWx lls
[2];
2144 for ( size_t n
= 0; n
< WXSIZEOF(testLongs
); n
++ )
2148 for ( size_t m
= 0; m
< WXSIZEOF(lls
); m
++ )
2150 res
= lls
[m
] > testLongs
[n
];
2151 wxPrintf(_T("0x%lx > 0x%lx is %s (%s)\n"),
2152 ls
[m
], testLongs
[n
], res
? "true" : "false",
2153 res
== (ls
[m
] > testLongs
[n
]) ? "ok" : "ERROR");
2155 res
= lls
[m
] < testLongs
[n
];
2156 wxPrintf(_T("0x%lx < 0x%lx is %s (%s)\n"),
2157 ls
[m
], testLongs
[n
], res
? "true" : "false",
2158 res
== (ls
[m
] < testLongs
[n
]) ? "ok" : "ERROR");
2160 res
= lls
[m
] == testLongs
[n
];
2161 wxPrintf(_T("0x%lx == 0x%lx is %s (%s)\n"),
2162 ls
[m
], testLongs
[n
], res
? "true" : "false",
2163 res
== (ls
[m
] == testLongs
[n
]) ? "ok" : "ERROR");
2166 #endif // wxUSE_LONGLONG_WX
2169 static void TestLongLongPrint()
2171 wxPuts(_T("*** Testing wxLongLong printing ***\n"));
2173 for ( size_t n
= 0; n
< WXSIZEOF(testLongs
); n
++ )
2175 wxLongLong ll
= testLongs
[n
];
2176 wxPrintf(_T("%ld == %s\n"), testLongs
[n
], ll
.ToString().c_str());
2179 wxLongLong
ll(0x12345678, 0x87654321);
2180 wxPrintf(_T("0x1234567887654321 = %s\n"), ll
.ToString().c_str());
2183 wxPrintf(_T("-0x1234567887654321 = %s\n"), ll
.ToString().c_str());
2189 #endif // TEST_LONGLONG
2191 // ----------------------------------------------------------------------------
2193 // ----------------------------------------------------------------------------
2195 #ifdef TEST_PATHLIST
2197 static void TestPathList()
2199 wxPuts(_T("*** Testing wxPathList ***\n"));
2201 wxPathList pathlist
;
2202 pathlist
.AddEnvList("PATH");
2203 wxString path
= pathlist
.FindValidPath("ls");
2206 wxPrintf(_T("ERROR: command not found in the path.\n"));
2210 wxPrintf(_T("Command found in the path as '%s'.\n"), path
.c_str());
2214 #endif // TEST_PATHLIST
2216 // ----------------------------------------------------------------------------
2217 // regular expressions
2218 // ----------------------------------------------------------------------------
2222 #include "wx/regex.h"
2224 static void TestRegExCompile()
2226 wxPuts(_T("*** Testing RE compilation ***\n"));
2228 static struct RegExCompTestData
2230 const wxChar
*pattern
;
2232 } regExCompTestData
[] =
2234 { _T("foo"), TRUE
},
2235 { _T("foo("), FALSE
},
2236 { _T("foo(bar"), FALSE
},
2237 { _T("foo(bar)"), TRUE
},
2238 { _T("foo["), FALSE
},
2239 { _T("foo[bar"), FALSE
},
2240 { _T("foo[bar]"), TRUE
},
2241 { _T("foo{"), TRUE
},
2242 { _T("foo{1"), FALSE
},
2243 { _T("foo{bar"), TRUE
},
2244 { _T("foo{1}"), TRUE
},
2245 { _T("foo{1,2}"), TRUE
},
2246 { _T("foo{bar}"), TRUE
},
2247 { _T("foo*"), TRUE
},
2248 { _T("foo**"), FALSE
},
2249 { _T("foo+"), TRUE
},
2250 { _T("foo++"), FALSE
},
2251 { _T("foo?"), TRUE
},
2252 { _T("foo??"), FALSE
},
2253 { _T("foo?+"), FALSE
},
2257 for ( size_t n
= 0; n
< WXSIZEOF(regExCompTestData
); n
++ )
2259 const RegExCompTestData
& data
= regExCompTestData
[n
];
2260 bool ok
= re
.Compile(data
.pattern
);
2262 wxPrintf(_T("'%s' is %sa valid RE (%s)\n"),
2264 ok
? _T("") : _T("not "),
2265 ok
== data
.correct
? _T("ok") : _T("ERROR"));
2269 static void TestRegExMatch()
2271 wxPuts(_T("*** Testing RE matching ***\n"));
2273 static struct RegExMatchTestData
2275 const wxChar
*pattern
;
2278 } regExMatchTestData
[] =
2280 { _T("foo"), _T("bar"), FALSE
},
2281 { _T("foo"), _T("foobar"), TRUE
},
2282 { _T("^foo"), _T("foobar"), TRUE
},
2283 { _T("^foo"), _T("barfoo"), FALSE
},
2284 { _T("bar$"), _T("barbar"), TRUE
},
2285 { _T("bar$"), _T("barbar "), FALSE
},
2288 for ( size_t n
= 0; n
< WXSIZEOF(regExMatchTestData
); n
++ )
2290 const RegExMatchTestData
& data
= regExMatchTestData
[n
];
2292 wxRegEx
re(data
.pattern
);
2293 bool ok
= re
.Matches(data
.text
);
2295 wxPrintf(_T("'%s' %s %s (%s)\n"),
2297 ok
? _T("matches") : _T("doesn't match"),
2299 ok
== data
.correct
? _T("ok") : _T("ERROR"));
2303 static void TestRegExSubmatch()
2305 wxPuts(_T("*** Testing RE subexpressions ***\n"));
2307 wxRegEx
re(_T("([[:alpha:]]+) ([[:alpha:]]+) ([[:digit:]]+).*([[:digit:]]+)$"));
2308 if ( !re
.IsValid() )
2310 wxPuts(_T("ERROR: compilation failed."));
2314 wxString text
= _T("Fri Jul 13 18:37:52 CEST 2001");
2316 if ( !re
.Matches(text
) )
2318 wxPuts(_T("ERROR: match expected."));
2322 wxPrintf(_T("Entire match: %s\n"), re
.GetMatch(text
).c_str());
2324 wxPrintf(_T("Date: %s/%s/%s, wday: %s\n"),
2325 re
.GetMatch(text
, 3).c_str(),
2326 re
.GetMatch(text
, 2).c_str(),
2327 re
.GetMatch(text
, 4).c_str(),
2328 re
.GetMatch(text
, 1).c_str());
2332 static void TestRegExReplacement()
2334 wxPuts(_T("*** Testing RE replacement ***"));
2336 static struct RegExReplTestData
2340 const wxChar
*result
;
2342 } regExReplTestData
[] =
2344 { _T("foo123"), _T("bar"), _T("bar"), 1 },
2345 { _T("foo123"), _T("\\2\\1"), _T("123foo"), 1 },
2346 { _T("foo_123"), _T("\\2\\1"), _T("123foo"), 1 },
2347 { _T("123foo"), _T("bar"), _T("123foo"), 0 },
2348 { _T("123foo456foo"), _T("&&"), _T("123foo456foo456foo"), 1 },
2349 { _T("foo123foo123"), _T("bar"), _T("barbar"), 2 },
2350 { _T("foo123_foo456_foo789"), _T("bar"), _T("bar_bar_bar"), 3 },
2353 const wxChar
*pattern
= _T("([a-z]+)[^0-9]*([0-9]+)");
2354 wxRegEx
re(pattern
);
2356 wxPrintf(_T("Using pattern '%s' for replacement.\n"), pattern
);
2358 for ( size_t n
= 0; n
< WXSIZEOF(regExReplTestData
); n
++ )
2360 const RegExReplTestData
& data
= regExReplTestData
[n
];
2362 wxString text
= data
.text
;
2363 size_t nRepl
= re
.Replace(&text
, data
.repl
);
2365 wxPrintf(_T("%s =~ s/RE/%s/g: %u match%s, result = '%s' ("),
2366 data
.text
, data
.repl
,
2367 nRepl
, nRepl
== 1 ? _T("") : _T("es"),
2369 if ( text
== data
.result
&& nRepl
== data
.count
)
2375 wxPrintf(_T("ERROR: should be %u and '%s')\n"),
2376 data
.count
, data
.result
);
2381 static void TestRegExInteractive()
2383 wxPuts(_T("*** Testing RE interactively ***"));
2387 wxChar pattern
[128];
2388 wxPrintf(_T("\nEnter a pattern: "));
2389 if ( !wxFgets(pattern
, WXSIZEOF(pattern
), stdin
) )
2392 // kill the last '\n'
2393 pattern
[wxStrlen(pattern
) - 1] = 0;
2396 if ( !re
.Compile(pattern
) )
2404 wxPrintf(_T("Enter text to match: "));
2405 if ( !wxFgets(text
, WXSIZEOF(text
), stdin
) )
2408 // kill the last '\n'
2409 text
[wxStrlen(text
) - 1] = 0;
2411 if ( !re
.Matches(text
) )
2413 wxPrintf(_T("No match.\n"));
2417 wxPrintf(_T("Pattern matches at '%s'\n"), re
.GetMatch(text
).c_str());
2420 for ( size_t n
= 1; ; n
++ )
2422 if ( !re
.GetMatch(&start
, &len
, n
) )
2427 wxPrintf(_T("Subexpr %u matched '%s'\n"),
2428 n
, wxString(text
+ start
, len
).c_str());
2435 #endif // TEST_REGEX
2437 // ----------------------------------------------------------------------------
2439 // ----------------------------------------------------------------------------
2449 static void TestDbOpen()
2457 // ----------------------------------------------------------------------------
2458 // registry and related stuff
2459 // ----------------------------------------------------------------------------
2461 // this is for MSW only
2464 #undef TEST_REGISTRY
2469 #include "wx/confbase.h"
2470 #include "wx/msw/regconf.h"
2472 static void TestRegConfWrite()
2474 wxRegConfig
regconf(_T("console"), _T("wxwindows"));
2475 regconf
.Write(_T("Hello"), wxString(_T("world")));
2478 #endif // TEST_REGCONF
2480 #ifdef TEST_REGISTRY
2482 #include "wx/msw/registry.h"
2484 // I chose this one because I liked its name, but it probably only exists under
2486 static const wxChar
*TESTKEY
=
2487 _T("HKEY_LOCAL_MACHINE\\SYSTEM\\ControlSet001\\Control\\CrashControl");
2489 static void TestRegistryRead()
2491 wxPuts(_T("*** testing registry reading ***"));
2493 wxRegKey
key(TESTKEY
);
2494 wxPrintf(_T("The test key name is '%s'.\n"), key
.GetName().c_str());
2497 wxPuts(_T("ERROR: test key can't be opened, aborting test."));
2502 size_t nSubKeys
, nValues
;
2503 if ( key
.GetKeyInfo(&nSubKeys
, NULL
, &nValues
, NULL
) )
2505 wxPrintf(_T("It has %u subkeys and %u values.\n"), nSubKeys
, nValues
);
2508 wxPrintf(_T("Enumerating values:\n"));
2512 bool cont
= key
.GetFirstValue(value
, dummy
);
2515 wxPrintf(_T("Value '%s': type "), value
.c_str());
2516 switch ( key
.GetValueType(value
) )
2518 case wxRegKey::Type_None
: wxPrintf(_T("ERROR (none)")); break;
2519 case wxRegKey::Type_String
: wxPrintf(_T("SZ")); break;
2520 case wxRegKey::Type_Expand_String
: wxPrintf(_T("EXPAND_SZ")); break;
2521 case wxRegKey::Type_Binary
: wxPrintf(_T("BINARY")); break;
2522 case wxRegKey::Type_Dword
: wxPrintf(_T("DWORD")); break;
2523 case wxRegKey::Type_Multi_String
: wxPrintf(_T("MULTI_SZ")); break;
2524 default: wxPrintf(_T("other (unknown)")); break;
2527 wxPrintf(_T(", value = "));
2528 if ( key
.IsNumericValue(value
) )
2531 key
.QueryValue(value
, &val
);
2532 wxPrintf(_T("%ld"), val
);
2537 key
.QueryValue(value
, val
);
2538 wxPrintf(_T("'%s'"), val
.c_str());
2540 key
.QueryRawValue(value
, val
);
2541 wxPrintf(_T(" (raw value '%s')"), val
.c_str());
2546 cont
= key
.GetNextValue(value
, dummy
);
2550 static void TestRegistryAssociation()
2553 The second call to deleteself genertaes an error message, with a
2554 messagebox saying .flo is crucial to system operation, while the .ddf
2555 call also fails, but with no error message
2560 key
.SetName("HKEY_CLASSES_ROOT\\.ddf" );
2562 key
= "ddxf_auto_file" ;
2563 key
.SetName("HKEY_CLASSES_ROOT\\.flo" );
2565 key
= "ddxf_auto_file" ;
2566 key
.SetName("HKEY_CLASSES_ROOT\\ddxf_auto_file\\DefaultIcon");
2569 key
.SetName("HKEY_CLASSES_ROOT\\ddxf_auto_file\\shell\\open\\command");
2571 key
= "program \"%1\"" ;
2573 key
.SetName("HKEY_CLASSES_ROOT\\.ddf" );
2575 key
.SetName("HKEY_CLASSES_ROOT\\.flo" );
2577 key
.SetName("HKEY_CLASSES_ROOT\\ddxf_auto_file\\DefaultIcon");
2579 key
.SetName("HKEY_CLASSES_ROOT\\ddxf_auto_file\\shell\\open\\command");
2583 #endif // TEST_REGISTRY
2585 // ----------------------------------------------------------------------------
2587 // ----------------------------------------------------------------------------
2591 #include "wx/socket.h"
2592 #include "wx/protocol/protocol.h"
2593 #include "wx/protocol/http.h"
2595 static void TestSocketServer()
2597 wxPuts(_T("*** Testing wxSocketServer ***\n"));
2599 static const int PORT
= 3000;
2604 wxSocketServer
*server
= new wxSocketServer(addr
);
2605 if ( !server
->Ok() )
2607 wxPuts(_T("ERROR: failed to bind"));
2614 wxPrintf(_T("Server: waiting for connection on port %d...\n"), PORT
);
2616 wxSocketBase
*socket
= server
->Accept();
2619 wxPuts(_T("ERROR: wxSocketServer::Accept() failed."));
2623 wxPuts(_T("Server: got a client."));
2625 server
->SetTimeout(60); // 1 min
2627 while ( socket
->IsConnected() )
2630 wxChar ch
= _T('\0');
2633 if ( socket
->Read(&ch
, sizeof(ch
)).Error() )
2635 // don't log error if the client just close the connection
2636 if ( socket
->IsConnected() )
2638 wxPuts(_T("ERROR: in wxSocket::Read."));
2658 wxPrintf(_T("Server: got '%s'.\n"), s
.c_str());
2659 if ( s
== _T("bye") )
2666 socket
->Write(s
.MakeUpper().c_str(), s
.length());
2667 socket
->Write("\r\n", 2);
2668 wxPrintf(_T("Server: wrote '%s'.\n"), s
.c_str());
2671 wxPuts(_T("Server: lost a client."));
2676 // same as "delete server" but is consistent with GUI programs
2680 static void TestSocketClient()
2682 wxPuts(_T("*** Testing wxSocketClient ***\n"));
2684 static const wxChar
*hostname
= _T("www.wxwindows.org");
2687 addr
.Hostname(hostname
);
2690 wxPrintf(_T("--- Attempting to connect to %s:80...\n"), hostname
);
2692 wxSocketClient client
;
2693 if ( !client
.Connect(addr
) )
2695 wxPrintf(_T("ERROR: failed to connect to %s\n"), hostname
);
2699 wxPrintf(_T("--- Connected to %s:%u...\n"),
2700 addr
.Hostname().c_str(), addr
.Service());
2704 // could use simply "GET" here I suppose
2706 wxString::Format(_T("GET http://%s/\r\n"), hostname
);
2707 client
.Write(cmdGet
, cmdGet
.length());
2708 wxPrintf(_T("--- Sent command '%s' to the server\n"),
2709 MakePrintable(cmdGet
).c_str());
2710 client
.Read(buf
, WXSIZEOF(buf
));
2711 wxPrintf(_T("--- Server replied:\n%s"), buf
);
2715 #endif // TEST_SOCKETS
2717 // ----------------------------------------------------------------------------
2719 // ----------------------------------------------------------------------------
2723 #include "wx/protocol/ftp.h"
2727 #define FTP_ANONYMOUS
2729 #ifdef FTP_ANONYMOUS
2730 static const wxChar
*directory
= _T("/pub");
2731 static const wxChar
*filename
= _T("welcome.msg");
2733 static const wxChar
*directory
= _T("/etc");
2734 static const wxChar
*filename
= _T("issue");
2737 static bool TestFtpConnect()
2739 wxPuts(_T("*** Testing FTP connect ***"));
2741 #ifdef FTP_ANONYMOUS
2742 static const wxChar
*hostname
= _T("ftp.wxwindows.org");
2744 wxPrintf(_T("--- Attempting to connect to %s:21 anonymously...\n"), hostname
);
2745 #else // !FTP_ANONYMOUS
2746 static const wxChar
*hostname
= "localhost";
2749 wxFgets(user
, WXSIZEOF(user
), stdin
);
2750 user
[wxStrlen(user
) - 1] = '\0'; // chop off '\n'
2753 wxChar password
[256];
2754 wxPrintf(_T("Password for %s: "), password
);
2755 wxFgets(password
, WXSIZEOF(password
), stdin
);
2756 password
[wxStrlen(password
) - 1] = '\0'; // chop off '\n'
2757 ftp
.SetPassword(password
);
2759 wxPrintf(_T("--- Attempting to connect to %s:21 as %s...\n"), hostname
, user
);
2760 #endif // FTP_ANONYMOUS/!FTP_ANONYMOUS
2762 if ( !ftp
.Connect(hostname
) )
2764 wxPrintf(_T("ERROR: failed to connect to %s\n"), hostname
);
2770 wxPrintf(_T("--- Connected to %s, current directory is '%s'\n"),
2771 hostname
, ftp
.Pwd().c_str());
2777 // test (fixed?) wxFTP bug with wu-ftpd >= 2.6.0?
2778 static void TestFtpWuFtpd()
2781 static const wxChar
*hostname
= _T("ftp.eudora.com");
2782 if ( !ftp
.Connect(hostname
) )
2784 wxPrintf(_T("ERROR: failed to connect to %s\n"), hostname
);
2788 static const wxChar
*filename
= _T("eudora/pubs/draft-gellens-submit-09.txt");
2789 wxInputStream
*in
= ftp
.GetInputStream(filename
);
2792 wxPrintf(_T("ERROR: couldn't get input stream for %s\n"), filename
);
2796 size_t size
= in
->StreamSize();
2797 wxPrintf(_T("Reading file %s (%u bytes)..."), filename
, size
);
2799 wxChar
*data
= new wxChar
[size
];
2800 if ( !in
->Read(data
, size
) )
2802 wxPuts(_T("ERROR: read error"));
2806 wxPrintf(_T("Successfully retrieved the file.\n"));
2815 static void TestFtpList()
2817 wxPuts(_T("*** Testing wxFTP file listing ***\n"));
2820 if ( !ftp
.ChDir(directory
) )
2822 wxPrintf(_T("ERROR: failed to cd to %s\n"), directory
);
2825 wxPrintf(_T("Current directory is '%s'\n"), ftp
.Pwd().c_str());
2827 // test NLIST and LIST
2828 wxArrayString files
;
2829 if ( !ftp
.GetFilesList(files
) )
2831 wxPuts(_T("ERROR: failed to get NLIST of files"));
2835 wxPrintf(_T("Brief list of files under '%s':\n"), ftp
.Pwd().c_str());
2836 size_t count
= files
.GetCount();
2837 for ( size_t n
= 0; n
< count
; n
++ )
2839 wxPrintf(_T("\t%s\n"), files
[n
].c_str());
2841 wxPuts(_T("End of the file list"));
2844 if ( !ftp
.GetDirList(files
) )
2846 wxPuts(_T("ERROR: failed to get LIST of files"));
2850 wxPrintf(_T("Detailed list of files under '%s':\n"), ftp
.Pwd().c_str());
2851 size_t count
= files
.GetCount();
2852 for ( size_t n
= 0; n
< count
; n
++ )
2854 wxPrintf(_T("\t%s\n"), files
[n
].c_str());
2856 wxPuts(_T("End of the file list"));
2859 if ( !ftp
.ChDir(_T("..")) )
2861 wxPuts(_T("ERROR: failed to cd to .."));
2864 wxPrintf(_T("Current directory is '%s'\n"), ftp
.Pwd().c_str());
2867 static void TestFtpDownload()
2869 wxPuts(_T("*** Testing wxFTP download ***\n"));
2872 wxInputStream
*in
= ftp
.GetInputStream(filename
);
2875 wxPrintf(_T("ERROR: couldn't get input stream for %s\n"), filename
);
2879 size_t size
= in
->StreamSize();
2880 wxPrintf(_T("Reading file %s (%u bytes)..."), filename
, size
);
2883 wxChar
*data
= new wxChar
[size
];
2884 if ( !in
->Read(data
, size
) )
2886 wxPuts(_T("ERROR: read error"));
2890 wxPrintf(_T("\nContents of %s:\n%s\n"), filename
, data
);
2898 static void TestFtpFileSize()
2900 wxPuts(_T("*** Testing FTP SIZE command ***"));
2902 if ( !ftp
.ChDir(directory
) )
2904 wxPrintf(_T("ERROR: failed to cd to %s\n"), directory
);
2907 wxPrintf(_T("Current directory is '%s'\n"), ftp
.Pwd().c_str());
2909 if ( ftp
.FileExists(filename
) )
2911 int size
= ftp
.GetFileSize(filename
);
2913 wxPrintf(_T("ERROR: couldn't get size of '%s'\n"), filename
);
2915 wxPrintf(_T("Size of '%s' is %d bytes.\n"), filename
, size
);
2919 wxPrintf(_T("ERROR: '%s' doesn't exist\n"), filename
);
2923 static void TestFtpMisc()
2925 wxPuts(_T("*** Testing miscellaneous wxFTP functions ***"));
2927 if ( ftp
.SendCommand("STAT") != '2' )
2929 wxPuts(_T("ERROR: STAT failed"));
2933 wxPrintf(_T("STAT returned:\n\n%s\n"), ftp
.GetLastResult().c_str());
2936 if ( ftp
.SendCommand("HELP SITE") != '2' )
2938 wxPuts(_T("ERROR: HELP SITE failed"));
2942 wxPrintf(_T("The list of site-specific commands:\n\n%s\n"),
2943 ftp
.GetLastResult().c_str());
2947 static void TestFtpInteractive()
2949 wxPuts(_T("\n*** Interactive wxFTP test ***"));
2955 wxPrintf(_T("Enter FTP command: "));
2956 if ( !wxFgets(buf
, WXSIZEOF(buf
), stdin
) )
2959 // kill the last '\n'
2960 buf
[wxStrlen(buf
) - 1] = 0;
2962 // special handling of LIST and NLST as they require data connection
2963 wxString
start(buf
, 4);
2965 if ( start
== "LIST" || start
== "NLST" )
2968 if ( wxStrlen(buf
) > 4 )
2971 wxArrayString files
;
2972 if ( !ftp
.GetList(files
, wildcard
, start
== "LIST") )
2974 wxPrintf(_T("ERROR: failed to get %s of files\n"), start
.c_str());
2978 wxPrintf(_T("--- %s of '%s' under '%s':\n"),
2979 start
.c_str(), wildcard
.c_str(), ftp
.Pwd().c_str());
2980 size_t count
= files
.GetCount();
2981 for ( size_t n
= 0; n
< count
; n
++ )
2983 wxPrintf(_T("\t%s\n"), files
[n
].c_str());
2985 wxPuts(_T("--- End of the file list"));
2990 wxChar ch
= ftp
.SendCommand(buf
);
2991 wxPrintf(_T("Command %s"), ch
? _T("succeeded") : _T("failed"));
2994 wxPrintf(_T(" (return code %c)"), ch
);
2997 wxPrintf(_T(", server reply:\n%s\n\n"), ftp
.GetLastResult().c_str());
3001 wxPuts(_T("\n*** done ***"));
3004 static void TestFtpUpload()
3006 wxPuts(_T("*** Testing wxFTP uploading ***\n"));
3009 static const wxChar
*file1
= _T("test1");
3010 static const wxChar
*file2
= _T("test2");
3011 wxOutputStream
*out
= ftp
.GetOutputStream(file1
);
3014 wxPrintf(_T("--- Uploading to %s ---\n"), file1
);
3015 out
->Write("First hello", 11);
3019 // send a command to check the remote file
3020 if ( ftp
.SendCommand(wxString("STAT ") + file1
) != '2' )
3022 wxPrintf(_T("ERROR: STAT %s failed\n"), file1
);
3026 wxPrintf(_T("STAT %s returned:\n\n%s\n"),
3027 file1
, ftp
.GetLastResult().c_str());
3030 out
= ftp
.GetOutputStream(file2
);
3033 wxPrintf(_T("--- Uploading to %s ---\n"), file1
);
3034 out
->Write("Second hello", 12);
3041 // ----------------------------------------------------------------------------
3043 // ----------------------------------------------------------------------------
3047 #include "wx/wfstream.h"
3048 #include "wx/mstream.h"
3050 static void TestFileStream()
3052 wxPuts(_T("*** Testing wxFileInputStream ***"));
3054 static const wxChar
*filename
= _T("testdata.fs");
3056 wxFileOutputStream
fsOut(filename
);
3057 fsOut
.Write("foo", 3);
3060 wxFileInputStream
fsIn(filename
);
3061 wxPrintf(_T("File stream size: %u\n"), fsIn
.GetSize());
3062 while ( !fsIn
.Eof() )
3064 putchar(fsIn
.GetC());
3067 if ( !wxRemoveFile(filename
) )
3069 wxPrintf(_T("ERROR: failed to remove the file '%s'.\n"), filename
);
3072 wxPuts(_T("\n*** wxFileInputStream test done ***"));
3075 static void TestMemoryStream()
3077 wxPuts(_T("*** Testing wxMemoryOutputStream ***"));
3079 wxMemoryOutputStream memOutStream
;
3080 wxPrintf(_T("Initially out stream offset: %lu\n"),
3081 (unsigned long)memOutStream
.TellO());
3083 for ( const wxChar
*p
= _T("Hello, stream!"); *p
; p
++ )
3085 memOutStream
.PutC(*p
);
3088 wxPrintf(_T("Final out stream offset: %lu\n"),
3089 (unsigned long)memOutStream
.TellO());
3091 wxPuts(_T("*** Testing wxMemoryInputStream ***"));
3094 size_t len
= memOutStream
.CopyTo(buf
, WXSIZEOF(buf
));
3096 wxMemoryInputStream
memInpStream(buf
, len
);
3097 wxPrintf(_T("Memory stream size: %u\n"), memInpStream
.GetSize());
3098 while ( !memInpStream
.Eof() )
3100 putchar(memInpStream
.GetC());
3103 wxPuts(_T("\n*** wxMemoryInputStream test done ***"));
3106 #endif // TEST_STREAMS
3108 // ----------------------------------------------------------------------------
3110 // ----------------------------------------------------------------------------
3114 #include "wx/timer.h"
3115 #include "wx/utils.h"
3117 static void TestStopWatch()
3119 wxPuts(_T("*** Testing wxStopWatch ***\n"));
3123 wxPrintf(_T("Initially paused, after 2 seconds time is..."));
3126 wxPrintf(_T("\t%ldms\n"), sw
.Time());
3128 wxPrintf(_T("Resuming stopwatch and sleeping 3 seconds..."));
3132 wxPrintf(_T("\telapsed time: %ldms\n"), sw
.Time());
3135 wxPrintf(_T("Pausing agan and sleeping 2 more seconds..."));
3138 wxPrintf(_T("\telapsed time: %ldms\n"), sw
.Time());
3141 wxPrintf(_T("Finally resuming and sleeping 2 more seconds..."));
3144 wxPrintf(_T("\telapsed time: %ldms\n"), sw
.Time());
3147 wxPuts(_T("\nChecking for 'backwards clock' bug..."));
3148 for ( size_t n
= 0; n
< 70; n
++ )
3152 for ( size_t m
= 0; m
< 100000; m
++ )
3154 if ( sw
.Time() < 0 || sw2
.Time() < 0 )
3156 wxPuts(_T("\ntime is negative - ERROR!"));
3164 wxPuts(_T(", ok."));
3167 #endif // TEST_TIMER
3169 // ----------------------------------------------------------------------------
3171 // ----------------------------------------------------------------------------
3175 #include "wx/vcard.h"
3177 static void DumpVObject(size_t level
, const wxVCardObject
& vcard
)
3180 wxVCardObject
*vcObj
= vcard
.GetFirstProp(&cookie
);
3183 wxPrintf(_T("%s%s"),
3184 wxString(_T('\t'), level
).c_str(),
3185 vcObj
->GetName().c_str());
3188 switch ( vcObj
->GetType() )
3190 case wxVCardObject::String
:
3191 case wxVCardObject::UString
:
3194 vcObj
->GetValue(&val
);
3195 value
<< _T('"') << val
<< _T('"');
3199 case wxVCardObject::Int
:
3202 vcObj
->GetValue(&i
);
3203 value
.Printf(_T("%u"), i
);
3207 case wxVCardObject::Long
:
3210 vcObj
->GetValue(&l
);
3211 value
.Printf(_T("%lu"), l
);
3215 case wxVCardObject::None
:
3218 case wxVCardObject::Object
:
3219 value
= _T("<node>");
3223 value
= _T("<unknown value type>");
3227 wxPrintf(_T(" = %s"), value
.c_str());
3230 DumpVObject(level
+ 1, *vcObj
);
3233 vcObj
= vcard
.GetNextProp(&cookie
);
3237 static void DumpVCardAddresses(const wxVCard
& vcard
)
3239 wxPuts(_T("\nShowing all addresses from vCard:\n"));
3243 wxVCardAddress
*addr
= vcard
.GetFirstAddress(&cookie
);
3247 int flags
= addr
->GetFlags();
3248 if ( flags
& wxVCardAddress::Domestic
)
3250 flagsStr
<< _T("domestic ");
3252 if ( flags
& wxVCardAddress::Intl
)
3254 flagsStr
<< _T("international ");
3256 if ( flags
& wxVCardAddress::Postal
)
3258 flagsStr
<< _T("postal ");
3260 if ( flags
& wxVCardAddress::Parcel
)
3262 flagsStr
<< _T("parcel ");
3264 if ( flags
& wxVCardAddress::Home
)
3266 flagsStr
<< _T("home ");
3268 if ( flags
& wxVCardAddress::Work
)
3270 flagsStr
<< _T("work ");
3273 wxPrintf(_T("Address %u:\n")
3275 "\tvalue = %s;%s;%s;%s;%s;%s;%s\n",
3278 addr
->GetPostOffice().c_str(),
3279 addr
->GetExtAddress().c_str(),
3280 addr
->GetStreet().c_str(),
3281 addr
->GetLocality().c_str(),
3282 addr
->GetRegion().c_str(),
3283 addr
->GetPostalCode().c_str(),
3284 addr
->GetCountry().c_str()
3288 addr
= vcard
.GetNextAddress(&cookie
);
3292 static void DumpVCardPhoneNumbers(const wxVCard
& vcard
)
3294 wxPuts(_T("\nShowing all phone numbers from vCard:\n"));
3298 wxVCardPhoneNumber
*phone
= vcard
.GetFirstPhoneNumber(&cookie
);
3302 int flags
= phone
->GetFlags();
3303 if ( flags
& wxVCardPhoneNumber::Voice
)
3305 flagsStr
<< _T("voice ");
3307 if ( flags
& wxVCardPhoneNumber::Fax
)
3309 flagsStr
<< _T("fax ");
3311 if ( flags
& wxVCardPhoneNumber::Cellular
)
3313 flagsStr
<< _T("cellular ");
3315 if ( flags
& wxVCardPhoneNumber::Modem
)
3317 flagsStr
<< _T("modem ");
3319 if ( flags
& wxVCardPhoneNumber::Home
)
3321 flagsStr
<< _T("home ");
3323 if ( flags
& wxVCardPhoneNumber::Work
)
3325 flagsStr
<< _T("work ");
3328 wxPrintf(_T("Phone number %u:\n")
3333 phone
->GetNumber().c_str()
3337 phone
= vcard
.GetNextPhoneNumber(&cookie
);
3341 static void TestVCardRead()
3343 wxPuts(_T("*** Testing wxVCard reading ***\n"));
3345 wxVCard
vcard(_T("vcard.vcf"));
3346 if ( !vcard
.IsOk() )
3348 wxPuts(_T("ERROR: couldn't load vCard."));
3352 // read individual vCard properties
3353 wxVCardObject
*vcObj
= vcard
.GetProperty("FN");
3357 vcObj
->GetValue(&value
);
3362 value
= _T("<none>");
3365 wxPrintf(_T("Full name retrieved directly: %s\n"), value
.c_str());
3368 if ( !vcard
.GetFullName(&value
) )
3370 value
= _T("<none>");
3373 wxPrintf(_T("Full name from wxVCard API: %s\n"), value
.c_str());
3375 // now show how to deal with multiply occuring properties
3376 DumpVCardAddresses(vcard
);
3377 DumpVCardPhoneNumbers(vcard
);
3379 // and finally show all
3380 wxPuts(_T("\nNow dumping the entire vCard:\n")
3381 "-----------------------------\n");
3383 DumpVObject(0, vcard
);
3387 static void TestVCardWrite()
3389 wxPuts(_T("*** Testing wxVCard writing ***\n"));
3392 if ( !vcard
.IsOk() )
3394 wxPuts(_T("ERROR: couldn't create vCard."));
3399 vcard
.SetName("Zeitlin", "Vadim");
3400 vcard
.SetFullName("Vadim Zeitlin");
3401 vcard
.SetOrganization("wxWindows", "R&D");
3403 // just dump the vCard back
3404 wxPuts(_T("Entire vCard follows:\n"));
3405 wxPuts(vcard
.Write());
3409 #endif // TEST_VCARD
3411 // ----------------------------------------------------------------------------
3413 // ----------------------------------------------------------------------------
3415 #if !defined(__WIN32__) || !wxUSE_FSVOLUME
3421 #include "wx/volume.h"
3423 static const wxChar
*volumeKinds
[] =
3429 _T("network volume"),
3433 static void TestFSVolume()
3435 wxPuts(_T("*** Testing wxFSVolume class ***"));
3437 wxArrayString volumes
= wxFSVolume::GetVolumes();
3438 size_t count
= volumes
.GetCount();
3442 wxPuts(_T("ERROR: no mounted volumes?"));
3446 wxPrintf(_T("%u mounted volumes found:\n"), count
);
3448 for ( size_t n
= 0; n
< count
; n
++ )
3450 wxFSVolume
vol(volumes
[n
]);
3453 wxPuts(_T("ERROR: couldn't create volume"));
3457 wxPrintf(_T("%u: %s (%s), %s, %s, %s\n"),
3459 vol
.GetDisplayName().c_str(),
3460 vol
.GetName().c_str(),
3461 volumeKinds
[vol
.GetKind()],
3462 vol
.IsWritable() ? _T("rw") : _T("ro"),
3463 vol
.GetFlags() & wxFS_VOL_REMOVABLE
? _T("removable")
3468 #endif // TEST_VOLUME
3470 // ----------------------------------------------------------------------------
3471 // wide char and Unicode support
3472 // ----------------------------------------------------------------------------
3476 static void TestUnicodeToFromAscii()
3478 wxPuts(_T("Testing wxString::To/FromAscii()\n"));
3480 static const char *msg
= "Hello, world!";
3481 wxString s
= wxString::FromAscii(msg
);
3483 wxPrintf(_T("Message in Unicode: %s\n"), s
.c_str());
3484 wxPrintf(_T("Message in ASCII: %s\n"), s
.ToAscii());
3486 wxPutchar(_T('\n'));
3489 #endif // TEST_UNICODE
3493 #include "wx/strconv.h"
3494 #include "wx/fontenc.h"
3495 #include "wx/encconv.h"
3496 #include "wx/buffer.h"
3498 static const unsigned char textInUtf8_
[] =
3500 208, 157, 208, 181, 209, 129, 208, 186, 208, 176, 208, 183, 208, 176,
3501 208, 189, 208, 189, 208, 190, 32, 208, 191, 208, 190, 209, 128, 208,
3502 176, 208, 180, 208, 190, 208, 178, 208, 176, 208, 187, 32, 208, 188,
3503 208, 181, 208, 189, 209, 143, 32, 209, 129, 208, 178, 208, 190, 208,
3504 181, 208, 185, 32, 208, 186, 209, 128, 209, 131, 209, 130, 208, 181,
3505 208, 185, 209, 136, 208, 181, 208, 185, 32, 208, 189, 208, 190, 208,
3506 178, 208, 190, 209, 129, 209, 130, 209, 140, 209, 142, 0
3509 #define textInUtf8 ((const char *)textInUtf8_)
3511 static void TestUtf8()
3513 wxPuts(_T("*** Testing UTF8 support ***\n"));
3517 if ( wxConvUTF8
.MB2WC(wbuf
, textInUtf8
, WXSIZEOF(textInUtf8
)) <= 0 )
3519 wxPuts(_T("ERROR: UTF-8 decoding failed."));
3523 wxCSConv
conv(_T("koi8-r"));
3524 if ( conv
.WC2MB(buf
, wbuf
, 0 /* not needed wcslen(wbuf) */) <= 0 )
3526 wxPuts(_T("ERROR: conversion to KOI8-R failed."));
3530 wxPrintf(_T("The resulting string (in KOI8-R): %s\n"), buf
);
3534 if ( wxConvUTF8
.WC2MB(buf
, L
"Ã la", WXSIZEOF(buf
)) <= 0 )
3536 wxPuts(_T("ERROR: conversion to UTF-8 failed."));
3540 wxPrintf(_T("The string in UTF-8: %s\n"), buf
);
3546 static void TestEncodingConverter()
3548 wxPuts(_T("*** Testing wxEncodingConverter ***\n"));
3550 // using wxEncodingConverter should give the same result as above
3553 if ( wxConvUTF8
.MB2WC(wbuf
, textInUtf8
, WXSIZEOF(textInUtf8
)) <= 0 )
3555 wxPuts(_T("ERROR: UTF-8 decoding failed."));
3559 wxEncodingConverter ec
;
3560 ec
.Init(wxFONTENCODING_UNICODE
, wxFONTENCODING_KOI8
);
3561 ec
.Convert(wbuf
, buf
);
3562 wxPrintf(_T("The same string obtained using wxEC: %s\n"), buf
);
3568 #endif // TEST_WCHAR
3570 // ----------------------------------------------------------------------------
3572 // ----------------------------------------------------------------------------
3576 #include "wx/filesys.h"
3577 #include "wx/fs_zip.h"
3578 #include "wx/zipstrm.h"
3580 static const wxChar
*TESTFILE_ZIP
= _T("testdata.zip");
3582 static void TestZipStreamRead()
3584 wxPuts(_T("*** Testing ZIP reading ***\n"));
3586 static const wxChar
*filename
= _T("foo");
3587 wxZipInputStream
istr(TESTFILE_ZIP
, filename
);
3588 wxPrintf(_T("Archive size: %u\n"), istr
.GetSize());
3590 wxPrintf(_T("Dumping the file '%s':\n"), filename
);
3591 while ( !istr
.Eof() )
3593 putchar(istr
.GetC());
3597 wxPuts(_T("\n----- done ------"));
3600 static void DumpZipDirectory(wxFileSystem
& fs
,
3601 const wxString
& dir
,
3602 const wxString
& indent
)
3604 wxString prefix
= wxString::Format(_T("%s#zip:%s"),
3605 TESTFILE_ZIP
, dir
.c_str());
3606 wxString wildcard
= prefix
+ _T("/*");
3608 wxString dirname
= fs
.FindFirst(wildcard
, wxDIR
);
3609 while ( !dirname
.empty() )
3611 if ( !dirname
.StartsWith(prefix
+ _T('/'), &dirname
) )
3613 wxPrintf(_T("ERROR: unexpected wxFileSystem::FindNext result\n"));
3618 wxPrintf(_T("%s%s\n"), indent
.c_str(), dirname
.c_str());
3620 DumpZipDirectory(fs
, dirname
,
3621 indent
+ wxString(_T(' '), 4));
3623 dirname
= fs
.FindNext();
3626 wxString filename
= fs
.FindFirst(wildcard
, wxFILE
);
3627 while ( !filename
.empty() )
3629 if ( !filename
.StartsWith(prefix
, &filename
) )
3631 wxPrintf(_T("ERROR: unexpected wxFileSystem::FindNext result\n"));
3636 wxPrintf(_T("%s%s\n"), indent
.c_str(), filename
.c_str());
3638 filename
= fs
.FindNext();
3642 static void TestZipFileSystem()
3644 wxPuts(_T("*** Testing ZIP file system ***\n"));
3646 wxFileSystem::AddHandler(new wxZipFSHandler
);
3648 wxPrintf(_T("Dumping all files in the archive %s:\n"), TESTFILE_ZIP
);
3650 DumpZipDirectory(fs
, _T(""), wxString(_T(' '), 4));
3655 // ----------------------------------------------------------------------------
3657 // ----------------------------------------------------------------------------
3661 #include "wx/zstream.h"
3662 #include "wx/wfstream.h"
3664 static const wxChar
*FILENAME_GZ
= _T("test.gz");
3665 static const wxChar
*TEST_DATA
= _T("hello and hello and hello and hello and hello");
3667 static void TestZlibStreamWrite()
3669 wxPuts(_T("*** Testing Zlib stream reading ***\n"));
3671 wxFileOutputStream
fileOutStream(FILENAME_GZ
);
3672 wxZlibOutputStream
ostr(fileOutStream
);
3673 wxPrintf(_T("Compressing the test string... "));
3674 ostr
.Write(TEST_DATA
, wxStrlen(TEST_DATA
) + 1);
3677 wxPuts(_T("(ERROR: failed)"));
3684 wxPuts(_T("\n----- done ------"));
3687 static void TestZlibStreamRead()
3689 wxPuts(_T("*** Testing Zlib stream reading ***\n"));
3691 wxFileInputStream
fileInStream(FILENAME_GZ
);
3692 wxZlibInputStream
istr(fileInStream
);
3693 wxPrintf(_T("Archive size: %u\n"), istr
.GetSize());
3695 wxPuts(_T("Dumping the file:"));
3696 while ( !istr
.Eof() )
3698 putchar(istr
.GetC());
3702 wxPuts(_T("\n----- done ------"));
3707 // ----------------------------------------------------------------------------
3709 // ----------------------------------------------------------------------------
3711 #ifdef TEST_DATETIME
3715 #include "wx/date.h"
3716 #include "wx/datetime.h"
3721 wxDateTime::wxDateTime_t day
;
3722 wxDateTime::Month month
;
3724 wxDateTime::wxDateTime_t hour
, min
, sec
;
3726 wxDateTime::WeekDay wday
;
3727 time_t gmticks
, ticks
;
3729 void Init(const wxDateTime::Tm
& tm
)
3738 gmticks
= ticks
= -1;
3741 wxDateTime
DT() const
3742 { return wxDateTime(day
, month
, year
, hour
, min
, sec
); }
3744 bool SameDay(const wxDateTime::Tm
& tm
) const
3746 return day
== tm
.mday
&& month
== tm
.mon
&& year
== tm
.year
;
3749 wxString
Format() const
3752 s
.Printf(_T("%02d:%02d:%02d %10s %02d, %4d%s"),
3754 wxDateTime::GetMonthName(month
).c_str(),
3756 abs(wxDateTime::ConvertYearToBC(year
)),
3757 year
> 0 ? _T("AD") : _T("BC"));
3761 wxString
FormatDate() const
3764 s
.Printf(_T("%02d-%s-%4d%s"),
3766 wxDateTime::GetMonthName(month
, wxDateTime::Name_Abbr
).c_str(),
3767 abs(wxDateTime::ConvertYearToBC(year
)),
3768 year
> 0 ? _T("AD") : _T("BC"));
3773 static const Date testDates
[] =
3775 { 1, wxDateTime::Jan
, 1970, 00, 00, 00, 2440587.5, wxDateTime::Thu
, 0, -3600 },
3776 { 7, wxDateTime::Feb
, 2036, 00, 00, 00, 2464730.5, wxDateTime::Thu
, -1, -1 },
3777 { 8, wxDateTime::Feb
, 2036, 00, 00, 00, 2464731.5, wxDateTime::Fri
, -1, -1 },
3778 { 1, wxDateTime::Jan
, 2037, 00, 00, 00, 2465059.5, wxDateTime::Thu
, -1, -1 },
3779 { 1, wxDateTime::Jan
, 2038, 00, 00, 00, 2465424.5, wxDateTime::Fri
, -1, -1 },
3780 { 21, wxDateTime::Jan
, 2222, 00, 00, 00, 2532648.5, wxDateTime::Mon
, -1, -1 },
3781 { 29, wxDateTime::May
, 1976, 12, 00, 00, 2442928.0, wxDateTime::Sat
, 202219200, 202212000 },
3782 { 29, wxDateTime::Feb
, 1976, 00, 00, 00, 2442837.5, wxDateTime::Sun
, 194400000, 194396400 },
3783 { 1, wxDateTime::Jan
, 1900, 12, 00, 00, 2415021.0, wxDateTime::Mon
, -1, -1 },
3784 { 1, wxDateTime::Jan
, 1900, 00, 00, 00, 2415020.5, wxDateTime::Mon
, -1, -1 },
3785 { 15, wxDateTime::Oct
, 1582, 00, 00, 00, 2299160.5, wxDateTime::Fri
, -1, -1 },
3786 { 4, wxDateTime::Oct
, 1582, 00, 00, 00, 2299149.5, wxDateTime::Mon
, -1, -1 },
3787 { 1, wxDateTime::Mar
, 1, 00, 00, 00, 1721484.5, wxDateTime::Thu
, -1, -1 },
3788 { 1, wxDateTime::Jan
, 1, 00, 00, 00, 1721425.5, wxDateTime::Mon
, -1, -1 },
3789 { 31, wxDateTime::Dec
, 0, 00, 00, 00, 1721424.5, wxDateTime::Sun
, -1, -1 },
3790 { 1, wxDateTime::Jan
, 0, 00, 00, 00, 1721059.5, wxDateTime::Sat
, -1, -1 },
3791 { 12, wxDateTime::Aug
, -1234, 00, 00, 00, 1270573.5, wxDateTime::Fri
, -1, -1 },
3792 { 12, wxDateTime::Aug
, -4000, 00, 00, 00, 260313.5, wxDateTime::Sat
, -1, -1 },
3793 { 24, wxDateTime::Nov
, -4713, 00, 00, 00, -0.5, wxDateTime::Mon
, -1, -1 },
3796 // this test miscellaneous static wxDateTime functions
3797 static void TestTimeStatic()
3799 wxPuts(_T("\n*** wxDateTime static methods test ***"));
3801 // some info about the current date
3802 int year
= wxDateTime::GetCurrentYear();
3803 wxPrintf(_T("Current year %d is %sa leap one and has %d days.\n"),
3805 wxDateTime::IsLeapYear(year
) ? "" : "not ",
3806 wxDateTime::GetNumberOfDays(year
));
3808 wxDateTime::Month month
= wxDateTime::GetCurrentMonth();
3809 wxPrintf(_T("Current month is '%s' ('%s') and it has %d days\n"),
3810 wxDateTime::GetMonthName(month
, wxDateTime::Name_Abbr
).c_str(),
3811 wxDateTime::GetMonthName(month
).c_str(),
3812 wxDateTime::GetNumberOfDays(month
));
3815 static const size_t nYears
= 5;
3816 static const size_t years
[2][nYears
] =
3818 // first line: the years to test
3819 { 1990, 1976, 2000, 2030, 1984, },
3821 // second line: TRUE if leap, FALSE otherwise
3822 { FALSE
, TRUE
, TRUE
, FALSE
, TRUE
}
3825 for ( size_t n
= 0; n
< nYears
; n
++ )
3827 int year
= years
[0][n
];
3828 bool should
= years
[1][n
] != 0,
3829 is
= wxDateTime::IsLeapYear(year
);
3831 wxPrintf(_T("Year %d is %sa leap year (%s)\n"),
3834 should
== is
? "ok" : "ERROR");
3836 wxASSERT( should
== wxDateTime::IsLeapYear(year
) );
3840 // test constructing wxDateTime objects
3841 static void TestTimeSet()
3843 wxPuts(_T("\n*** wxDateTime construction test ***"));
3845 for ( size_t n
= 0; n
< WXSIZEOF(testDates
); n
++ )
3847 const Date
& d1
= testDates
[n
];
3848 wxDateTime dt
= d1
.DT();
3851 d2
.Init(dt
.GetTm());
3853 wxString s1
= d1
.Format(),
3856 wxPrintf(_T("Date: %s == %s (%s)\n"),
3857 s1
.c_str(), s2
.c_str(),
3858 s1
== s2
? _T("ok") : _T("ERROR"));
3862 // test time zones stuff
3863 static void TestTimeZones()
3865 wxPuts(_T("\n*** wxDateTime timezone test ***"));
3867 wxDateTime now
= wxDateTime::Now();
3869 wxPrintf(_T("Current GMT time:\t%s\n"), now
.Format(_T("%c"), wxDateTime::GMT0
).c_str());
3870 wxPrintf(_T("Unix epoch (GMT):\t%s\n"), wxDateTime((time_t)0).Format(_T("%c"), wxDateTime::GMT0
).c_str());
3871 wxPrintf(_T("Unix epoch (EST):\t%s\n"), wxDateTime((time_t)0).Format(_T("%c"), wxDateTime::EST
).c_str());
3872 wxPrintf(_T("Current time in Paris:\t%s\n"), now
.Format(_T("%c"), wxDateTime::CET
).c_str());
3873 wxPrintf(_T(" Moscow:\t%s\n"), now
.Format(_T("%c"), wxDateTime::MSK
).c_str());
3874 wxPrintf(_T(" New York:\t%s\n"), now
.Format(_T("%c"), wxDateTime::EST
).c_str());
3876 wxDateTime::Tm tm
= now
.GetTm();
3877 if ( wxDateTime(tm
) != now
)
3879 wxPrintf(_T("ERROR: got %s instead of %s\n"),
3880 wxDateTime(tm
).Format().c_str(), now
.Format().c_str());
3884 // test some minimal support for the dates outside the standard range
3885 static void TestTimeRange()
3887 wxPuts(_T("\n*** wxDateTime out-of-standard-range dates test ***"));
3889 static const wxChar
*fmt
= _T("%d-%b-%Y %H:%M:%S");
3891 wxPrintf(_T("Unix epoch:\t%s\n"),
3892 wxDateTime(2440587.5).Format(fmt
).c_str());
3893 wxPrintf(_T("Feb 29, 0: \t%s\n"),
3894 wxDateTime(29, wxDateTime::Feb
, 0).Format(fmt
).c_str());
3895 wxPrintf(_T("JDN 0: \t%s\n"),
3896 wxDateTime(0.0).Format(fmt
).c_str());
3897 wxPrintf(_T("Jan 1, 1AD:\t%s\n"),
3898 wxDateTime(1, wxDateTime::Jan
, 1).Format(fmt
).c_str());
3899 wxPrintf(_T("May 29, 2099:\t%s\n"),
3900 wxDateTime(29, wxDateTime::May
, 2099).Format(fmt
).c_str());
3903 static void TestTimeTicks()
3905 wxPuts(_T("\n*** wxDateTime ticks test ***"));
3907 for ( size_t n
= 0; n
< WXSIZEOF(testDates
); n
++ )
3909 const Date
& d
= testDates
[n
];
3910 if ( d
.ticks
== -1 )
3913 wxDateTime dt
= d
.DT();
3914 long ticks
= (dt
.GetValue() / 1000).ToLong();
3915 wxPrintf(_T("Ticks of %s:\t% 10ld"), d
.Format().c_str(), ticks
);
3916 if ( ticks
== d
.ticks
)
3918 wxPuts(_T(" (ok)"));
3922 wxPrintf(_T(" (ERROR: should be %ld, delta = %ld)\n"),
3923 (long)d
.ticks
, (long)(ticks
- d
.ticks
));
3926 dt
= d
.DT().ToTimezone(wxDateTime::GMT0
);
3927 ticks
= (dt
.GetValue() / 1000).ToLong();
3928 wxPrintf(_T("GMtks of %s:\t% 10ld"), d
.Format().c_str(), ticks
);
3929 if ( ticks
== d
.gmticks
)
3931 wxPuts(_T(" (ok)"));
3935 wxPrintf(_T(" (ERROR: should be %ld, delta = %ld)\n"),
3936 (long)d
.gmticks
, (long)(ticks
- d
.gmticks
));
3943 // test conversions to JDN &c
3944 static void TestTimeJDN()
3946 wxPuts(_T("\n*** wxDateTime to JDN test ***"));
3948 for ( size_t n
= 0; n
< WXSIZEOF(testDates
); n
++ )
3950 const Date
& d
= testDates
[n
];
3951 wxDateTime
dt(d
.day
, d
.month
, d
.year
, d
.hour
, d
.min
, d
.sec
);
3952 double jdn
= dt
.GetJulianDayNumber();
3954 wxPrintf(_T("JDN of %s is:\t% 15.6f"), d
.Format().c_str(), jdn
);
3957 wxPuts(_T(" (ok)"));
3961 wxPrintf(_T(" (ERROR: should be %f, delta = %f)\n"),
3962 d
.jdn
, jdn
- d
.jdn
);
3967 // test week days computation
3968 static void TestTimeWDays()
3970 wxPuts(_T("\n*** wxDateTime weekday test ***"));
3972 // test GetWeekDay()
3974 for ( n
= 0; n
< WXSIZEOF(testDates
); n
++ )
3976 const Date
& d
= testDates
[n
];
3977 wxDateTime
dt(d
.day
, d
.month
, d
.year
, d
.hour
, d
.min
, d
.sec
);
3979 wxDateTime::WeekDay wday
= dt
.GetWeekDay();
3980 wxPrintf(_T("%s is: %s"),
3982 wxDateTime::GetWeekDayName(wday
).c_str());
3983 if ( wday
== d
.wday
)
3985 wxPuts(_T(" (ok)"));
3989 wxPrintf(_T(" (ERROR: should be %s)\n"),
3990 wxDateTime::GetWeekDayName(d
.wday
).c_str());
3996 // test SetToWeekDay()
3997 struct WeekDateTestData
3999 Date date
; // the real date (precomputed)
4000 int nWeek
; // its week index in the month
4001 wxDateTime::WeekDay wday
; // the weekday
4002 wxDateTime::Month month
; // the month
4003 int year
; // and the year
4005 wxString
Format() const
4008 switch ( nWeek
< -1 ? -nWeek
: nWeek
)
4010 case 1: which
= _T("first"); break;
4011 case 2: which
= _T("second"); break;
4012 case 3: which
= _T("third"); break;
4013 case 4: which
= _T("fourth"); break;
4014 case 5: which
= _T("fifth"); break;
4016 case -1: which
= _T("last"); break;
4021 which
+= _T(" from end");
4024 s
.Printf(_T("The %s %s of %s in %d"),
4026 wxDateTime::GetWeekDayName(wday
).c_str(),
4027 wxDateTime::GetMonthName(month
).c_str(),
4034 // the array data was generated by the following python program
4036 from DateTime import *
4037 from whrandom import *
4038 from string import *
4040 monthNames = [ 'Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec' ]
4041 wdayNames = [ 'Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat', 'Sun' ]
4043 week = DateTimeDelta(7)
4046 year = randint(1900, 2100)
4047 month = randint(1, 12)
4048 day = randint(1, 28)
4049 dt = DateTime(year, month, day)
4050 wday = dt.day_of_week
4052 countFromEnd = choice([-1, 1])
4055 while dt.month is month:
4056 dt = dt - countFromEnd * week
4057 weekNum = weekNum + countFromEnd
4059 data = { 'day': rjust(`day`, 2), 'month': monthNames[month - 1], 'year': year, 'weekNum': rjust(`weekNum`, 2), 'wday': wdayNames[wday] }
4061 print "{ { %(day)s, wxDateTime::%(month)s, %(year)d }, %(weekNum)d, "\
4062 "wxDateTime::%(wday)s, wxDateTime::%(month)s, %(year)d }," % data
4065 static const WeekDateTestData weekDatesTestData
[] =
4067 { { 20, wxDateTime::Mar
, 2045 }, 3, wxDateTime::Mon
, wxDateTime::Mar
, 2045 },
4068 { { 5, wxDateTime::Jun
, 1985 }, -4, wxDateTime::Wed
, wxDateTime::Jun
, 1985 },
4069 { { 12, wxDateTime::Nov
, 1961 }, -3, wxDateTime::Sun
, wxDateTime::Nov
, 1961 },
4070 { { 27, wxDateTime::Feb
, 2093 }, -1, wxDateTime::Fri
, wxDateTime::Feb
, 2093 },
4071 { { 4, wxDateTime::Jul
, 2070 }, -4, wxDateTime::Fri
, wxDateTime::Jul
, 2070 },
4072 { { 2, wxDateTime::Apr
, 1906 }, -5, wxDateTime::Mon
, wxDateTime::Apr
, 1906 },
4073 { { 19, wxDateTime::Jul
, 2023 }, -2, wxDateTime::Wed
, wxDateTime::Jul
, 2023 },
4074 { { 5, wxDateTime::May
, 1958 }, -4, wxDateTime::Mon
, wxDateTime::May
, 1958 },
4075 { { 11, wxDateTime::Aug
, 1900 }, 2, wxDateTime::Sat
, wxDateTime::Aug
, 1900 },
4076 { { 14, wxDateTime::Feb
, 1945 }, 2, wxDateTime::Wed
, wxDateTime::Feb
, 1945 },
4077 { { 25, wxDateTime::Jul
, 1967 }, -1, wxDateTime::Tue
, wxDateTime::Jul
, 1967 },
4078 { { 9, wxDateTime::May
, 1916 }, -4, wxDateTime::Tue
, wxDateTime::May
, 1916 },
4079 { { 20, wxDateTime::Jun
, 1927 }, 3, wxDateTime::Mon
, wxDateTime::Jun
, 1927 },
4080 { { 2, wxDateTime::Aug
, 2000 }, 1, wxDateTime::Wed
, wxDateTime::Aug
, 2000 },
4081 { { 20, wxDateTime::Apr
, 2044 }, 3, wxDateTime::Wed
, wxDateTime::Apr
, 2044 },
4082 { { 20, wxDateTime::Feb
, 1932 }, -2, wxDateTime::Sat
, wxDateTime::Feb
, 1932 },
4083 { { 25, wxDateTime::Jul
, 2069 }, 4, wxDateTime::Thu
, wxDateTime::Jul
, 2069 },
4084 { { 3, wxDateTime::Apr
, 1925 }, 1, wxDateTime::Fri
, wxDateTime::Apr
, 1925 },
4085 { { 21, wxDateTime::Mar
, 2093 }, 3, wxDateTime::Sat
, wxDateTime::Mar
, 2093 },
4086 { { 3, wxDateTime::Dec
, 2074 }, -5, wxDateTime::Mon
, wxDateTime::Dec
, 2074 },
4089 static const wxChar
*fmt
= _T("%d-%b-%Y");
4092 for ( n
= 0; n
< WXSIZEOF(weekDatesTestData
); n
++ )
4094 const WeekDateTestData
& wd
= weekDatesTestData
[n
];
4096 dt
.SetToWeekDay(wd
.wday
, wd
.nWeek
, wd
.month
, wd
.year
);
4098 wxPrintf(_T("%s is %s"), wd
.Format().c_str(), dt
.Format(fmt
).c_str());
4100 const Date
& d
= wd
.date
;
4101 if ( d
.SameDay(dt
.GetTm()) )
4103 wxPuts(_T(" (ok)"));
4107 dt
.Set(d
.day
, d
.month
, d
.year
);
4109 wxPrintf(_T(" (ERROR: should be %s)\n"), dt
.Format(fmt
).c_str());
4114 // test the computation of (ISO) week numbers
4115 static void TestTimeWNumber()
4117 wxPuts(_T("\n*** wxDateTime week number test ***"));
4119 struct WeekNumberTestData
4121 Date date
; // the date
4122 wxDateTime::wxDateTime_t week
; // the week number in the year
4123 wxDateTime::wxDateTime_t wmon
; // the week number in the month
4124 wxDateTime::wxDateTime_t wmon2
; // same but week starts with Sun
4125 wxDateTime::wxDateTime_t dnum
; // day number in the year
4128 // data generated with the following python script:
4130 from DateTime import *
4131 from whrandom import *
4132 from string import *
4134 monthNames = [ 'Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec' ]
4135 wdayNames = [ 'Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat', 'Sun' ]
4137 def GetMonthWeek(dt):
4138 weekNumMonth = dt.iso_week[1] - DateTime(dt.year, dt.month, 1).iso_week[1] + 1
4139 if weekNumMonth < 0:
4140 weekNumMonth = weekNumMonth + 53
4143 def GetLastSundayBefore(dt):
4144 if dt.iso_week[2] == 7:
4147 return dt - DateTimeDelta(dt.iso_week[2])
4150 year = randint(1900, 2100)
4151 month = randint(1, 12)
4152 day = randint(1, 28)
4153 dt = DateTime(year, month, day)
4154 dayNum = dt.day_of_year
4155 weekNum = dt.iso_week[1]
4156 weekNumMonth = GetMonthWeek(dt)
4159 dtSunday = GetLastSundayBefore(dt)
4161 while dtSunday >= GetLastSundayBefore(DateTime(dt.year, dt.month, 1)):
4162 weekNumMonth2 = weekNumMonth2 + 1
4163 dtSunday = dtSunday - DateTimeDelta(7)
4165 data = { 'day': rjust(`day`, 2), \
4166 'month': monthNames[month - 1], \
4168 'weekNum': rjust(`weekNum`, 2), \
4169 'weekNumMonth': weekNumMonth, \
4170 'weekNumMonth2': weekNumMonth2, \
4171 'dayNum': rjust(`dayNum`, 3) }
4173 print " { { %(day)s, "\
4174 "wxDateTime::%(month)s, "\
4177 "%(weekNumMonth)s, "\
4178 "%(weekNumMonth2)s, "\
4179 "%(dayNum)s }," % data
4182 static const WeekNumberTestData weekNumberTestDates
[] =
4184 { { 27, wxDateTime::Dec
, 1966 }, 52, 5, 5, 361 },
4185 { { 22, wxDateTime::Jul
, 1926 }, 29, 4, 4, 203 },
4186 { { 22, wxDateTime::Oct
, 2076 }, 43, 4, 4, 296 },
4187 { { 1, wxDateTime::Jul
, 1967 }, 26, 1, 1, 182 },
4188 { { 8, wxDateTime::Nov
, 2004 }, 46, 2, 2, 313 },
4189 { { 21, wxDateTime::Mar
, 1920 }, 12, 3, 4, 81 },
4190 { { 7, wxDateTime::Jan
, 1965 }, 1, 2, 2, 7 },
4191 { { 19, wxDateTime::Oct
, 1999 }, 42, 4, 4, 292 },
4192 { { 13, wxDateTime::Aug
, 1955 }, 32, 2, 2, 225 },
4193 { { 18, wxDateTime::Jul
, 2087 }, 29, 3, 3, 199 },
4194 { { 2, wxDateTime::Sep
, 2028 }, 35, 1, 1, 246 },
4195 { { 28, wxDateTime::Jul
, 1945 }, 30, 5, 4, 209 },
4196 { { 15, wxDateTime::Jun
, 1901 }, 24, 3, 3, 166 },
4197 { { 10, wxDateTime::Oct
, 1939 }, 41, 3, 2, 283 },
4198 { { 3, wxDateTime::Dec
, 1965 }, 48, 1, 1, 337 },
4199 { { 23, wxDateTime::Feb
, 1940 }, 8, 4, 4, 54 },
4200 { { 2, wxDateTime::Jan
, 1987 }, 1, 1, 1, 2 },
4201 { { 11, wxDateTime::Aug
, 2079 }, 32, 2, 2, 223 },
4202 { { 2, wxDateTime::Feb
, 2063 }, 5, 1, 1, 33 },
4203 { { 16, wxDateTime::Oct
, 1942 }, 42, 3, 3, 289 },
4206 for ( size_t n
= 0; n
< WXSIZEOF(weekNumberTestDates
); n
++ )
4208 const WeekNumberTestData
& wn
= weekNumberTestDates
[n
];
4209 const Date
& d
= wn
.date
;
4211 wxDateTime dt
= d
.DT();
4213 wxDateTime::wxDateTime_t
4214 week
= dt
.GetWeekOfYear(wxDateTime::Monday_First
),
4215 wmon
= dt
.GetWeekOfMonth(wxDateTime::Monday_First
),
4216 wmon2
= dt
.GetWeekOfMonth(wxDateTime::Sunday_First
),
4217 dnum
= dt
.GetDayOfYear();
4219 wxPrintf(_T("%s: the day number is %d"), d
.FormatDate().c_str(), dnum
);
4220 if ( dnum
== wn
.dnum
)
4222 wxPrintf(_T(" (ok)"));
4226 wxPrintf(_T(" (ERROR: should be %d)"), wn
.dnum
);
4229 wxPrintf(_T(", week in month is %d"), wmon
);
4230 if ( wmon
== wn
.wmon
)
4232 wxPrintf(_T(" (ok)"));
4236 wxPrintf(_T(" (ERROR: should be %d)"), wn
.wmon
);
4239 wxPrintf(_T(" or %d"), wmon2
);
4240 if ( wmon2
== wn
.wmon2
)
4242 wxPrintf(_T(" (ok)"));
4246 wxPrintf(_T(" (ERROR: should be %d)"), wn
.wmon2
);
4249 wxPrintf(_T(", week in year is %d"), week
);
4250 if ( week
== wn
.week
)
4252 wxPuts(_T(" (ok)"));
4256 wxPrintf(_T(" (ERROR: should be %d)\n"), wn
.week
);
4261 // test DST calculations
4262 static void TestTimeDST()
4264 wxPuts(_T("\n*** wxDateTime DST test ***"));
4266 wxPrintf(_T("DST is%s in effect now.\n\n"),
4267 wxDateTime::Now().IsDST() ? _T("") : _T(" not"));
4269 // taken from http://www.energy.ca.gov/daylightsaving.html
4270 static const Date datesDST
[2][2004 - 1900 + 1] =
4273 { 1, wxDateTime::Apr
, 1990 },
4274 { 7, wxDateTime::Apr
, 1991 },
4275 { 5, wxDateTime::Apr
, 1992 },
4276 { 4, wxDateTime::Apr
, 1993 },
4277 { 3, wxDateTime::Apr
, 1994 },
4278 { 2, wxDateTime::Apr
, 1995 },
4279 { 7, wxDateTime::Apr
, 1996 },
4280 { 6, wxDateTime::Apr
, 1997 },
4281 { 5, wxDateTime::Apr
, 1998 },
4282 { 4, wxDateTime::Apr
, 1999 },
4283 { 2, wxDateTime::Apr
, 2000 },
4284 { 1, wxDateTime::Apr
, 2001 },
4285 { 7, wxDateTime::Apr
, 2002 },
4286 { 6, wxDateTime::Apr
, 2003 },
4287 { 4, wxDateTime::Apr
, 2004 },
4290 { 28, wxDateTime::Oct
, 1990 },
4291 { 27, wxDateTime::Oct
, 1991 },
4292 { 25, wxDateTime::Oct
, 1992 },
4293 { 31, wxDateTime::Oct
, 1993 },
4294 { 30, wxDateTime::Oct
, 1994 },
4295 { 29, wxDateTime::Oct
, 1995 },
4296 { 27, wxDateTime::Oct
, 1996 },
4297 { 26, wxDateTime::Oct
, 1997 },
4298 { 25, wxDateTime::Oct
, 1998 },
4299 { 31, wxDateTime::Oct
, 1999 },
4300 { 29, wxDateTime::Oct
, 2000 },
4301 { 28, wxDateTime::Oct
, 2001 },
4302 { 27, wxDateTime::Oct
, 2002 },
4303 { 26, wxDateTime::Oct
, 2003 },
4304 { 31, wxDateTime::Oct
, 2004 },
4309 for ( year
= 1990; year
< 2005; year
++ )
4311 wxDateTime dtBegin
= wxDateTime::GetBeginDST(year
, wxDateTime::USA
),
4312 dtEnd
= wxDateTime::GetEndDST(year
, wxDateTime::USA
);
4314 wxPrintf(_T("DST period in the US for year %d: from %s to %s"),
4315 year
, dtBegin
.Format().c_str(), dtEnd
.Format().c_str());
4317 size_t n
= year
- 1990;
4318 const Date
& dBegin
= datesDST
[0][n
];
4319 const Date
& dEnd
= datesDST
[1][n
];
4321 if ( dBegin
.SameDay(dtBegin
.GetTm()) && dEnd
.SameDay(dtEnd
.GetTm()) )
4323 wxPuts(_T(" (ok)"));
4327 wxPrintf(_T(" (ERROR: should be %s %d to %s %d)\n"),
4328 wxDateTime::GetMonthName(dBegin
.month
).c_str(), dBegin
.day
,
4329 wxDateTime::GetMonthName(dEnd
.month
).c_str(), dEnd
.day
);
4335 for ( year
= 1990; year
< 2005; year
++ )
4337 wxPrintf(_T("DST period in Europe for year %d: from %s to %s\n"),
4339 wxDateTime::GetBeginDST(year
, wxDateTime::Country_EEC
).Format().c_str(),
4340 wxDateTime::GetEndDST(year
, wxDateTime::Country_EEC
).Format().c_str());
4344 // test wxDateTime -> text conversion
4345 static void TestTimeFormat()
4347 wxPuts(_T("\n*** wxDateTime formatting test ***"));
4349 // some information may be lost during conversion, so store what kind
4350 // of info should we recover after a round trip
4353 CompareNone
, // don't try comparing
4354 CompareBoth
, // dates and times should be identical
4355 CompareDate
, // dates only
4356 CompareTime
// time only
4361 CompareKind compareKind
;
4362 const wxChar
*format
;
4363 } formatTestFormats
[] =
4365 { CompareBoth
, _T("---> %c") },
4366 { CompareDate
, _T("Date is %A, %d of %B, in year %Y") },
4367 { CompareBoth
, _T("Date is %x, time is %X") },
4368 { CompareTime
, _T("Time is %H:%M:%S or %I:%M:%S %p") },
4369 { CompareNone
, _T("The day of year: %j, the week of year: %W") },
4370 { CompareDate
, _T("ISO date without separators: %4Y%2m%2d") },
4373 static const Date formatTestDates
[] =
4375 { 29, wxDateTime::May
, 1976, 18, 30, 00 },
4376 { 31, wxDateTime::Dec
, 1999, 23, 30, 00 },
4378 // this test can't work for other centuries because it uses two digit
4379 // years in formats, so don't even try it
4380 { 29, wxDateTime::May
, 2076, 18, 30, 00 },
4381 { 29, wxDateTime::Feb
, 2400, 02, 15, 25 },
4382 { 01, wxDateTime::Jan
, -52, 03, 16, 47 },
4386 // an extra test (as it doesn't depend on date, don't do it in the loop)
4387 wxPrintf(_T("%s\n"), wxDateTime::Now().Format(_T("Our timezone is %Z")).c_str());
4389 for ( size_t d
= 0; d
< WXSIZEOF(formatTestDates
) + 1; d
++ )
4393 wxDateTime dt
= d
== 0 ? wxDateTime::Now() : formatTestDates
[d
- 1].DT();
4394 for ( size_t n
= 0; n
< WXSIZEOF(formatTestFormats
); n
++ )
4396 wxString s
= dt
.Format(formatTestFormats
[n
].format
);
4397 wxPrintf(_T("%s"), s
.c_str());
4399 // what can we recover?
4400 int kind
= formatTestFormats
[n
].compareKind
;
4404 const wxChar
*result
= dt2
.ParseFormat(s
, formatTestFormats
[n
].format
);
4407 // converion failed - should it have?
4408 if ( kind
== CompareNone
)
4409 wxPuts(_T(" (ok)"));
4411 wxPuts(_T(" (ERROR: conversion back failed)"));
4415 // should have parsed the entire string
4416 wxPuts(_T(" (ERROR: conversion back stopped too soon)"));
4420 bool equal
= FALSE
; // suppress compilaer warning
4428 equal
= dt
.IsSameDate(dt2
);
4432 equal
= dt
.IsSameTime(dt2
);
4438 wxPrintf(_T(" (ERROR: got back '%s' instead of '%s')\n"),
4439 dt2
.Format().c_str(), dt
.Format().c_str());
4443 wxPuts(_T(" (ok)"));
4450 // test text -> wxDateTime conversion
4451 static void TestTimeParse()
4453 wxPuts(_T("\n*** wxDateTime parse test ***"));
4455 struct ParseTestData
4457 const wxChar
*format
;
4462 static const ParseTestData parseTestDates
[] =
4464 { _T("Sat, 18 Dec 1999 00:46:40 +0100"), { 18, wxDateTime::Dec
, 1999, 00, 46, 40 }, TRUE
},
4465 { _T("Wed, 1 Dec 1999 05:17:20 +0300"), { 1, wxDateTime::Dec
, 1999, 03, 17, 20 }, TRUE
},
4468 for ( size_t n
= 0; n
< WXSIZEOF(parseTestDates
); n
++ )
4470 const wxChar
*format
= parseTestDates
[n
].format
;
4472 wxPrintf(_T("%s => "), format
);
4475 if ( dt
.ParseRfc822Date(format
) )
4477 wxPrintf(_T("%s "), dt
.Format().c_str());
4479 if ( parseTestDates
[n
].good
)
4481 wxDateTime dtReal
= parseTestDates
[n
].date
.DT();
4488 wxPrintf(_T("(ERROR: should be %s)\n"), dtReal
.Format().c_str());
4493 wxPuts(_T("(ERROR: bad format)"));
4498 wxPrintf(_T("bad format (%s)\n"),
4499 parseTestDates
[n
].good
? "ERROR" : "ok");
4504 static void TestDateTimeInteractive()
4506 wxPuts(_T("\n*** interactive wxDateTime tests ***"));
4512 wxPrintf(_T("Enter a date: "));
4513 if ( !wxFgets(buf
, WXSIZEOF(buf
), stdin
) )
4516 // kill the last '\n'
4517 buf
[wxStrlen(buf
) - 1] = 0;
4520 const wxChar
*p
= dt
.ParseDate(buf
);
4523 wxPrintf(_T("ERROR: failed to parse the date '%s'.\n"), buf
);
4529 wxPrintf(_T("WARNING: parsed only first %u characters.\n"), p
- buf
);
4532 wxPrintf(_T("%s: day %u, week of month %u/%u, week of year %u\n"),
4533 dt
.Format(_T("%b %d, %Y")).c_str(),
4535 dt
.GetWeekOfMonth(wxDateTime::Monday_First
),
4536 dt
.GetWeekOfMonth(wxDateTime::Sunday_First
),
4537 dt
.GetWeekOfYear(wxDateTime::Monday_First
));
4540 wxPuts(_T("\n*** done ***"));
4543 static void TestTimeMS()
4545 wxPuts(_T("*** testing millisecond-resolution support in wxDateTime ***"));
4547 wxDateTime dt1
= wxDateTime::Now(),
4548 dt2
= wxDateTime::UNow();
4550 wxPrintf(_T("Now = %s\n"), dt1
.Format(_T("%H:%M:%S:%l")).c_str());
4551 wxPrintf(_T("UNow = %s\n"), dt2
.Format(_T("%H:%M:%S:%l")).c_str());
4552 wxPrintf(_T("Dummy loop: "));
4553 for ( int i
= 0; i
< 6000; i
++ )
4555 //for ( int j = 0; j < 10; j++ )
4558 s
.Printf(_T("%g"), sqrt(i
));
4564 wxPuts(_T(", done"));
4567 dt2
= wxDateTime::UNow();
4568 wxPrintf(_T("UNow = %s\n"), dt2
.Format(_T("%H:%M:%S:%l")).c_str());
4570 wxPrintf(_T("Loop executed in %s ms\n"), (dt2
- dt1
).Format(_T("%l")).c_str());
4572 wxPuts(_T("\n*** done ***"));
4575 static void TestTimeArithmetics()
4577 wxPuts(_T("\n*** testing arithmetic operations on wxDateTime ***"));
4579 static const struct ArithmData
4581 ArithmData(const wxDateSpan
& sp
, const wxChar
*nam
)
4582 : span(sp
), name(nam
) { }
4586 } testArithmData
[] =
4588 ArithmData(wxDateSpan::Day(), _T("day")),
4589 ArithmData(wxDateSpan::Week(), _T("week")),
4590 ArithmData(wxDateSpan::Month(), _T("month")),
4591 ArithmData(wxDateSpan::Year(), _T("year")),
4592 ArithmData(wxDateSpan(1, 2, 3, 4), _T("year, 2 months, 3 weeks, 4 days")),
4595 wxDateTime
dt(29, wxDateTime::Dec
, 1999), dt1
, dt2
;
4597 for ( size_t n
= 0; n
< WXSIZEOF(testArithmData
); n
++ )
4599 wxDateSpan span
= testArithmData
[n
].span
;
4603 const wxChar
*name
= testArithmData
[n
].name
;
4604 wxPrintf(_T("%s + %s = %s, %s - %s = %s\n"),
4605 dt
.FormatISODate().c_str(), name
, dt1
.FormatISODate().c_str(),
4606 dt
.FormatISODate().c_str(), name
, dt2
.FormatISODate().c_str());
4608 wxPrintf(_T("Going back: %s"), (dt1
- span
).FormatISODate().c_str());
4609 if ( dt1
- span
== dt
)
4611 wxPuts(_T(" (ok)"));
4615 wxPrintf(_T(" (ERROR: should be %s)\n"), dt
.FormatISODate().c_str());
4618 wxPrintf(_T("Going forward: %s"), (dt2
+ span
).FormatISODate().c_str());
4619 if ( dt2
+ span
== dt
)
4621 wxPuts(_T(" (ok)"));
4625 wxPrintf(_T(" (ERROR: should be %s)\n"), dt
.FormatISODate().c_str());
4628 wxPrintf(_T("Double increment: %s"), (dt2
+ 2*span
).FormatISODate().c_str());
4629 if ( dt2
+ 2*span
== dt1
)
4631 wxPuts(_T(" (ok)"));
4635 wxPrintf(_T(" (ERROR: should be %s)\n"), dt2
.FormatISODate().c_str());
4642 static void TestTimeHolidays()
4644 wxPuts(_T("\n*** testing wxDateTimeHolidayAuthority ***\n"));
4646 wxDateTime::Tm tm
= wxDateTime(29, wxDateTime::May
, 2000).GetTm();
4647 wxDateTime
dtStart(1, tm
.mon
, tm
.year
),
4648 dtEnd
= dtStart
.GetLastMonthDay();
4650 wxDateTimeArray hol
;
4651 wxDateTimeHolidayAuthority::GetHolidaysInRange(dtStart
, dtEnd
, hol
);
4653 const wxChar
*format
= _T("%d-%b-%Y (%a)");
4655 wxPrintf(_T("All holidays between %s and %s:\n"),
4656 dtStart
.Format(format
).c_str(), dtEnd
.Format(format
).c_str());
4658 size_t count
= hol
.GetCount();
4659 for ( size_t n
= 0; n
< count
; n
++ )
4661 wxPrintf(_T("\t%s\n"), hol
[n
].Format(format
).c_str());
4667 static void TestTimeZoneBug()
4669 wxPuts(_T("\n*** testing for DST/timezone bug ***\n"));
4671 wxDateTime date
= wxDateTime(1, wxDateTime::Mar
, 2000);
4672 for ( int i
= 0; i
< 31; i
++ )
4674 wxPrintf(_T("Date %s: week day %s.\n"),
4675 date
.Format(_T("%d-%m-%Y")).c_str(),
4676 date
.GetWeekDayName(date
.GetWeekDay()).c_str());
4678 date
+= wxDateSpan::Day();
4684 static void TestTimeSpanFormat()
4686 wxPuts(_T("\n*** wxTimeSpan tests ***"));
4688 static const wxChar
*formats
[] =
4690 _T("(default) %H:%M:%S"),
4691 _T("%E weeks and %D days"),
4692 _T("%l milliseconds"),
4693 _T("(with ms) %H:%M:%S:%l"),
4694 _T("100%% of minutes is %M"), // test "%%"
4695 _T("%D days and %H hours"),
4696 _T("or also %S seconds"),
4699 wxTimeSpan
ts1(1, 2, 3, 4),
4701 for ( size_t n
= 0; n
< WXSIZEOF(formats
); n
++ )
4703 wxPrintf(_T("ts1 = %s\tts2 = %s\n"),
4704 ts1
.Format(formats
[n
]).c_str(),
4705 ts2
.Format(formats
[n
]).c_str());
4713 // test compatibility with the old wxDate/wxTime classes
4714 static void TestTimeCompatibility()
4716 wxPuts(_T("\n*** wxDateTime compatibility test ***"));
4718 wxPrintf(_T("wxDate for JDN 0: %s\n"), wxDate(0l).FormatDate().c_str());
4719 wxPrintf(_T("wxDate for MJD 0: %s\n"), wxDate(2400000).FormatDate().c_str());
4721 double jdnNow
= wxDateTime::Now().GetJDN();
4722 long jdnMidnight
= (long)(jdnNow
- 0.5);
4723 wxPrintf(_T("wxDate for today: %s\n"), wxDate(jdnMidnight
).FormatDate().c_str());
4725 jdnMidnight
= wxDate().Set().GetJulianDate();
4726 wxPrintf(_T("wxDateTime for today: %s\n"),
4727 wxDateTime((double)(jdnMidnight
+ 0.5)).Format("%c", wxDateTime::GMT0
).c_str());
4729 int flags
= wxEUROPEAN
;//wxFULL;
4732 wxPrintf(_T("Today is %s\n"), date
.FormatDate(flags
).c_str());
4733 for ( int n
= 0; n
< 7; n
++ )
4735 wxPrintf(_T("Previous %s is %s\n"),
4736 wxDateTime::GetWeekDayName((wxDateTime::WeekDay
)n
),
4737 date
.Previous(n
+ 1).FormatDate(flags
).c_str());
4743 #endif // TEST_DATETIME
4745 // ----------------------------------------------------------------------------
4747 // ----------------------------------------------------------------------------
4751 #include "wx/thread.h"
4753 static size_t gs_counter
= (size_t)-1;
4754 static wxCriticalSection gs_critsect
;
4755 static wxSemaphore gs_cond
;
4757 class MyJoinableThread
: public wxThread
4760 MyJoinableThread(size_t n
) : wxThread(wxTHREAD_JOINABLE
)
4761 { m_n
= n
; Create(); }
4763 // thread execution starts here
4764 virtual ExitCode
Entry();
4770 wxThread::ExitCode
MyJoinableThread::Entry()
4772 unsigned long res
= 1;
4773 for ( size_t n
= 1; n
< m_n
; n
++ )
4777 // it's a loooong calculation :-)
4781 return (ExitCode
)res
;
4784 class MyDetachedThread
: public wxThread
4787 MyDetachedThread(size_t n
, wxChar ch
)
4791 m_cancelled
= FALSE
;
4796 // thread execution starts here
4797 virtual ExitCode
Entry();
4800 virtual void OnExit();
4803 size_t m_n
; // number of characters to write
4804 wxChar m_ch
; // character to write
4806 bool m_cancelled
; // FALSE if we exit normally
4809 wxThread::ExitCode
MyDetachedThread::Entry()
4812 wxCriticalSectionLocker
lock(gs_critsect
);
4813 if ( gs_counter
== (size_t)-1 )
4819 for ( size_t n
= 0; n
< m_n
; n
++ )
4821 if ( TestDestroy() )
4831 wxThread::Sleep(100);
4837 void MyDetachedThread::OnExit()
4839 wxLogTrace(_T("thread"), _T("Thread %ld is in OnExit"), GetId());
4841 wxCriticalSectionLocker
lock(gs_critsect
);
4842 if ( !--gs_counter
&& !m_cancelled
)
4846 static void TestDetachedThreads()
4848 wxPuts(_T("\n*** Testing detached threads ***"));
4850 static const size_t nThreads
= 3;
4851 MyDetachedThread
*threads
[nThreads
];
4853 for ( n
= 0; n
< nThreads
; n
++ )
4855 threads
[n
] = new MyDetachedThread(10, 'A' + n
);
4858 threads
[0]->SetPriority(WXTHREAD_MIN_PRIORITY
);
4859 threads
[1]->SetPriority(WXTHREAD_MAX_PRIORITY
);
4861 for ( n
= 0; n
< nThreads
; n
++ )
4866 // wait until all threads terminate
4872 static void TestJoinableThreads()
4874 wxPuts(_T("\n*** Testing a joinable thread (a loooong calculation...) ***"));
4876 // calc 10! in the background
4877 MyJoinableThread
thread(10);
4880 wxPrintf(_T("\nThread terminated with exit code %lu.\n"),
4881 (unsigned long)thread
.Wait());
4884 static void TestThreadSuspend()
4886 wxPuts(_T("\n*** Testing thread suspend/resume functions ***"));
4888 MyDetachedThread
*thread
= new MyDetachedThread(15, 'X');
4892 // this is for this demo only, in a real life program we'd use another
4893 // condition variable which would be signaled from wxThread::Entry() to
4894 // tell us that the thread really started running - but here just wait a
4895 // bit and hope that it will be enough (the problem is, of course, that
4896 // the thread might still not run when we call Pause() which will result
4898 wxThread::Sleep(300);
4900 for ( size_t n
= 0; n
< 3; n
++ )
4904 wxPuts(_T("\nThread suspended"));
4907 // don't sleep but resume immediately the first time
4908 wxThread::Sleep(300);
4910 wxPuts(_T("Going to resume the thread"));
4915 wxPuts(_T("Waiting until it terminates now"));
4917 // wait until the thread terminates
4923 static void TestThreadDelete()
4925 // As above, using Sleep() is only for testing here - we must use some
4926 // synchronisation object instead to ensure that the thread is still
4927 // running when we delete it - deleting a detached thread which already
4928 // terminated will lead to a crash!
4930 wxPuts(_T("\n*** Testing thread delete function ***"));
4932 MyDetachedThread
*thread0
= new MyDetachedThread(30, 'W');
4936 wxPuts(_T("\nDeleted a thread which didn't start to run yet."));
4938 MyDetachedThread
*thread1
= new MyDetachedThread(30, 'Y');
4942 wxThread::Sleep(300);
4946 wxPuts(_T("\nDeleted a running thread."));
4948 MyDetachedThread
*thread2
= new MyDetachedThread(30, 'Z');
4952 wxThread::Sleep(300);
4958 wxPuts(_T("\nDeleted a sleeping thread."));
4960 MyJoinableThread
thread3(20);
4965 wxPuts(_T("\nDeleted a joinable thread."));
4967 MyJoinableThread
thread4(2);
4970 wxThread::Sleep(300);
4974 wxPuts(_T("\nDeleted a joinable thread which already terminated."));
4979 class MyWaitingThread
: public wxThread
4982 MyWaitingThread( wxMutex
*mutex
, wxCondition
*condition
)
4985 m_condition
= condition
;
4990 virtual ExitCode
Entry()
4992 wxPrintf(_T("Thread %lu has started running.\n"), GetId());
4997 wxPrintf(_T("Thread %lu starts to wait...\n"), GetId());
5001 m_condition
->Wait();
5004 wxPrintf(_T("Thread %lu finished to wait, exiting.\n"), GetId());
5012 wxCondition
*m_condition
;
5015 static void TestThreadConditions()
5018 wxCondition
condition(mutex
);
5020 // otherwise its difficult to understand which log messages pertain to
5022 //wxLogTrace(_T("thread"), _T("Local condition var is %08x, gs_cond = %08x"),
5023 // condition.GetId(), gs_cond.GetId());
5025 // create and launch threads
5026 MyWaitingThread
*threads
[10];
5029 for ( n
= 0; n
< WXSIZEOF(threads
); n
++ )
5031 threads
[n
] = new MyWaitingThread( &mutex
, &condition
);
5034 for ( n
= 0; n
< WXSIZEOF(threads
); n
++ )
5039 // wait until all threads run
5040 wxPuts(_T("Main thread is waiting for the other threads to start"));
5043 size_t nRunning
= 0;
5044 while ( nRunning
< WXSIZEOF(threads
) )
5050 wxPrintf(_T("Main thread: %u already running\n"), nRunning
);
5054 wxPuts(_T("Main thread: all threads started up."));
5057 wxThread::Sleep(500);
5060 // now wake one of them up
5061 wxPrintf(_T("Main thread: about to signal the condition.\n"));
5066 wxThread::Sleep(200);
5068 // wake all the (remaining) threads up, so that they can exit
5069 wxPrintf(_T("Main thread: about to broadcast the condition.\n"));
5071 condition
.Broadcast();
5073 // give them time to terminate (dirty!)
5074 wxThread::Sleep(500);
5077 #include "wx/utils.h"
5079 class MyExecThread
: public wxThread
5082 MyExecThread(const wxString
& command
) : wxThread(wxTHREAD_JOINABLE
),
5088 virtual ExitCode
Entry()
5090 return (ExitCode
)wxExecute(m_command
, wxEXEC_SYNC
);
5097 static void TestThreadExec()
5099 wxPuts(_T("*** Testing wxExecute interaction with threads ***\n"));
5101 MyExecThread
thread(_T("true"));
5104 wxPrintf(_T("Main program exit code: %ld.\n"),
5105 wxExecute(_T("false"), wxEXEC_SYNC
));
5107 wxPrintf(_T("Thread exit code: %ld.\n"), (long)thread
.Wait());
5111 #include "wx/datetime.h"
5113 class MySemaphoreThread
: public wxThread
5116 MySemaphoreThread(int i
, wxSemaphore
*sem
)
5117 : wxThread(wxTHREAD_JOINABLE
),
5124 virtual ExitCode
Entry()
5126 wxPrintf(_T("%s: Thread #%d (%ld) starting to wait for semaphore...\n"),
5127 wxDateTime::Now().FormatTime().c_str(), m_i
, (long)GetId());
5131 wxPrintf(_T("%s: Thread #%d (%ld) acquired the semaphore.\n"),
5132 wxDateTime::Now().FormatTime().c_str(), m_i
, (long)GetId());
5136 wxPrintf(_T("%s: Thread #%d (%ld) releasing the semaphore.\n"),
5137 wxDateTime::Now().FormatTime().c_str(), m_i
, (long)GetId());
5149 WX_DEFINE_ARRAY(wxThread
*, ArrayThreads
);
5151 static void TestSemaphore()
5153 wxPuts(_T("*** Testing wxSemaphore class. ***"));
5155 static const int SEM_LIMIT
= 3;
5157 wxSemaphore
sem(SEM_LIMIT
, SEM_LIMIT
);
5158 ArrayThreads threads
;
5160 for ( int i
= 0; i
< 3*SEM_LIMIT
; i
++ )
5162 threads
.Add(new MySemaphoreThread(i
, &sem
));
5163 threads
.Last()->Run();
5166 for ( size_t n
= 0; n
< threads
.GetCount(); n
++ )
5173 #endif // TEST_THREADS
5175 // ----------------------------------------------------------------------------
5177 // ----------------------------------------------------------------------------
5181 #include "wx/dynarray.h"
5183 typedef unsigned short ushort
;
5185 #define DefineCompare(name, T) \
5187 int wxCMPFUNC_CONV name ## CompareValues(T first, T second) \
5189 return first - second; \
5192 int wxCMPFUNC_CONV name ## Compare(T* first, T* second) \
5194 return *first - *second; \
5197 int wxCMPFUNC_CONV name ## RevCompare(T* first, T* second) \
5199 return *second - *first; \
5202 DefineCompare(UShort, ushort);
5203 DefineCompare(Int
, int);
5205 // test compilation of all macros
5206 WX_DEFINE_ARRAY_SHORT(ushort
, wxArrayUShort
);
5207 WX_DEFINE_SORTED_ARRAY_SHORT(ushort
, wxSortedArrayUShortNoCmp
);
5208 WX_DEFINE_SORTED_ARRAY_CMP_SHORT(ushort
, UShortCompareValues
, wxSortedArrayUShort
);
5209 WX_DEFINE_SORTED_ARRAY_CMP_INT(int, IntCompareValues
, wxSortedArrayInt
);
5211 WX_DECLARE_OBJARRAY(Bar
, ArrayBars
);
5212 #include "wx/arrimpl.cpp"
5213 WX_DEFINE_OBJARRAY(ArrayBars
);
5215 static void PrintArray(const wxChar
* name
, const wxArrayString
& array
)
5217 wxPrintf(_T("Dump of the array '%s'\n"), name
);
5219 size_t nCount
= array
.GetCount();
5220 for ( size_t n
= 0; n
< nCount
; n
++ )
5222 wxPrintf(_T("\t%s[%u] = '%s'\n"), name
, n
, array
[n
].c_str());
5226 int wxCMPFUNC_CONV
StringLenCompare(const wxString
& first
,
5227 const wxString
& second
)
5229 return first
.length() - second
.length();
5232 #define TestArrayOf(name) \
5234 static void PrintArray(const wxChar* name, const wxSortedArray##name & array) \
5236 wxPrintf(_T("Dump of the array '%s'\n"), name); \
5238 size_t nCount = array.GetCount(); \
5239 for ( size_t n = 0; n < nCount; n++ ) \
5241 wxPrintf(_T("\t%s[%u] = %d\n"), name, n, array[n]); \
5245 static void PrintArray(const wxChar* name, const wxArray##name & array) \
5247 wxPrintf(_T("Dump of the array '%s'\n"), name); \
5249 size_t nCount = array.GetCount(); \
5250 for ( size_t n = 0; n < nCount; n++ ) \
5252 wxPrintf(_T("\t%s[%u] = %d\n"), name, n, array[n]); \
5256 static void TestArrayOf ## name ## s() \
5258 wxPrintf(_T("*** Testing wxArray%s ***\n"), #name); \
5266 wxPuts(_T("Initially:")); \
5267 PrintArray(_T("a"), a); \
5269 wxPuts(_T("After sort:")); \
5270 a.Sort(name ## Compare); \
5271 PrintArray(_T("a"), a); \
5273 wxPuts(_T("After reverse sort:")); \
5274 a.Sort(name ## RevCompare); \
5275 PrintArray(_T("a"), a); \
5277 wxSortedArray##name b; \
5283 wxPuts(_T("Sorted array initially:")); \
5284 PrintArray(_T("b"), b); \
5287 TestArrayOf(UShort
);
5290 static void TestArrayOfObjects()
5292 wxPuts(_T("*** Testing wxObjArray ***\n"));
5296 Bar
bar("second bar (two copies!)");
5298 wxPrintf(_T("Initially: %u objects in the array, %u objects total.\n"),
5299 bars
.GetCount(), Bar::GetNumber());
5301 bars
.Add(new Bar("first bar"));
5304 wxPrintf(_T("Now: %u objects in the array, %u objects total.\n"),
5305 bars
.GetCount(), Bar::GetNumber());
5307 bars
.RemoveAt(1, bars
.GetCount() - 1);
5309 wxPrintf(_T("After removing all but first element: %u objects in the ")
5310 _T("array, %u objects total.\n"),
5311 bars
.GetCount(), Bar::GetNumber());
5315 wxPrintf(_T("After Empty(): %u objects in the array, %u objects total.\n"),
5316 bars
.GetCount(), Bar::GetNumber());
5319 wxPrintf(_T("Finally: no more objects in the array, %u objects total.\n"),
5323 #endif // TEST_ARRAYS
5325 // ----------------------------------------------------------------------------
5327 // ----------------------------------------------------------------------------
5331 #include "wx/timer.h"
5332 #include "wx/tokenzr.h"
5334 static void TestStringConstruction()
5336 wxPuts(_T("*** Testing wxString constructores ***"));
5338 #define TEST_CTOR(args, res) \
5341 wxPrintf(_T("wxString%s = %s "), #args, s.c_str()); \
5344 wxPuts(_T("(ok)")); \
5348 wxPrintf(_T("(ERROR: should be %s)\n"), res); \
5352 TEST_CTOR((_T('Z'), 4), _T("ZZZZ"));
5353 TEST_CTOR((_T("Hello"), 4), _T("Hell"));
5354 TEST_CTOR((_T("Hello"), 5), _T("Hello"));
5355 // TEST_CTOR((_T("Hello"), 6), _T("Hello")); -- should give assert failure
5357 static const wxChar
*s
= _T("?really!");
5358 const wxChar
*start
= wxStrchr(s
, _T('r'));
5359 const wxChar
*end
= wxStrchr(s
, _T('!'));
5360 TEST_CTOR((start
, end
), _T("really"));
5365 static void TestString()
5375 for (int i
= 0; i
< 1000000; ++i
)
5379 c
= "! How'ya doin'?";
5382 c
= "Hello world! What's up?";
5387 wxPrintf(_T("TestString elapsed time: %ld\n"), sw
.Time());
5390 static void TestPChar()
5398 for (int i
= 0; i
< 1000000; ++i
)
5400 wxStrcpy (a
, _T("Hello"));
5401 wxStrcpy (b
, _T(" world"));
5402 wxStrcpy (c
, _T("! How'ya doin'?"));
5405 wxStrcpy (c
, _T("Hello world! What's up?"));
5406 if (wxStrcmp (c
, a
) == 0)
5407 wxStrcpy (c
, _T("Doh!"));
5410 wxPrintf(_T("TestPChar elapsed time: %ld\n"), sw
.Time());
5413 static void TestStringSub()
5415 wxString
s("Hello, world!");
5417 wxPuts(_T("*** Testing wxString substring extraction ***"));
5419 wxPrintf(_T("String = '%s'\n"), s
.c_str());
5420 wxPrintf(_T("Left(5) = '%s'\n"), s
.Left(5).c_str());
5421 wxPrintf(_T("Right(6) = '%s'\n"), s
.Right(6).c_str());
5422 wxPrintf(_T("Mid(3, 5) = '%s'\n"), s(3, 5).c_str());
5423 wxPrintf(_T("Mid(3) = '%s'\n"), s
.Mid(3).c_str());
5424 wxPrintf(_T("substr(3, 5) = '%s'\n"), s
.substr(3, 5).c_str());
5425 wxPrintf(_T("substr(3) = '%s'\n"), s
.substr(3).c_str());
5427 static const wxChar
*prefixes
[] =
5431 _T("Hello, world!"),
5432 _T("Hello, world!!!"),
5438 for ( size_t n
= 0; n
< WXSIZEOF(prefixes
); n
++ )
5440 wxString prefix
= prefixes
[n
], rest
;
5441 bool rc
= s
.StartsWith(prefix
, &rest
);
5442 wxPrintf(_T("StartsWith('%s') = %s"), prefix
.c_str(), rc
? _T("TRUE") : _T("FALSE"));
5445 wxPrintf(_T(" (the rest is '%s')\n"), rest
.c_str());
5456 static void TestStringFormat()
5458 wxPuts(_T("*** Testing wxString formatting ***"));
5461 s
.Printf(_T("%03d"), 18);
5463 wxPrintf(_T("Number 18: %s\n"), wxString::Format(_T("%03d"), 18).c_str());
5464 wxPrintf(_T("Number 18: %s\n"), s
.c_str());
5469 // returns "not found" for npos, value for all others
5470 static wxString
PosToString(size_t res
)
5472 wxString s
= res
== wxString::npos
? wxString(_T("not found"))
5473 : wxString::Format(_T("%u"), res
);
5477 static void TestStringFind()
5479 wxPuts(_T("*** Testing wxString find() functions ***"));
5481 static const wxChar
*strToFind
= _T("ell");
5482 static const struct StringFindTest
5486 result
; // of searching "ell" in str
5489 { _T("Well, hello world"), 0, 1 },
5490 { _T("Well, hello world"), 6, 7 },
5491 { _T("Well, hello world"), 9, wxString::npos
},
5494 for ( size_t n
= 0; n
< WXSIZEOF(findTestData
); n
++ )
5496 const StringFindTest
& ft
= findTestData
[n
];
5497 size_t res
= wxString(ft
.str
).find(strToFind
, ft
.start
);
5499 wxPrintf(_T("Index of '%s' in '%s' starting from %u is %s "),
5500 strToFind
, ft
.str
, ft
.start
, PosToString(res
).c_str());
5502 size_t resTrue
= ft
.result
;
5503 if ( res
== resTrue
)
5509 wxPrintf(_T("(ERROR: should be %s)\n"),
5510 PosToString(resTrue
).c_str());
5517 static void TestStringTokenizer()
5519 wxPuts(_T("*** Testing wxStringTokenizer ***"));
5521 static const wxChar
*modeNames
[] =
5525 _T("return all empty"),
5530 static const struct StringTokenizerTest
5532 const wxChar
*str
; // string to tokenize
5533 const wxChar
*delims
; // delimiters to use
5534 size_t count
; // count of token
5535 wxStringTokenizerMode mode
; // how should we tokenize it
5536 } tokenizerTestData
[] =
5538 { _T(""), _T(" "), 0 },
5539 { _T("Hello, world"), _T(" "), 2 },
5540 { _T("Hello, world "), _T(" "), 2 },
5541 { _T("Hello, world"), _T(","), 2 },
5542 { _T("Hello, world!"), _T(",!"), 2 },
5543 { _T("Hello,, world!"), _T(",!"), 3 },
5544 { _T("Hello, world!"), _T(",!"), 3, wxTOKEN_RET_EMPTY_ALL
},
5545 { _T("username:password:uid:gid:gecos:home:shell"), _T(":"), 7 },
5546 { _T("1 \t3\t4 6 "), wxDEFAULT_DELIMITERS
, 4 },
5547 { _T("1 \t3\t4 6 "), wxDEFAULT_DELIMITERS
, 6, wxTOKEN_RET_EMPTY
},
5548 { _T("1 \t3\t4 6 "), wxDEFAULT_DELIMITERS
, 9, wxTOKEN_RET_EMPTY_ALL
},
5549 { _T("01/02/99"), _T("/-"), 3 },
5550 { _T("01-02/99"), _T("/-"), 3, wxTOKEN_RET_DELIMS
},
5553 for ( size_t n
= 0; n
< WXSIZEOF(tokenizerTestData
); n
++ )
5555 const StringTokenizerTest
& tt
= tokenizerTestData
[n
];
5556 wxStringTokenizer
tkz(tt
.str
, tt
.delims
, tt
.mode
);
5558 size_t count
= tkz
.CountTokens();
5559 wxPrintf(_T("String '%s' has %u tokens delimited by '%s' (mode = %s) "),
5560 MakePrintable(tt
.str
).c_str(),
5562 MakePrintable(tt
.delims
).c_str(),
5563 modeNames
[tkz
.GetMode()]);
5564 if ( count
== tt
.count
)
5570 wxPrintf(_T("(ERROR: should be %u)\n"), tt
.count
);
5575 // if we emulate strtok(), check that we do it correctly
5576 wxChar
*buf
, *s
= NULL
, *last
;
5578 if ( tkz
.GetMode() == wxTOKEN_STRTOK
)
5580 buf
= new wxChar
[wxStrlen(tt
.str
) + 1];
5581 wxStrcpy(buf
, tt
.str
);
5583 s
= wxStrtok(buf
, tt
.delims
, &last
);
5590 // now show the tokens themselves
5592 while ( tkz
.HasMoreTokens() )
5594 wxString token
= tkz
.GetNextToken();
5596 wxPrintf(_T("\ttoken %u: '%s'"),
5598 MakePrintable(token
).c_str());
5604 wxPuts(_T(" (ok)"));
5608 wxPrintf(_T(" (ERROR: should be %s)\n"), s
);
5611 s
= wxStrtok(NULL
, tt
.delims
, &last
);
5615 // nothing to compare with
5620 if ( count2
!= count
)
5622 wxPuts(_T("\tERROR: token count mismatch"));
5631 static void TestStringReplace()
5633 wxPuts(_T("*** Testing wxString::replace ***"));
5635 static const struct StringReplaceTestData
5637 const wxChar
*original
; // original test string
5638 size_t start
, len
; // the part to replace
5639 const wxChar
*replacement
; // the replacement string
5640 const wxChar
*result
; // and the expected result
5641 } stringReplaceTestData
[] =
5643 { _T("012-AWORD-XYZ"), 4, 5, _T("BWORD"), _T("012-BWORD-XYZ") },
5644 { _T("increase"), 0, 2, _T("de"), _T("decrease") },
5645 { _T("wxWindow"), 8, 0, _T("s"), _T("wxWindows") },
5646 { _T("foobar"), 3, 0, _T("-"), _T("foo-bar") },
5647 { _T("barfoo"), 0, 6, _T("foobar"), _T("foobar") },
5650 for ( size_t n
= 0; n
< WXSIZEOF(stringReplaceTestData
); n
++ )
5652 const StringReplaceTestData data
= stringReplaceTestData
[n
];
5654 wxString original
= data
.original
;
5655 original
.replace(data
.start
, data
.len
, data
.replacement
);
5657 wxPrintf(_T("wxString(\"%s\").replace(%u, %u, %s) = %s "),
5658 data
.original
, data
.start
, data
.len
, data
.replacement
,
5661 if ( original
== data
.result
)
5667 wxPrintf(_T("(ERROR: should be '%s')\n"), data
.result
);
5674 static void TestStringMatch()
5676 wxPuts(_T("*** Testing wxString::Matches() ***"));
5678 static const struct StringMatchTestData
5681 const wxChar
*wildcard
;
5683 } stringMatchTestData
[] =
5685 { _T("foobar"), _T("foo*"), 1 },
5686 { _T("foobar"), _T("*oo*"), 1 },
5687 { _T("foobar"), _T("*bar"), 1 },
5688 { _T("foobar"), _T("??????"), 1 },
5689 { _T("foobar"), _T("f??b*"), 1 },
5690 { _T("foobar"), _T("f?b*"), 0 },
5691 { _T("foobar"), _T("*goo*"), 0 },
5692 { _T("foobar"), _T("*foo"), 0 },
5693 { _T("foobarfoo"), _T("*foo"), 1 },
5694 { _T(""), _T("*"), 1 },
5695 { _T(""), _T("?"), 0 },
5698 for ( size_t n
= 0; n
< WXSIZEOF(stringMatchTestData
); n
++ )
5700 const StringMatchTestData
& data
= stringMatchTestData
[n
];
5701 bool matches
= wxString(data
.text
).Matches(data
.wildcard
);
5702 wxPrintf(_T("'%s' %s '%s' (%s)\n"),
5704 matches
? _T("matches") : _T("doesn't match"),
5706 matches
== data
.matches
? _T("ok") : _T("ERROR"));
5712 #endif // TEST_STRINGS
5714 // ----------------------------------------------------------------------------
5716 // ----------------------------------------------------------------------------
5718 #ifdef TEST_SNGLINST
5719 #include "wx/snglinst.h"
5720 #endif // TEST_SNGLINST
5722 int main(int argc
, char **argv
)
5724 wxApp::CheckBuildOptions(wxBuildOptions());
5726 wxInitializer initializer
;
5729 fprintf(stderr
, "Failed to initialize the wxWindows library, aborting.");
5734 #ifdef TEST_SNGLINST
5735 wxSingleInstanceChecker checker
;
5736 if ( checker
.Create(_T(".wxconsole.lock")) )
5738 if ( checker
.IsAnotherRunning() )
5740 wxPrintf(_T("Another instance of the program is running, exiting.\n"));
5745 // wait some time to give time to launch another instance
5746 wxPrintf(_T("Press \"Enter\" to continue..."));
5749 else // failed to create
5751 wxPrintf(_T("Failed to init wxSingleInstanceChecker.\n"));
5753 #endif // TEST_SNGLINST
5757 #endif // TEST_CHARSET
5760 TestCmdLineConvert();
5762 #if wxUSE_CMDLINE_PARSER
5763 static const wxCmdLineEntryDesc cmdLineDesc
[] =
5765 { wxCMD_LINE_SWITCH
, _T("h"), _T("help"), _T("show this help message"),
5766 wxCMD_LINE_VAL_NONE
, wxCMD_LINE_OPTION_HELP
},
5767 { wxCMD_LINE_SWITCH
, _T("v"), _T("verbose"), _T("be verbose") },
5768 { wxCMD_LINE_SWITCH
, _T("q"), _T("quiet"), _T("be quiet") },
5770 { wxCMD_LINE_OPTION
, _T("o"), _T("output"), _T("output file") },
5771 { wxCMD_LINE_OPTION
, _T("i"), _T("input"), _T("input dir") },
5772 { wxCMD_LINE_OPTION
, _T("s"), _T("size"), _T("output block size"),
5773 wxCMD_LINE_VAL_NUMBER
},
5774 { wxCMD_LINE_OPTION
, _T("d"), _T("date"), _T("output file date"),
5775 wxCMD_LINE_VAL_DATE
},
5777 { wxCMD_LINE_PARAM
, NULL
, NULL
, _T("input file"),
5778 wxCMD_LINE_VAL_STRING
, wxCMD_LINE_PARAM_MULTIPLE
},
5784 wxChar
**wargv
= new wxChar
*[argc
+ 1];
5787 for ( int n
= 0; n
< argc
; n
++ )
5789 wxMB2WXbuf warg
= wxConvertMB2WX(argv
[n
]);
5790 wargv
[n
] = wxStrdup(warg
);
5797 #endif // wxUSE_UNICODE
5799 wxCmdLineParser
parser(cmdLineDesc
, argc
, argv
);
5803 for ( int n
= 0; n
< argc
; n
++ )
5808 #endif // wxUSE_UNICODE
5810 parser
.AddOption(_T("project_name"), _T(""), _T("full path to project file"),
5811 wxCMD_LINE_VAL_STRING
,
5812 wxCMD_LINE_OPTION_MANDATORY
| wxCMD_LINE_NEEDS_SEPARATOR
);
5814 switch ( parser
.Parse() )
5817 wxLogMessage(_T("Help was given, terminating."));
5821 ShowCmdLine(parser
);
5825 wxLogMessage(_T("Syntax error detected, aborting."));
5828 #endif // wxUSE_CMDLINE_PARSER
5830 #endif // TEST_CMDLINE
5838 TestStringConstruction();
5841 TestStringTokenizer();
5842 TestStringReplace();
5848 #endif // TEST_STRINGS
5854 a1
.Add(_T("tiger"));
5856 a1
.Add(_T("lion"), 3);
5858 a1
.Add(_T("human"));
5861 wxPuts(_T("*** Initially:"));
5863 PrintArray(_T("a1"), a1
);
5865 wxArrayString
a2(a1
);
5866 PrintArray(_T("a2"), a2
);
5868 wxSortedArrayString
a3(a1
);
5869 PrintArray(_T("a3"), a3
);
5871 wxPuts(_T("*** After deleting three strings from a1"));
5874 PrintArray(_T("a1"), a1
);
5875 PrintArray(_T("a2"), a2
);
5876 PrintArray(_T("a3"), a3
);
5878 wxPuts(_T("*** After reassigning a1 to a2 and a3"));
5880 PrintArray(_T("a2"), a2
);
5881 PrintArray(_T("a3"), a3
);
5883 wxPuts(_T("*** After sorting a1"));
5885 PrintArray(_T("a1"), a1
);
5887 wxPuts(_T("*** After sorting a1 in reverse order"));
5889 PrintArray(_T("a1"), a1
);
5891 wxPuts(_T("*** After sorting a1 by the string length"));
5892 a1
.Sort(StringLenCompare
);
5893 PrintArray(_T("a1"), a1
);
5895 TestArrayOfObjects();
5896 TestArrayOfUShorts();
5900 #endif // TEST_ARRAYS
5911 #ifdef TEST_DLLLOADER
5913 #endif // TEST_DLLLOADER
5917 #endif // TEST_ENVIRON
5921 #endif // TEST_EXECUTE
5923 #ifdef TEST_FILECONF
5925 #endif // TEST_FILECONF
5933 #endif // TEST_LOCALE
5937 for ( size_t n
= 0; n
< 8000; n
++ )
5939 s
<< (wxChar
)(_T('A') + (n
% 26));
5943 msg
.Printf(_T("A very very long message: '%s', the end!\n"), s
.c_str());
5945 // this one shouldn't be truncated
5948 // but this one will because log functions use fixed size buffer
5949 // (note that it doesn't need '\n' at the end neither - will be added
5951 wxLogMessage(_T("A very very long message 2: '%s', the end!"), s
.c_str());
5963 #ifdef TEST_FILENAME
5967 fn
.Assign(_T("c:\\foo"), _T("bar.baz"));
5968 fn
.Assign(_T("/u/os9-port/Viewer/tvision/WEI2HZ-3B3-14_05-04-00MSC1.asc"));
5973 TestFileNameConstruction();
5976 TestFileNameConstruction();
5977 TestFileNameMakeRelative();
5978 TestFileNameSplit();
5981 TestFileNameComparison();
5982 TestFileNameOperations();
5984 #endif // TEST_FILENAME
5986 #ifdef TEST_FILETIME
5990 #endif // TEST_FILETIME
5993 wxLog::AddTraceMask(FTP_TRACE_MASK
);
5994 if ( TestFtpConnect() )
6005 if ( TEST_INTERACTIVE
)
6006 TestFtpInteractive();
6008 //else: connecting to the FTP server failed
6014 #ifdef TEST_LONGLONG
6015 // seed pseudo random generator
6016 srand((unsigned)time(NULL
));
6025 TestMultiplication();
6028 TestLongLongConversion();
6029 TestBitOperations();
6030 TestLongLongComparison();
6031 TestLongLongPrint();
6033 #endif // TEST_LONGLONG
6041 #endif // TEST_HASHMAP
6044 wxLog::AddTraceMask(_T("mime"));
6049 TestMimeAssociate();
6054 #ifdef TEST_INFO_FUNCTIONS
6060 if ( TEST_INTERACTIVE
)
6063 #endif // TEST_INFO_FUNCTIONS
6065 #ifdef TEST_PATHLIST
6067 #endif // TEST_PATHLIST
6075 #endif // TEST_REGCONF
6078 // TODO: write a real test using src/regex/tests file
6083 TestRegExSubmatch();
6084 TestRegExReplacement();
6086 if ( TEST_INTERACTIVE
)
6087 TestRegExInteractive();
6089 #endif // TEST_REGEX
6091 #ifdef TEST_REGISTRY
6093 TestRegistryAssociation();
6094 #endif // TEST_REGISTRY
6099 #endif // TEST_SOCKETS
6107 #endif // TEST_STREAMS
6110 int nCPUs
= wxThread::GetCPUCount();
6111 wxPrintf(_T("This system has %d CPUs\n"), nCPUs
);
6113 wxThread::SetConcurrency(nCPUs
);
6117 TestDetachedThreads();
6118 TestJoinableThreads();
6119 TestThreadSuspend();
6121 TestThreadConditions();
6126 #endif // TEST_THREADS
6130 #endif // TEST_TIMER
6132 #ifdef TEST_DATETIME
6145 TestTimeArithmetics();
6148 TestTimeSpanFormat();
6154 if ( TEST_INTERACTIVE
)
6155 TestDateTimeInteractive();
6156 #endif // TEST_DATETIME
6159 wxPuts(_T("Sleeping for 3 seconds... z-z-z-z-z..."));
6161 #endif // TEST_USLEEP
6166 #endif // TEST_VCARD
6170 #endif // TEST_VOLUME
6173 TestUnicodeToFromAscii();
6174 #endif // TEST_UNICODE
6178 TestEncodingConverter();
6179 #endif // TEST_WCHAR
6182 TestZipStreamRead();
6183 TestZipFileSystem();
6187 TestZlibStreamWrite();
6188 TestZlibStreamRead();