9a4f5db362a487dce9de5dc73a2842f8d512755b
[scilab.git] / scilab / modules / core / src / cpp / InitScilab.cpp
1 /*
2  * Scilab ( http://www.scilab.org/ ) - This file is part of Scilab
3  * Copyright (C) 2013 - Scilab Enterprises - Antoine ELIAS
4  * Copyright (C) 2013 - Scilab Enterprises - Cedric DELAMARRE
5  *
6  * This file must be used under the terms of the CeCILL.
7  * This source file is licensed as described in the file COPYING, which
8  * you should have received as part of this distribution.  The terms
9  * are also available at
10  * http://www.cecill.info/licences/Licence_CeCILL_V2-en.txt
11  *
12  */
13
14 #include <string>
15 #include <libxml/parser.h>
16
17 #include "inspector.hxx"
18 #include "double.hxx"
19 #include "polynom.hxx"
20 #include "string.hxx"
21 #include "bool.hxx"
22
23 #include "scilabWrite.hxx"
24 #include "tasks.hxx"
25 #include "parser.hxx"
26 #include "context.hxx"
27 #include "configvariable.hxx"
28 #include "filemanager.hxx"
29 #include "runner.hxx"
30 #include "visitor_common.hxx"
31 #include "operations.hxx"
32
33 extern "C"
34 {
35 #include "machine.h"
36 #include "InitializeLocalization.h"
37 #include "elem_common.h"
38 #include "LaunchScilabSignal.h"
39 #include "InitializeJVM.h"
40 #include "TerminateJVM.h"
41 #include "InitializeGUI.h"
42 #include "graphicModuleLoad.h"
43 #include "TerminateGraphics.h"
44 #include "loadBackGroundClassPath.h"
45 #include "sci_tmpdir.h"
46 #include "configvariable_interface.h"
47 #include "setgetlanguage.h"
48 #include "InitializeConsole.h"
49 #include "InitializeHistoryManager.h"
50 #include "TerminateHistoryManager.h"
51 #include "prompt.h"
52 #include "scilabRead.h"
53 #include "functions_manager.h"
54 #include "InitScilab.h"
55 #include "setenvvar.h"
56 #include "getScilabPreference.h"
57 #include "saveCWDInPreferences.h"
58 #include "h5_fileManagement.h"
59 #include "with_fftw.h"
60
61
62 #ifdef _MSC_VER
63 #include "InitializeWindows_tools.h"
64 #include "TerminateWindows_tools.h"
65 #include "WndThread.h"
66 #include "console.h"
67 #include "InnosetupMutex.h"
68 #include "MutexClosingScilab.h"
69 #include "WinConsole.h"
70 #else
71 #include "signal_mgmt.h"
72 #include "initConsoleMode.h"
73 #endif
74
75 #if defined(linux) && defined(__i386__)
76 #include "setPrecisionFPU.h"
77 #endif
78
79     /* Defined without include to avoid useless header dependency */
80     extern BOOL isItTheDisabledLib(void);
81 }
82
83 static void Add_i(void);
84 static void Add_pi(void);
85 static void Add_eps(void);
86 static void Add_e(void);
87 static void Add_s(void);
88 static void Add_z(void);
89 static void Add_gui(void);
90 static void Add_fftw(void);
91 static void Add_Nan(void);
92 static void Add_Inf(void);
93 static void Add_All_Variables(void);
94 static void Add_Double_Constant(std::wstring _szName, double _dblReal, double _dblImg, bool _bComplex);
95 static void Add_Poly_Constant(std::wstring _szName, std::wstring _szPolyVar, int _iRank, types::Double * _pdblReal);
96 static void Add_Boolean_Constant(std::wstring _szName, bool _bBool);
97 static void Add_String_Constant(std::wstring _szName, const char *_pstString);
98 static void checkForLinkerErrors(void);
99
100 static int batchMain(ScilabEngineInfo* _pSEI);
101 static int InitializeEnvironnement(void);
102 static int interactiveMain(ScilabEngineInfo* _pSEI);
103 static Parser::ControlStatus processCommand(ScilabEngineInfo* _pSEI);
104 static void stateShow(Parser::ControlStatus status);
105
106 using namespace ast;
107
108 ScilabEngineInfo* InitScilabEngineInfo()
109 {
110     // Disable all startup flags.
111     ScilabEngineInfo* pSEI = (ScilabEngineInfo*)CALLOC(1, sizeof(ScilabEngineInfo));
112
113     //Active default flags
114     pSEI->iExecAst = 1;
115     pSEI->iNoBanner = 1;
116
117     return pSEI;
118 }
119
120 int StartScilabEngine(ScilabEngineInfo* _pSEI)
121 {
122     int iMainRet = 0;
123     ConfigVariable::setStartProcessing(true);
124
125     /* This bug only occurs under Linux 32 bits
126      * See: http://wiki.scilab.org/Scilab_precision
127      */
128 #if defined(linux) && defined(__i386__)
129     setFPUToDouble();
130 #endif
131
132 #ifndef _MSC_VER
133     /* Management of the signals (seg fault, floating point exception, etc) */
134     if (getenv("SCI_DISABLE_EXCEPTION_CATCHING") == NULL)
135     {
136         base_error_init();
137     }
138 #endif
139
140 #if defined(netbsd) || defined(freebsd)
141     /* floating point exceptions */
142     fpsetmask(0);
143 #endif
144
145     Runner::init();
146
147     checkForLinkerErrors();
148
149 #ifdef _MSC_VER
150     //get current console window and hide it
151     int scilabMode = getScilabMode();
152     if (scilabMode == SCILAB_STD || scilabMode == SCILAB_NW)
153     {
154         CreateScilabHiddenWndThread();
155     }
156
157     if (scilabMode == SCILAB_STD)
158     {
159         //show banner in console window
160         CreateScilabConsole(_pSEI->iNoBanner);
161
162         if (_pSEI->iKeepConsole == 0)
163         {
164             HideScilex(); /* hide console window */
165         }
166         else
167         {
168             ShowScilex();
169         }
170     }
171     else
172     {
173         if (scilabMode == SCILAB_NW || scilabMode == SCILAB_NWNI)
174         {
175             SaveConsoleColors();
176             if (scilabMode == SCILAB_NW)
177             {
178                 RenameConsole();
179                 UpdateConsoleColors();
180             }
181         }
182     }
183
184     //create a thread for innosetup to allow reinstall during scilab running
185     createInnosetupMutex();
186 #endif
187
188     InitializeLaunchScilabSignal();
189
190     /* Scilab Startup */
191     xmlInitParser();
192     InitializeEnvironnement();
193
194     if (_pSEI->pstLang)
195     {
196         wchar_t *pwstLang = to_wide_string(_pSEI->pstLang);
197         setlanguage(pwstLang);
198         FREE(pwstLang);
199     }
200
201 #ifdef _MSC_VER
202     InitializeWindows_tools();
203 #endif
204
205     if (_pSEI->iNoJvm == 0) // With JVM
206     {
207         /* bug 3702 */
208         /* tclsci creates a TK window on Windows */
209         /* it changes focus on previous windows */
210         /* we put InitializeTclTk before InitializeGUI */
211
212         //InitializeTclTk();
213         InitializeJVM();
214         InitializeGUI();
215
216         /* create needed data structure if not already created */
217         loadGraphicModule();
218
219         loadBackGroundClassPath();
220
221         //update %gui to true
222         Add_Boolean_Constant(L"%gui", true);
223     }
224
225     /* Standard mode -> init Java Console */
226     if (_pSEI->iConsoleMode == 0)
227     {
228         /* Initialize console: lines... */
229         InitializeConsole();
230     }
231     else
232     {
233 #ifndef _MSC_VER
234         initConsoleMode(RAW);
235 #endif
236     }
237
238     //open "protection" scope to protect all variables after scilab start
239     symbol::Context::getInstance()->scope_begin();
240
241     LoadModules();
242
243     //execute scilab.start
244     if (_pSEI->iNoStart == 0)
245     {
246         StartModules();
247         execScilabStartTask(_pSEI->iSerialize != 0);
248     }
249
250     ConfigVariable::setStartProcessing(false);
251     int pause = 0;
252
253     //set prompt value
254     C2F(setprlev) (&pause);
255
256     ConfigVariable::setPromptMode(0);
257     try
258     {
259         if (_pSEI->pstExec)
260         {
261             //-e option
262
263             processCommand(_pSEI);
264             iMainRet = ConfigVariable::getExitStatus();
265         }
266         else if (_pSEI->pstFile)
267         {
268             //-f option execute exec('%s',-1)
269             char *pstCommand = (char *)MALLOC(sizeof(char) * (strlen("exec(\"\",-1)") + strlen(_pSEI->pstFile) + 1));
270             sprintf(pstCommand, "exec(\"%s\",-1)", _pSEI->pstFile);
271
272             _pSEI->pstExec = pstCommand;
273             processCommand(_pSEI);
274             FREE(pstCommand);
275             iMainRet = ConfigVariable::getExitStatus();
276             _pSEI->pstExec = NULL;
277             _pSEI->pstFile = NULL;
278         }
279     }
280     catch (const ast::ScilabException& se)
281     {
282         scilabErrorW(se.GetErrorMessage().c_str());
283     }
284
285     ConfigVariable::setPromptMode(2);
286     return iMainRet;
287 }
288
289 int RunScilabEngine(ScilabEngineInfo* _pSEI)
290 {
291     if (_pSEI->pstParseFile)
292     {
293         // Only for parsing test, won't execute anything.
294         return batchMain(_pSEI);
295     }
296     else
297     {
298         //always run as interactiveMain even after -e or -f option
299         return interactiveMain(_pSEI);
300     }
301 }
302
303 int ExecExternalCommand(ScilabEngineInfo* _pSEI)
304 {
305     if (_pSEI->pstExec)
306     {
307         processCommand(_pSEI);
308         return ConfigVariable::getExitStatus();
309     }
310
311     return -1;
312 }
313
314 void StopScilabEngine(ScilabEngineInfo* _pSEI)
315 {
316     ConfigVariable::setEndProcessing(true);
317 #ifdef _MSC_VER
318     /* bug 3672 */
319     /* Create a Mutex (closing scilab)
320      * used by files association
321      */
322     createMutexClosingScilab();
323 #endif
324
325     clearScilabPreferences();
326
327     //close "protection" scope
328     symbol::Context::getInstance()->scope_end();
329
330     //execute scilab.quit
331     if (_pSEI->pstFile)
332     {
333         //-f option execute exec('%s',-1)
334         char *pstCommand = (char *)MALLOC(sizeof(char) * (strlen("exec(\"\",-1)") + strlen(_pSEI->pstFile) + 1));
335         sprintf(pstCommand, "exec(\"%s\",-1)", _pSEI->pstFile);
336
337         _pSEI->pstExec = pstCommand;
338         processCommand(_pSEI);
339         FREE(pstCommand);
340     }
341     else if (_pSEI->iNoStart == 0)
342     {
343         execScilabQuitTask(_pSEI->iSerialize != 0);
344         //call all modules.quit
345         EndModules();
346     }
347
348     //clean context
349     symbol::Context::getInstance()->clearAll();
350     //destroy context
351     symbol::Context::destroyInstance();
352
353 #ifndef NDEBUG
354     //uncomment to print mem leak log
355     //types::Inspector::displayMemleak();
356 #endif
357
358     // cleanup Java dependent features
359     saveCWDInPreferences();
360     clearScilabPreferences();
361     TerminateHistoryManager();
362
363     // stop the JVM
364     if (_pSEI->iNoJvm == 0)
365     {
366         //dynamic_TerminateTclTk();
367         TerminateGraphics();
368         TerminateJVM();
369     }
370     /* TerminateCorePart2 */
371
372     //clear opened files
373     FileManager::destroy();
374
375     /* Remove TMPDIR before exit */
376     clearTMPDIR();
377
378     //Unload dynamic modules
379     UnloadModules();
380
381     //destroy function manager
382     destroyfunctionManagerInstance();
383     /* TerminateCorePart2 end */
384
385     /*
386     * Cleanup function for the XML library.
387     */
388     xmlCleanupParser();
389
390     /* Cleanup the parser state */
391     Parser::cleanup();
392
393 #ifdef _MSC_VER
394     TerminateWindows_tools();
395 #endif
396
397     /* Reset terminal configuration */
398     if (_pSEI->iConsoleMode)
399     {
400 #ifndef _MSC_VER
401         initConsoleMode(ATTR_RESET);
402 #endif
403     }
404
405 #ifdef _MSC_VER
406     /* close mutex (closing scilab)
407      * used by files association
408      */
409     terminateMutexClosingScilab();
410 #endif
411     ConfigVariable::setEndProcessing(false);
412 }
413
414 static Parser::ControlStatus processCommand(ScilabEngineInfo* _pSEI)
415 {
416     Parser *parser = new Parser();
417
418     parser->setParseTrace(_pSEI->iParseTrace != 0);
419     if (strcmp(_pSEI->pstExec, "") != 0)
420     {
421         wchar_t *pwstCommand = to_wide_string(_pSEI->pstExec);
422
423         /*
424          ** -*- PARSING -*-
425          */
426         parseCommandTask(parser, _pSEI->iTimed != 0, pwstCommand);
427
428         /*
429          ** -*- DUMPING TREE -*-
430          */
431         if (_pSEI->iDumpAst)
432         {
433             dumpAstTask(parser->getTree(), _pSEI->iTimed != 0);
434         }
435
436         if (parser->getExitStatus() == Parser::Succeded)
437         {
438             /*
439              ** -*- PRETTY PRINT TREE -*-
440              */
441             if (_pSEI->iPrintAst)
442             {
443                 printAstTask(parser->getTree(), _pSEI->iTimed != 0);
444             }
445
446             /*
447              ** -*- EXECUTING TREE -*-
448              */
449             if (_pSEI->iExecAst)
450             {
451                 //before calling YaspReader, try to call %onprompt function
452                 callOnPrompt();
453                 execAstTask(parser->getTree(), _pSEI->iSerialize != 0, _pSEI->iTimed != 0, _pSEI->iAstTimed != 0, _pSEI->iExecVerbose != 0);
454             }
455
456             /*
457              ** -*- DUMPING STACK AFTER EXECUTION -*-
458              */
459             if (_pSEI->iDumpStack)
460             {
461                 dumpStackTask(_pSEI->iTimed != 0);
462             }
463         }
464         else if (parser->getExitStatus() == Parser::Failed && parser->getControlStatus() == Parser::AllControlClosed)
465         {
466             if (_pSEI->iExecAst)
467             {
468                 //before calling YaspReader, try to call %onprompt function
469                 callOnPrompt();
470             }
471
472             scilabWriteW(parser->getErrorMessage());
473         }
474
475         FREE(pwstCommand);
476     }
477     else
478     {
479         if (_pSEI->iExecAst)
480         {
481             //before calling YaspReader, try to call %onprompt function
482             callOnPrompt();
483         }
484     }
485
486     Parser::ControlStatus ret = parser->getControlStatus();
487     delete parser;
488     return ret;
489 }
490
491 /*
492 ** -*- Interactive Main -*-
493 */
494 static int interactiveMain(ScilabEngineInfo* _pSEI)
495 {
496     int pause = 0;
497     char *command = NULL;
498
499     Parser::ControlStatus controlStatus = Parser::AllControlClosed;
500
501 #ifndef WITH_GUI
502 #ifndef _MSC_VER
503     if (getScilabMode() != SCILAB_NWNI)
504     {
505         fprintf(stderr, "Scilab was compiled without its GUI and advanced features. Run scilab-cli or us the -nwni option.\n");
506         initConsoleMode(ATTR_RESET);
507         exit(1);
508     }
509 #endif
510 #endif
511
512     InitializeHistoryManager();
513
514     //before calling reader, try to call %onprompt function
515     callOnPrompt();
516
517     while (!ConfigVariable::getForceQuit())
518     {
519         // Show Parser Sate before prompt
520         stateShow(controlStatus);
521
522         pause = ConfigVariable::getPauseLevel();
523
524         //set prompt value
525         C2F(setprlev) (&pause);
526
527         if (controlStatus == Parser::AllControlClosed)
528         {
529             if (command)
530             {
531                 FREE(command);
532                 command = NULL;
533             }
534
535             if (ConfigVariable::isEmptyLineShow())
536             {
537                 scilabWriteW(L"\n");
538             }
539
540             command = scilabRead();
541         }
542         else
543         {
544             char *pstRead = scilabRead();
545
546             //+1 for null termination and +1 for '\n'
547             size_t iLen = strlen(command) + strlen(pstRead) + 2;
548             char *pstNewCommand = (char *)MALLOC(iLen * sizeof(char));
549
550 #ifdef _MSC_VER
551             sprintf_s(pstNewCommand, iLen, "%s\n%s", command, pstRead);
552 #else
553             sprintf(pstNewCommand, "%s\n%s", command, pstRead);
554 #endif
555             FREE(pstRead);
556             FREE(command);
557             command = pstNewCommand;
558         }
559
560         _pSEI->pstExec = command;
561         controlStatus = processCommand(_pSEI);
562         _pSEI->pstExec = NULL;
563     }
564 #ifdef DEBUG
565     std::cerr << "To end program press [ENTER]" << std::endl;
566 #endif
567
568     FREE(command);
569     return ConfigVariable::getExitStatus();
570 }
571
572 /*
573 ** -*- Batch Main -*-
574 */
575 static int batchMain(ScilabEngineInfo* _pSEI)
576 {
577     /*
578      ** -*- PARSING -*-
579      */
580     Parser *parser = new Parser();
581
582     parser->setParseTrace(_pSEI->iParseTrace != 0);
583
584     wchar_t *pwstFileName = to_wide_string(_pSEI->pstParseFile);
585
586     /*
587      ** -*- PARSING -*-
588      */
589     parseFileTask(parser, _pSEI->iTimed != 0, pwstFileName, L"YaSp");
590
591     /*
592      ** -*- DUMPING TREE -*-
593      */
594     if (_pSEI->iDumpAst)
595     {
596         dumpAstTask(parser->getTree(), _pSEI->iTimed != 0);
597     }
598
599     if (parser->getExitStatus() == Parser::Succeded)
600     {
601         /*
602          ** -*- PRETTY PRINT TREE -*-
603          */
604         if (_pSEI->iPrintAst)
605         {
606             printAstTask(parser->getTree(), _pSEI->iTimed != 0);
607         }
608
609     }
610     else
611     {
612         scilabWriteW(parser->getErrorMessage());
613     }
614
615 #ifdef DEBUG
616     std::cerr << "To end program press [ENTER]" << std::endl;
617 #endif
618     return parser->getExitStatus();
619 }
620
621 /*
622 ** -*- stateView
623 ** Used to show parser state.
624 ** Find if we are stuck within some control structure.
625 */
626 static void stateShow(Parser::ControlStatus status)
627 {
628     switch (status)
629     {
630         case Parser::WithinFor:
631             SetTemporaryPrompt("-for       ->");
632             break;
633         case Parser::WithinWhile:
634             SetTemporaryPrompt("-while     ->");
635             break;
636         case Parser::WithinIf:
637             SetTemporaryPrompt("-if        ->");
638             break;
639         case Parser::WithinElse:
640             SetTemporaryPrompt("-else      ->");
641             break;
642         case Parser::WithinElseIf:
643             SetTemporaryPrompt("-elseif    ->");
644             break;
645         case Parser::WithinTry:
646             SetTemporaryPrompt("-try       ->");
647             break;
648         case Parser::WithinCatch:
649             SetTemporaryPrompt("-catch     ->");
650             break;
651         case Parser::WithinFunction:
652             SetTemporaryPrompt("-function  ->");
653             break;
654         case Parser::WithinSelect:
655             SetTemporaryPrompt("-select    ->");
656             break;
657         case Parser::WithinCase:
658             SetTemporaryPrompt("-case      ->");
659             break;
660         case Parser::WithinSwitch:
661             SetTemporaryPrompt("-switch    ->");
662             break;
663         case Parser::WithinOtherwise:
664             SetTemporaryPrompt("-otherwise ->");
665             break;
666         case Parser::WithinMatrix:
667             SetTemporaryPrompt("- [        ->");
668             break;
669         case Parser::WithinCell:
670             SetTemporaryPrompt("- {        ->");
671             break;
672         case Parser::WithinBlockComment:
673             SetTemporaryPrompt("- /*       ->");
674             break;
675         case Parser::WithinDots:
676             SetTemporaryPrompt("- ...      ->");
677             break;
678         case Parser::AllControlClosed:
679             //ClearTemporaryPrompt();
680             break;
681     }
682 }
683
684 static int InitializeEnvironnement(void)
685 {
686     SetScilabEnvironment();
687     InitializeLocalization();
688
689     ConfigVariable::setConsoleWidth(75);
690     ConfigVariable::setFormatSize(10);
691     ConfigVariable::setFormatMode(1);
692     Add_All_Variables();
693     FileManager::initialize();
694     initOperationArray();
695     return 0;
696 }
697
698 /*
699  * Private function to check any linker errors
700  */
701
702 static void checkForLinkerErrors(void)
703 {
704 #ifndef _MSC_VER
705     /*
706        Depending on the linking order, sometime, libs are not loaded the right way.
707        This can cause painful debugging tasks for packager or developer, we are
708        doing the check to help them.
709     */
710 #define LINKER_ERROR_1 "Scilab startup function detected that the function proposed to the engine is the wrong one. Usually, it comes from a linker problem in your distribution/OS.\n"
711 #define LINKER_ERROR_2 "If you do not know what it means, please report a bug on http://bugzilla.scilab.org/. If you do, you probably know that you should change the link order in SCI/modules/Makefile.am\n"
712
713     if (getScilabMode() != SCILAB_NWNI)
714     {
715         if (isItTheDisabledLib())
716         {
717             fprintf(stderr, LINKER_ERROR_1);
718             fprintf(stderr, "Here, Scilab should have 'libscijvm' defined but gets 'libscijvm-disable' instead.\n");
719             fprintf(stderr, LINKER_ERROR_2);
720             exit(1);
721
722         }
723     }
724     else
725     {
726         /* NWNI mode */
727         if (!isItTheDisabledLib())
728         {
729             fprintf(stderr, LINKER_ERROR_1);
730             fprintf(stderr, "Here, Scilab should have 'libscijvm-disable' defined but gets 'libscijvm' instead.\n");
731             fprintf(stderr, LINKER_ERROR_2);
732             exit(1);
733         }
734     }
735 #undef LINKER_ERROR_1
736 #undef LINKER_ERROR_2
737 #endif
738 }
739
740 static void Add_All_Variables(void)
741 {
742     Add_pi();
743     Add_eps();
744     Add_e();
745     Add_i();
746     Add_s();
747     Add_z();
748     Add_gui();
749     Add_fftw();
750     Add_Nan();
751     Add_Inf();
752 }
753
754 static void Add_Nan(void)
755 {
756     double dbl1 = -1.0;
757     double dbl0 = fabs(dbl1 - dbl1);
758
759     Add_Double_Constant(L"%nan", dbl0 / dbl0, 0, false);
760 }
761
762 static void Add_Inf(void)
763 {
764     double dbl1 = 1.0;
765     double dbl0 = dbl1 - dbl1;
766
767     Add_Double_Constant(L"%inf", dbl1 / dbl0, 0, false);
768 }
769
770 static void Add_gui(void)
771 {
772     Add_Boolean_Constant(L"%gui", false);
773 }
774
775 static void Add_fftw(void)
776 {
777     Add_Boolean_Constant(L"%fftw", withfftw() == 1);
778 }
779
780 static void Add_pi(void)
781 {
782     Add_Double_Constant(L"%pi", 3.1415926535897931159980, 0, false);
783 }
784
785 static void Add_eps(void)
786 {
787     Add_Double_Constant(L"%eps", C2F(dlamch) ("p", 1L), 0, false);
788 }
789
790 static void Add_e(void)
791 {
792     Add_Double_Constant(L"%e", 2.71828182845904530, 0, false);
793 }
794
795 static void Add_i(void)
796 {
797     Add_Double_Constant(L"%i", 0, 1, true);
798 }
799
800 static void Add_s(void)
801 {
802     Double dblCoef(1, 2);
803
804     dblCoef.set(0, 0, 0);
805     dblCoef.set(0, 1, 1);
806
807     Add_Poly_Constant(L"%s", L"s", 1, &dblCoef);
808 }
809
810 static void Add_z(void)
811 {
812     Double dblCoef(1, 2);
813
814     dblCoef.set(0, 0, 0);
815     dblCoef.set(0, 1, 1);
816
817     Add_Poly_Constant(L"%z", L"z", 1, &dblCoef);
818 }
819
820 static void Add_Poly_Constant(wstring _szName, wstring _szPolyVar, int _iRank, Double * _pdbl)
821 {
822     types::Polynom * pVar = new types::Polynom(_szPolyVar, 1, 1, &_iRank);
823     SinglePoly *poPoly = pVar->get(0);
824
825     poPoly->setCoef(_pdbl);
826     symbol::Context::getInstance()->put(symbol::Symbol(_szName), pVar);
827 }
828
829 static void Add_Double_Constant(wstring _szName, double _dblReal, double _dblImg, bool _bComplex)
830 {
831     types::Double * pVal = new types::Double(1, 1, _bComplex);
832     pVal->set(0, 0, _dblReal);
833     pVal->setImg(0, 0, _dblImg);
834     symbol::Context::getInstance()->put(symbol::Symbol(_szName), pVal);
835 }
836
837 static void Add_Boolean_Constant(wstring _szName, bool _bBool)
838 {
839     types::Bool * pVal = new types::Bool(_bBool);
840     symbol::Context::getInstance()->put(symbol::Symbol(_szName), pVal);
841 }
842
843 static void Add_String_Constant(wstring _szName, const char *_pstString)
844 {
845     types::String * ps = new types::String(_pstString);
846     symbol::Context::getInstance()->put(symbol::Symbol(_szName), ps);
847 }