sdk: const correctness
[sdk] / compiler / ecc / ecc.ec
index 08bbb69..0ea90d5 100644 (file)
@@ -6,12 +6,13 @@ import "ecere"
 import "ec"
 #endif
 
-#include <stdarg.h>
+
+//#include <stdarg.h>
 
 static Context globalContext { };
 static Module privateModule;
 static ModuleImport mainModule;
-static OldList _excludedSymbols { offset = (uint)&((Symbol)0).left }; 
+static OldList _excludedSymbols { offset = (uint)(uintptr)&((Symbol)0).left };
 static OldList defines, imports;
 static NameSpace globalData
 {
@@ -20,7 +21,6 @@ static NameSpace globalData
    functions.CompareKey = (void *)BinaryTree::CompareString;
    nameSpaces.CompareKey = (void *)BinaryTree::CompareString;
 };
-static OldList _precompDefines;
 
 static void OutputImports(char * fileName)
 {
@@ -114,6 +114,123 @@ static void OutputImports(char * fileName)
    delete f;
 }
 
+#ifdef _DEBUG
+/*static bool TestType(String string, String expected)
+{
+   bool result = true;
+   char typeString[1024] = { 0 };
+   Type type = ProcessTypeString(string, false);
+   PrintType(type, typeString, true, false);//true);
+   if(strcmp(typeString, expected ? expected : string))
+   {
+      PrintLn("FAILED: ", string, " -> ", typeString);
+      result = false;
+   }
+   return result;
+}
+
+static void TestTypes()
+{
+   int succeeded = 0, count = 0;
+
+   count++, succeeded += TestType("dllexport void (dllexport * Module::signal(int, void (*)(int)))(int)", null);
+   count++, succeeded += TestType("int (* f[8])[10]", null);
+   count++, succeeded += TestType("void (* signal(int, void (*)(int)))(int)", null);
+   count++, succeeded += TestType("void (* signal(double))()", null);
+   count++, succeeded += TestType("void (* bla)(int)", null);
+   count++, succeeded += TestType("int f(void (*[10])())", null);
+   count++, succeeded += TestType("void (*[10])()", null);
+   count++, succeeded += TestType("void (* converters_table[10])()", null);
+   count++, succeeded += TestType("int (* f[8])[10]", null);
+
+   count++, succeeded += TestType("int f[8][10]", null);
+   count++, succeeded += TestType("int f[10]", null);
+   count++, succeeded += TestType("void *", null);
+   count++, succeeded += TestType("char * x", "char * x");
+   count++, succeeded += TestType("char * x", null);
+   count++, succeeded += TestType("char (* x[3])()", null);
+   count++, succeeded += TestType("char (*(* x[3])())", "char * (* x[3])()");
+   count++, succeeded += TestType("char (* x())", "char * x()");
+   count++, succeeded += TestType("char (* (* x[3])())[5]", null);
+   count++, succeeded += TestType("char (* f())[5]", null);
+   count++, succeeded += TestType("char * (* f())[5]", null);
+   count++, succeeded += TestType("char * (* * f())[5][2][3]", null);
+   count++, succeeded += TestType("char * (* * (* f)())[5][2][3]", null);
+   count++, succeeded += TestType("char * (* (* * (* f)())[5][2])[3]", null);
+   count++, succeeded += TestType("void (* (* bar)[5])()", null);
+   count++, succeeded += TestType("const int * (* const f)(char[10])", null);
+   count++, succeeded += TestType("const int", null);
+   count++, succeeded += TestType("int * const *", null);
+   count++, succeeded += TestType("int * const", null);
+   count++, succeeded += TestType("const int *", null);
+
+   count++, succeeded += TestType("char * const (* (* const bar)[5])(int)", null);
+   count++, succeeded += TestType("char * const (* (* (* const bar)[5][6])(int))[2]", null);
+   count++, succeeded += TestType("int * * a", null);
+
+   count++, succeeded += TestType("char * const (* bar)()", null);
+
+   count++, succeeded += TestType("char * const (* const (* const bar)[5])(int)", null);
+
+   count++, succeeded += TestType("char * (* const (* bar)[5])(int)", null);
+   count++, succeeded += TestType("void (* * const bar[5])()", null);
+   count++, succeeded += TestType("void (* * const bar)()", null);
+   count++, succeeded += TestType("void (* const * bar)()", null);
+   count++, succeeded += TestType("const int * * foo", null); // this prevents you from doing: **foo = 0;
+   count++, succeeded += TestType("int * const * bar", null); // this prevents you from doing: *bar = 0;
+   count++, succeeded += TestType("int * * const two", null); // this prevents you from doing: two = 0;
+   count++, succeeded += TestType("dllexport int TestFunction()", null);
+   count++, succeeded += TestType("dllexport int (* TestFunction())[3]", null);
+
+
+   count++, succeeded += TestType("int dllexport TestFunction()", "dllexport int TestFunction()");
+   count++, succeeded += TestType("bool (stdcall * Load)(Module module)", null);
+
+   count++, succeeded += TestType("bool (__attribute__((stdcall)) * Load)(Module module)", "bool (stdcall * Load)(Module module)");
+   count++, succeeded += TestType("int (dllexport * Load)()", null);
+   count++, succeeded += TestType("int (* Load)(Module module)", null);
+   count++, succeeded += TestType("bool (__declspec(dllexport) * Load)(Module module)", "bool (dllexport * Load)(Module module)");
+   count++, succeeded += TestType("__declspec(dllexport) int TestFunction()", "dllexport int TestFunction()");
+   count++, succeeded += TestType("int __declspec(dllexport) TestFunction()", "dllexport int TestFunction()");
+   count++, succeeded += TestType("int __attribute__((dllexport)) TestFunction()", "dllexport int TestFunction()");
+   count++, succeeded += TestType("bool (__attribute__((dllexport)) * Load)(Module module)", "bool (dllexport * Load)(Module module)");
+   count++, succeeded += TestType("any_object TestFunction(any_object, typed_object param)", null);
+   count++, succeeded += TestType("void typed_object::OnDisplay(Surface surface, int x, int y, int width, void * fieldData, Alignment alignment, DataDisplayFlags displayFlags)", null);
+   count++, succeeded += TestType("int typed_object::OnCompare(any_object object)", null);
+   count++, succeeded += TestType("char * typed_object::OnGetString(char * tempString, void * fieldData, bool * needClass)", null);
+   count++, succeeded += TestType("void typed_object&::OnCopy(any_object newData)", null);
+   count++, succeeded += TestType("void typed_object::OnFree(void)", null);
+   count++, succeeded += TestType("bool typed_object&::OnGetDataFromString(char * string)", null);
+   count++, succeeded += TestType("Window typed_object::OnEdit(DataBox dataBox, DataBox obsolete, int x, int y, int w, int h, void * userData)", null);
+   count++, succeeded += TestType("void typed_object::OnSerialize(IOChannel channel)", null);
+   count++, succeeded += TestType("void typed_object&::OnUnserialize(IOChannel channel)", null);
+   count++, succeeded += TestType("bool typed_object&::OnSaveEdit(Window window, void * object)", null);
+   count++, succeeded += TestType("void ::StaticMethod(IOChannel channel)", null);
+
+   count++, succeeded += TestType("void PrintLn(typed_object object, ...)", null);
+   count++, succeeded += TestType("void PrintLn(typed_object object, ...)", null);
+
+   count++, succeeded += TestType("thisclass RemoveSwapRight()", null);
+   count++, succeeded += TestType("struct { thisclass prev; thisclass next; }", null);
+
+   count++, succeeded += TestType("LinkElement<thisclass>", null);
+
+   count++, succeeded += TestType("void (dllexport * converters_table[10])()", null);
+
+   count++, succeeded += TestType("bool (stdcall * * Load)(Module module)", null);
+
+   count++, succeeded += TestType("int stdcall TestFunction()", "stdcall int TestFunction()");
+   count++, succeeded += TestType("dllexport stdcall void test()", null);
+
+   count++, succeeded += TestType("bool (* Module::notifySelect)(MenuItem selection, Modifiers mods)", null);
+
+   count++, succeeded += TestType("typed_object &", null);
+
+   PrintLn("\n", succeeded, " / ", count, " tests succeeded.");
+}
+*/
+#endif
+
 class CompilerApp : Application
 {
    void Main()
@@ -126,10 +243,15 @@ class CompilerApp : Application
       int c;
       bool valid = true;
       char defaultOutputFile[MAX_LOCATION];
+      bool buildingBootStrap = false;
 
       Platform targetPlatform = GetRuntimePlatform();
       int targetBits = GetHostBits();
 
+#ifdef _DEBUG
+      // buildingBootStrap = true;
+#endif
+
       SetSymbolsDir("");
 
       /*for(c = 0; c<this.argc; c++)
@@ -157,47 +279,53 @@ class CompilerApp : Application
          argc++;
       }*/
 
+#if 0 //def _DEBUG
+      printf("\nArguments given:\n");
+      for(c=1; c<argc; c++)
+         printf(" %s", argv[c]);
+      printf("\n\n");
+      for(c=1; c<argc; c++)
+         PrintLn("Arg", c, ": ", argv[c]);
+      printf("\n");
+      //getch();
+#endif
+
       for(c = 1; c<argc; c++)
       {
-         char * arg = argv[c];
+         const char * arg = argv[c];
          if(arg[0] == '-')
          {
             if(!strcmp(arg + 1, "m32") || !strcmp(arg + 1, "m64"))
             {
-               int argLen = strlen(arg);
-               int newLen = cppOptionsLen + 1 + argLen;
+               int newLen = cppOptionsLen + 1 + strlen(arg);
                cppOptions = renew cppOptions char[newLen + 1];
                cppOptions[cppOptionsLen] = ' ';
                strcpy(cppOptions + cppOptionsLen + 1, arg);
                cppOptionsLen = newLen;
                targetBits = !strcmp(arg + 1, "m32") ? 32 : 64;
             }
-            else if(arg[1] == 'D')
+            else if(!strcmp(arg + 1, "t32") || !strcmp(arg + 1, "t64"))
             {
-               int argLen = strlen(arg);
-               int newLen = cppOptionsLen + 1 + argLen;
-               cppOptions = renew cppOptions char[newLen + 1];
-               cppOptions[cppOptionsLen] = ' ';
-               strcpy(cppOptions + cppOptionsLen + 1, arg); 
-               cppOptionsLen = newLen;
-               if(!strcmp(arg, "-DBUILDING_ECERE_COM"))
-                  SetBuildingEcereCom(true);
-               else if(!strcmp(arg, "-DECERE_COM_MODULE"))
-                  SetBuildingEcereComModule(true);
+               targetBits = !strcmp(arg + 1, "t32") ? 32 : 64;
             }
-            else if(arg[1] == 'I')
+            else if(arg[1] == 'D' || arg[1] == 'I')
             {
-               int argLen = strlen(arg);
-               int newLen = cppOptionsLen + argLen + 3;
-               cppOptions = renew cppOptions char[newLen + 1];
-               cppOptions[cppOptionsLen] = ' ';
-               cppOptions[cppOptionsLen+1] = '-';
-               cppOptions[cppOptionsLen+2] = 'I';
-               cppOptions[cppOptionsLen+3] = '"';
-               strcpy(cppOptions + cppOptionsLen + 4, arg+2); 
-               cppOptions[newLen-1] = '\"';
-               cppOptions[newLen] = '\0';
-               cppOptionsLen = newLen;
+               char * buf;
+               int size = cppOptionsLen + 1 + strlen(arg) * 2 + 1;
+               cppOptions = renew cppOptions char[size];
+               buf = cppOptions + cppOptionsLen;
+               *buf++ = ' ';
+               PassArg(buf, arg);
+               cppOptionsLen = cppOptionsLen + 1 + strlen(buf);
+               if(arg[1] == 'D')
+               {
+                  if(!strcmp(arg, "-DBUILDING_ECERE_COM"))
+                     SetBuildingEcereCom(true);
+                  else if(!strcmp(arg, "-DECERE_COM_MODULE"))
+                     SetBuildingEcereComModule(true);
+                  else if(!strcmp(arg, "-DECERE_BOOTSTRAP"))
+                     buildingBootStrap = true;
+               }
             }
             else if(!strcmp(arg+1, "t"))
             {
@@ -237,23 +365,30 @@ class CompilerApp : Application
             {
                if(c + 1 < argc)
                {
-                  int argLen = strlen(arg);
-                  int arg1Len = strlen(argv[c+1]);
-                  int newLen = cppOptionsLen + argLen + arg1Len + 4;
-                  cppOptions = renew cppOptions char[newLen + 1];
-                  cppOptions[cppOptionsLen] = ' ';
-                  strcpy(cppOptions + cppOptionsLen + 1, arg); 
-                  cppOptions[cppOptionsLen+argLen+1] = ' ';
-                  cppOptions[cppOptionsLen+argLen+2] = '"';
-                  arg = argv[++c];
-                  strcpy(cppOptions + cppOptionsLen + argLen + 3, arg); 
-                  cppOptions[newLen-1] = '\"';
-                  cppOptions[newLen] = '\0';
-                  cppOptionsLen = newLen;
+                  char * buf;
+                  const char * arg1 = argv[++c];
+                  int size = cppOptionsLen + 1 + strlen(arg) * 2 + strlen(arg1) * 2 + 1;
+                  cppOptions = renew cppOptions char[size];
+                  buf = cppOptions + cppOptionsLen;
+                  *buf++ = ' ';
+                  buf = PassArg(buf, arg);
+                  *buf++ = ' ';
+                  buf = PassArg(buf, arg1);
+                  cppOptionsLen = buf - cppOptions;
                }
                else
                   valid = false;
             }
+            else if(!strcmp(arg+1, "fno-diagnostics-show-caret"))
+            {
+               char * buf;
+               int size = cppOptionsLen + 1 + strlen(arg) * 2 + 1;
+               cppOptions = renew cppOptions char[size];
+               buf = cppOptions + cppOptionsLen;
+               *buf++ = ' ';
+               PassArg(buf, arg);
+               cppOptionsLen = cppOptionsLen + 1 + strlen(buf);
+            }
             else if(!strcmp(arg+1, "symbols"))
             {
                if(c + 1 < argc)
@@ -264,6 +399,16 @@ class CompilerApp : Application
                else
                   valid = false;
             }
+            else if(!strcmp(arg+1, "module"))
+            {
+               if(c + 1 < argc)
+               {
+                  SetI18nModuleName(argv[c+1]);
+                  c++;
+               }
+               else
+                  valid = false;
+            }
             else if(!strcmp(arg+1, "memguard"))
             {
                SetMemoryGuard(true);
@@ -307,7 +452,9 @@ class CompilerApp : Application
       }
 
       if(!valid)
-         printf($"Syntax:\n   ecc [-t <target platform>] [-cpp <c preprocessor>] [-o <output>] [-symbols <outputdir>] [-I<includedir>]* [-isystem <sysincludedir>]* [-D<definition>]* -c <input>\n");
+      {
+         printf($"Syntax:\n   ecc [-t <target platform>] [-cpp <c preprocessor>] [-o <output>] [-module <module>] [-symbols <outputdir>] [-I<includedir>]* [-isystem <sysincludedir>]* [-D<definition>]* -c <input>\n");
+      }
       else
       {
          DualPipe cppOutput;
@@ -324,8 +471,8 @@ class CompilerApp : Application
          SetTargetPlatform(targetPlatform);
          SetTargetBits(targetBits);
          SetEchoOn(false);
-
-         privateModule = (Module)__ecere_COM_Initialize(true | (targetBits == sizeof(uintptr)*8 ? 0 : targetBits == 64 ? 2 : targetBits==32 ? 4 : 0) | 8, 1, null);
+                                                        // TOFIX: Use a bit class instead of a bool to store target bits information
+         privateModule = (Module)__ecere_COM_Initialize((bool)(true | (targetBits == sizeof(uintptr)*8 ? 0 : targetBits == 64 ? 2 : targetBits==32 ? 4 : 0) | 8), 1, null);
          SetPrivateModule(privateModule);
 
          globalContext.types.Add((BTNode)Symbol { string = CopyString("uint"), type = ProcessTypeString("unsigned int", false) });
@@ -333,8 +480,18 @@ class CompilerApp : Application
          globalContext.types.Add((BTNode)Symbol { string = CopyString("uint32"), type = ProcessTypeString("unsigned int", false) });
          globalContext.types.Add((BTNode)Symbol { string = CopyString("uint16"), type = ProcessTypeString("unsigned short", false) });
          globalContext.types.Add((BTNode)Symbol { string = CopyString("byte"), type = ProcessTypeString("unsigned char", false) });
-         globalContext.types.Add((BTNode)Symbol { string = CopyString("intptr_t"), type = ProcessTypeString("intptr", false) });
-         globalContext.types.Add((BTNode)Symbol { string = CopyString("uintptr_t"), type = ProcessTypeString("uintptr", false) });
+         if(buildingBootStrap)
+         {
+            // Do not define this when we pre-include stdint.h or the eC compiler will be confused when parsing these types (External prioritization in pass15.ec will fail)
+            globalContext.types.Add((BTNode)Symbol { string = CopyString("intptr_t"), type = ProcessTypeString("intptr", false) });
+            globalContext.types.Add((BTNode)Symbol { string = CopyString("uintptr_t"), type = ProcessTypeString("uintptr", false) });
+            globalContext.types.Add((BTNode)Symbol { string = CopyString("ssize_t"), type = ProcessTypeString("intsize", false) });
+            globalContext.types.Add((BTNode)Symbol { string = CopyString("size_t"), type = ProcessTypeString("uintsize", false) });
+         }
+
+#ifdef _DEBUG
+         // TestTypes();
+#endif
 
          {
             GlobalData data { fullName = CopyString("__thisModule"), dataTypeString = CopyString("Module"), module = privateModule };
@@ -342,12 +499,17 @@ class CompilerApp : Application
             globalData.functions.Add((BTNode)data);
          }
 
-         snprintf(command, sizeof(command), "%s%s -x c -E -D_INTPTR_T_DEFINED -D_UINTPTR_T_DEFINED \"%s\"", cppCommand, cppOptions ? cppOptions : "", GetSourceFile());
+         snprintf(command, sizeof(command), "%s%s -x c -E %s\"%s\"", cppCommand, cppOptions ? cppOptions : "", buildingBootStrap ? "" : "-include stdint.h -include sys/types.h ", GetSourceFile());
          command[sizeof(command)-1] = 0;
+#if 0 //def _DEBUG
+         PrintLn("ECC Executing:");
+         PrintLn(command);
+#endif
          if((cppOutput = DualPipeOpen({ output = true }, command)))
          {
             char impFile[MAX_LOCATION];
             ImportedModule module;
+            char sourceFileName[MAX_FILENAME];
             char mainModuleName[MAX_FILENAME];
             int exitCode;
             OldList * ast;
@@ -358,11 +520,12 @@ class CompilerApp : Application
             imports.Add((mainModule = ModuleImport { }));
             SetMainModule(mainModule);
 
-            GetLastDirectory(GetSourceFile(), mainModuleName);
+            GetLastDirectory(GetSourceFile(), sourceFileName);
+            strcpy(mainModuleName, sourceFileName);
 
 #if 0
             // TEMP: UNTIL WE CAN HAVE PER SOURCE FILE PREPROCESSOR DEFINITIONS...
-            if(GetBuildingEcereCom() && 
+            if(GetBuildingEcereCom() &&
                !(strcmpi(mainModuleName, "instance.ec") && strcmpi(mainModuleName, "BinaryTree.ec") &&
                strcmpi(mainModuleName, "dataTypes.ec") && strcmpi(mainModuleName, "OldList.ec") &&
                strcmpi(mainModuleName, "String.ec") && strcmpi(mainModuleName, "BTNode.ec") &&
@@ -372,14 +535,14 @@ class CompilerApp : Application
                strcmpi(mainModuleName, "List.ec") && strcmpi(mainModuleName, "Map.ec") &&
                strcmpi(mainModuleName, "Mutex.ec")))
                SetBuildingEcereComModule(true);
-            if(GetBuildingEcereCom() && 
+            if(GetBuildingEcereCom() &&
                !(strcmpi(mainModuleName, "instance.ec") && strcmpi(mainModuleName, "BinaryTree.ec") &&
                /*strcmpi(mainModuleName, "dataTypes.ec") && strcmpi(mainModuleName, "OldList.ec") &&*/
                /*strcmpi(mainModuleName, "String.ec") && */strcmpi(mainModuleName, "BTNode.ec") &&
                strcmpi(mainModuleName, "Mutex.ec") && strcmpi(mainModuleName, "Thread.ec")))
             //if(GetBuildingEcereCom() && !strcmpi(mainModuleName, "instance.ec"))
                SetMemoryGuard(false);
-#endif            
+#endif
 
             StripExtension(mainModuleName);
             module = ImportedModule { name = CopyString(mainModuleName), type = moduleDefinition };
@@ -407,15 +570,15 @@ class CompilerApp : Application
                char symLocation[MAX_LOCATION];
                ImportedModule module, next;
 
-               GetLastDirectory(GetSourceFile(), symFile);
+               strcpy(symFile, sourceFileName);
                ChangeExtension(symFile, "sym", symFile);
 
                strcpy(symLocation, GetSymbolsDir());
                PathCat(symLocation, symFile);
-               
+
                // LoadSymbols(symLocation, normalImport, true);
                LoadSymbols(symLocation, preDeclImport, false);
-               
+
                for(module = ::defines.first; module; module = next)
                {
                   next = module.next;
@@ -444,7 +607,7 @@ class CompilerApp : Application
 
             ast = GetAST();
 
-            if(/*ast /*&& !parseError*/ /*&& */!exitCode)
+            if(/*ast && !parseError*/ /*&& */!exitCode)
             {
                ProcessDBTableDefinitions();
 
@@ -458,7 +621,7 @@ class CompilerApp : Application
                // For classes defined in this module...
                ComputeModuleClasses(privateModule);
 
-               
+
                // *** PASS 1 - Turn the class functions into functions               ***
                // *** Write the RegisterModule (Register classes)                    ***
                ProcessClassDefinitions();
@@ -476,12 +639,8 @@ class CompilerApp : Application
                ProcessInstanceDeclarations();
 
                strcpy(impFile, GetSymbolsDir());
-               {
-                  char fileName[MAX_FILENAME];
-                  GetLastDirectory(GetSourceFile(), fileName);
-                  PathCat(impFile, fileName);
-                  ChangeExtension(impFile, "imp", impFile);
-               }
+               PathCat(impFile, sourceFileName);
+               ChangeExtension(impFile, "imp", impFile);
                if(imports.first)
                   OutputImports(impFile);
                // For now use precomp to generate sym file only...
@@ -491,6 +650,7 @@ class CompilerApp : Application
                   File output = FileOpen(GetOutputFile(), write);
                   if(output)
                   {
+                     output.Printf("/* Code generated from eC source file: %s */\n", sourceFileName);
                      output.Printf("#if defined(__GNUC__)\n");
                         output.Printf("typedef long long int64;\n");
                         output.Printf("typedef unsigned long long uint64;\n");
@@ -520,17 +680,24 @@ class CompilerApp : Application
                      output.Printf("#else\n");
                         output.Printf("#define __ENDIAN_PAD(x) 0\n");
                      output.Printf("#endif\n");
-                     output.Printf("#ifdef __MINGW32__\n");
-                     output.Printf("#ifdef _WIN64\n");
-                     output.Printf("typedef unsigned long long int uintptr_t;\n");
-                     output.Printf("typedef long long int intptr_t;\n");
-                     output.Printf("#else\n");
-                     output.Printf("typedef unsigned int uintptr_t;\n");
-                     output.Printf("typedef int intptr_t;\n");
-                     output.Printf("#endif\n");
-                     output.Printf("#else\n");
-                     output.Printf("#include <stdint.h>\n");
-                     output.Printf("#endif\n");
+                     if(buildingBootStrap)
+                     {
+                        //output.Printf("#ifdef __MINGW32__\n");
+                        //output.Printf("#ifdef _WIN64\n");
+                        /*
+                        output.Printf("#if defined(_WIN64) || WORDSIZE == 64\n");
+                        output.Printf("typedef unsigned long long int uintptr_t;\n");
+                        output.Printf("typedef long long int intptr_t;\n");
+                        output.Printf("#else\n");
+                        output.Printf("typedef unsigned int uintptr_t;\n");
+                        output.Printf("typedef int intptr_t;\n");
+                        output.Printf("#endif\n");
+                        */
+                        //output.Printf("#else\n");
+                        output.Printf("#include <stdint.h>\n");
+                        output.Printf("#include <sys/types.h>\n");
+                        //output.Printf("#endif\n");
+                     }
 
                      // NOTE: If anything is changed up there, the start outputLine must be updated in libec's output.c or Debugging lines will be wrong
 
@@ -582,7 +749,8 @@ class CompilerApp : Application
 
       OutputIntlStrings();
 
-#if defined(_DEBUG) && defined(__WIN32__)
+#if 0 //defined(_DEBUG) && defined(__WIN32__)
+      PrintLn("Done.");
       if(exitCode || GetNumWarnings())
          getch();
 #endif