[bug_14411] while loop fixed when using ctrl-C then abort
[scilab.git] / scilab / modules / ast / src / cpp / ast / runvisitor.cpp
1 /*
2  *  Scilab ( http://www.scilab.org/ ) - This file is part of Scilab
3  *  Copyright (C) 2014 - Scilab Enterprises - Antoine ELIAS
4  *
5  * Copyright (C) 2012 - 2016 - Scilab Enterprises
6  *
7  * This file is hereby licensed under the terms of the GNU GPL v2.0,
8  * pursuant to article 5.3.4 of the CeCILL v.2.1.
9  * This file was originally licensed under the terms of the CeCILL v2.1,
10  * and continues to be available under such terms.
11  * For more information, see the COPYING file which you should have received
12  * along with this program.
13  *
14  */
15
16 //for Visual Leak Detector in debug compilation mode
17 //#define DEBUG_VLD
18 #if defined(DEBUG_VLD) && defined(_DEBUG)
19 #include <vld.h>
20 #endif
21
22 #include <string>
23
24 #include "execvisitor.hxx"
25 #include "stepvisitor.hxx"
26 #include "timedvisitor.hxx"
27 #include "shortcutvisitor.hxx"
28 #include "printvisitor.hxx"
29 //#include "AnalysisVisitor.hxx"
30 #include "debuggervisitor.hxx"
31 #include "debugmanager.hxx"
32
33 #include "visitor_common.hxx"
34
35 #include "context.hxx"
36 #include "generic_operations.hxx"
37 #include "types_or.hxx"
38 #include "types_and.hxx"
39 #include "localization.hxx"
40
41 #include "macrofile.hxx"
42 #include "macro.hxx"
43 #include "cell.hxx"
44 #include "filemanager_interface.h"
45
46 #include "runner.hxx"
47 #include "threadmanagement.hxx"
48
49 #include "coverage_instance.hxx"
50
51 extern "C"
52 {
53 #include "sciprint.h"
54 #include "os_string.h"
55 #include "elem_common.h"
56 #include "storeCommand.h"
57 #include "prompt.h"
58 #include "scilabRead.h"
59 }
60
61 namespace ast
62 {
63 template <class T>
64 void RunVisitorT<T>::visitprivate(const StringExp & e)
65 {
66     CoverageInstance::invokeAndStartChrono((void*)&e);
67     if (e.getConstant() == nullptr)
68     {
69         types::String *psz = new types::String(e.getValue().c_str());
70         (const_cast<StringExp *>(&e))->setConstant(psz);
71     }
72     setResult(e.getConstant());
73     CoverageInstance::stopChrono((void*)&e);
74 }
75
76 template <class T>
77 void RunVisitorT<T>::visitprivate(const DoubleExp & e)
78 {
79     CoverageInstance::invokeAndStartChrono((void*)&e);
80     if (e.getConstant() == nullptr)
81     {
82         types::Double *pdbl = new types::Double(e.getValue());
83         (const_cast<DoubleExp *>(&e))->setConstant(pdbl);
84     }
85     setResult(e.getConstant());
86     CoverageInstance::stopChrono((void*)&e);
87 }
88
89 template <class T>
90 void RunVisitorT<T>::visitprivate(const BoolExp & e)
91 {
92     CoverageInstance::invokeAndStartChrono((void*)&e);
93     if (e.getConstant() == nullptr)
94     {
95         types::Bool *pB = new types::Bool(e.getValue());
96         (const_cast<BoolExp *>(&e))->setConstant(pB);
97     }
98     setResult(e.getConstant());
99     CoverageInstance::stopChrono((void*)&e);
100 }
101
102 template <class T>
103 void RunVisitorT<T>::visitprivate(const NilExp & e)
104 {
105     CoverageInstance::invokeAndStartChrono((void*)&e);
106     setResult(new types::Void());
107     CoverageInstance::stopChrono((void*)&e);
108 }
109
110 template <class T>
111 void RunVisitorT<T>::visitprivate(const SimpleVar & e)
112 {
113     CoverageInstance::invokeAndStartChrono((void*)&e);
114     symbol::Context* ctx = symbol::Context::getInstance();
115     symbol::Variable* var = ((SimpleVar&)e).getStack();
116     types::InternalType *pI = ctx->get(var);
117     setResult(pI);
118     if (pI != nullptr)
119     {
120         if (e.isVerbose() && pI->isCallable() == false && ConfigVariable::isPrintOutput())
121         {
122             std::wostringstream ostr;
123             ostr << L" " << e.getSymbol().getName() << L"  = ";
124 #ifndef NDEBUG
125             ostr << L"(" << pI->getRef() << L")";
126 #endif
127             ostr << std::endl;
128             ostr << std::endl;
129             scilabWriteW(ostr.str().c_str());
130             std::wostringstream ostrName;
131             ostrName << e.getSymbol().getName();
132             VariableToString(pI, ostrName.str().c_str());
133         }
134
135         //check if var is recalled in current scope like
136         //function f()
137         //  a; //<=> a=a;
138         //  a(2) = 18;
139         //endfunction
140         if (e.getParent()->isSeqExp())
141         {
142             if (ctx->getScopeLevel() > 1 && var->empty() == false && var->top()->m_iLevel != ctx->getScopeLevel())
143             {
144                 //put var in current scope
145                 ctx->put(var, pI);
146             }
147         }
148     }
149     else
150     {
151         char pstError[bsiz];
152         wchar_t* pwstError;
153
154         char* strErr = wide_string_to_UTF8(e.getSymbol().getName().c_str());
155
156         os_sprintf(pstError, _("Undefined variable: %s\n"), strErr);
157         pwstError = to_wide_string(pstError);
158         FREE(strErr);
159         std::wstring wstError(pwstError);
160         FREE(pwstError);
161         CoverageInstance::stopChrono((void*)&e);
162         throw InternalError(wstError, 999, e.getLocation());
163         //Err, SimpleVar doesn't exist in Scilab scopes.
164     }
165     CoverageInstance::stopChrono((void*)&e);
166 }
167
168 template <class T>
169 void RunVisitorT<T>::visitprivate(const ColonVar & e)
170 {
171     CoverageInstance::invokeAndStartChrono((void*)&e);
172     types::Colon *pC = new types::Colon();
173     setResult(pC);
174     CoverageInstance::stopChrono((void*)&e);
175 }
176
177 template <class T>
178 void RunVisitorT<T>::visitprivate(const DollarVar & e)
179 {
180     CoverageInstance::invokeAndStartChrono((void*)&e);
181     setResult(types::Polynom::Dollar());
182     CoverageInstance::stopChrono((void*)&e);
183 }
184
185 template <class T>
186 void RunVisitorT<T>::visitprivate(const BreakExp & e)
187 {
188     CoverageInstance::invokeAndStartChrono((void*)&e);
189     const_cast<BreakExp*>(&e)->setBreak();
190     CoverageInstance::stopChrono((void*)&e);
191 }
192
193 template <class T>
194 void RunVisitorT<T>::visitprivate(const ContinueExp &e)
195 {
196     CoverageInstance::invokeAndStartChrono((void*)&e);
197     const_cast<ContinueExp*>(&e)->setContinue();
198     CoverageInstance::stopChrono((void*)&e);
199 }
200
201 template <class T>
202 void RunVisitorT<T>::visitprivate(const ArrayListExp & e)
203 {
204     CoverageInstance::invokeAndStartChrono((void*)&e);
205     exps_t::const_iterator it;
206     int iNbExpSize = this->getExpectedSize();
207     this->setExpectedSize(1);
208
209     types::typed_list lstIT;
210     for (it = e.getExps().begin(); it != e.getExps().end(); it++)
211     {
212         (*it)->accept(*this);
213         for (int j = 0; j < getResultSize(); j++)
214         {
215             lstIT.push_back(getResult(j));
216         }
217     }
218
219     setResult(lstIT);
220
221     this->setExpectedSize(iNbExpSize);
222     CoverageInstance::stopChrono((void*)&e);
223 }
224
225 template <class T>
226 void RunVisitorT<T>::visitprivate(const VarDec & e)
227 {
228     CoverageInstance::invokeAndStartChrono((void*)&e);
229     try
230     {
231         /*getting what to assign*/
232         e.getInit().accept(*this);
233         getResult()->IncreaseRef();
234     }
235     catch (const InternalError& error)
236     {
237         CoverageInstance::stopChrono((void*)&e);
238         throw error;
239     }
240     CoverageInstance::stopChrono((void*)&e);
241 }
242
243 template <class T>
244 void RunVisitorT<T>::visitprivate(const CellExp & e)
245 {
246     CoverageInstance::invokeAndStartChrono((void*)&e);
247
248     exps_t::const_iterator row;
249     exps_t::const_iterator col;
250     int iColMax = 0;
251
252     exps_t lines = e.getLines();
253     //check dimmension
254     for (row = lines.begin(); row != lines.end(); ++row)
255     {
256         exps_t cols = (*row)->getAs<MatrixLineExp>()->getColumns();
257         if (iColMax == 0)
258         {
259             iColMax = static_cast<int>(cols.size());
260         }
261
262         if (iColMax != static_cast<int>(cols.size()))
263         {
264             std::wostringstream os;
265             os << _W("inconsistent row/column dimensions\n");
266             //os << ((Location)(*row)->getLocation()).getLocationString() << std::endl;
267             CoverageInstance::stopChrono((void*)&e);
268             throw InternalError(os.str(), 999, (*row)->getLocation());
269         }
270     }
271
272     //alloc result cell
273     types::Cell *pC = new types::Cell(static_cast<int>(lines.size()), iColMax);
274
275     int i = 0;
276     int j = 0;
277
278     //insert items in cell
279     for (i = 0, row = lines.begin(); row != lines.end(); ++row, ++i)
280     {
281         exps_t cols = (*row)->getAs<MatrixLineExp>()->getColumns();
282         for (j = 0, col = cols.begin(); col != cols.end(); ++col, ++j)
283         {
284             try
285             {
286                 (*col)->accept(*this);
287             }
288             catch (ScilabException &)
289             {
290                 CoverageInstance::stopChrono((void*)&e);
291                 throw;
292             }
293             types::InternalType *pIT = getResult();
294             if (pIT->isImplicitList())
295             {
296                 types::InternalType * _pIT = pIT->getAs<types::ImplicitList>()->extractFullMatrix();
297                 pC->set(i, j, _pIT);
298                 _pIT->killMe();
299             }
300             else
301             {
302                 pC->set(i, j, pIT);
303             }
304             clearResult();
305         }
306     }
307
308     //return new cell
309     setResult(pC);
310
311     CoverageInstance::stopChrono((void*)&e);
312 }
313
314 template <class T>
315 void RunVisitorT<T>::visitprivate(const FieldExp &e)
316 {
317     /*
318       a.b
319       */
320
321     CoverageInstance::invokeAndStartChrono((void*)&e);
322
323     if (!e.getTail()->isSimpleVar())
324     {
325         wchar_t szError[bsiz];
326         os_swprintf(szError, bsiz, _W("/!\\ Unmanaged FieldExp.\n").c_str());
327         CoverageInstance::stopChrono((void*)&e);
328         throw InternalError(szError, 999, e.getLocation());
329     }
330
331     try
332     {
333         e.getHead()->accept(*this);
334     }
335     catch (const InternalError& error)
336     {
337         CoverageInstance::stopChrono((void*)&e);
338         throw error;
339     }
340
341     if (getResult() == NULL)
342     {
343         wchar_t szError[bsiz];
344         os_swprintf(szError, bsiz, _W("Attempt to reference field of non-structure array.\n").c_str());
345         CoverageInstance::stopChrono((void*)&e);
346         throw InternalError(szError, 999, e.getLocation());
347     }
348
349     // TODO: handle case where getSize() > 1
350     // l=list(struct("toto","coucou"),struct("toto","hello"),1,2);[a,b]=l(1:2).toto
351     //
352     if (getResultSize() > 1)
353     {
354         clearResult();
355         wchar_t szError[bsiz];
356         os_swprintf(szError, bsiz, _W("Not yet implemented in Scilab.\n").c_str());
357         CoverageInstance::stopChrono((void*)&e);
358         throw InternalError(szError, 999, e.getLocation());
359     }
360
361     SimpleVar * psvRightMember = static_cast<SimpleVar *>(const_cast<Exp *>(e.getTail()));
362     std::wstring wstField = psvRightMember->getSymbol().getName();
363     types::InternalType * pValue = getResult();
364     types::InternalType * pReturn = NULL;
365     bool ok = false;
366
367     try
368     {
369         if (pValue->isGenericType() || pValue->isUserType())
370         {
371             ok = pValue->getAs<types::GenericType>()->extract(wstField, pReturn);
372         }
373     }
374     catch (std::wstring & err)
375     {
376         CoverageInstance::stopChrono((void*)&e);
377         throw InternalError(err.c_str(), 999, e.getTail()->getLocation());
378     }
379
380     if (ok)
381     {
382         if (pReturn == NULL)
383         {
384             std::wostringstream os;
385             os << _W("Invalid index.\n");
386             CoverageInstance::stopChrono((void*)&e);
387             throw InternalError(os.str(), 999, e.getLocation());
388         }
389
390         setResult(pReturn);
391         if (pValue->isDeletable())
392         {
393             if (pValue->isContainer())
394             {
395                 // prevent delete of pReturn in case where
396                 // extract not return a clone
397                 pReturn->IncreaseRef();
398                 pValue->killMe();
399                 pReturn->DecreaseRef();
400             }
401             else
402             {
403                 pValue->killMe();
404             }
405         }
406     }
407     else if (pValue->isFieldExtractionOverloadable())
408     {
409         types::typed_list in;
410         types::typed_list out;
411
412         types::String* pS = new types::String(wstField.c_str());
413
414         //TODO: in the case where overload is a macro there is no need to incref in
415         // because args will be put in context, removed and killed if required.
416         // But if the overload is a function... it is another story...
417
418         pS->IncreaseRef();
419         pValue->IncreaseRef();
420
421         in.push_back(pS);
422         in.push_back(pValue);
423         types::Callable::ReturnValue Ret = types::Callable::Error;
424         std::wstring stType = pValue->getShortTypeStr();
425
426         try
427         {
428             Ret = Overload::call(L"%" + stType + L"_e", in, 1, out, true);
429         }
430         catch (const InternalError& ie)
431         {
432             try
433             {
434                 //to compatibility with scilab 5 code.
435                 //tlist/mlist name are truncated to 8 first character
436                 if (stType.size() > 8)
437                 {
438                     Ret = Overload::call(L"%" + stType.substr(0, 8) + L"_e", in, 1, out, true);
439                 }
440                 else
441                 {
442                     CoverageInstance::stopChrono((void*)&e);
443                     throw ie;
444                 }
445             }
446             catch (const InternalError& ie)
447             {
448                 // TList or Mlist
449                 if (pValue->isList())
450                 {
451                     Ret = Overload::call(L"%l_e", in, 1, out, true);
452                 }
453                 else
454                 {
455                     CoverageInstance::stopChrono((void*)&e);
456                     throw ie;
457                 }
458             }
459         }
460
461         if (Ret != types::Callable::OK)
462         {
463             cleanInOut(in, out);
464             setResult(NULL);
465             CoverageInstance::stopChrono((void*)&e);
466             throw InternalError(ConfigVariable::getLastErrorMessage(), ConfigVariable::getLastErrorNumber(), e.getLocation());
467         }
468
469         setResult(out);
470         cleanIn(in, out);
471     }
472     else
473     {
474         pValue->killMe();
475         wchar_t szError[bsiz];
476         os_swprintf(szError, bsiz, _W("Attempt to reference field of non-structure array.\n").c_str());
477         CoverageInstance::stopChrono((void*)&e);
478         throw InternalError(szError, 999, e.getLocation());
479     }
480
481     CoverageInstance::stopChrono((void*)&e);
482 }
483
484 template <class T>
485 void RunVisitorT<T>::visitprivate(const IfExp  &e)
486 {
487     CoverageInstance::invokeAndStartChrono((void*)&e);
488
489     //Create local exec visitor
490     ShortCutVisitor SCTest;
491     bool bTestStatus = false;
492
493     //condition
494     try
495     {
496         e.getTest().accept(SCTest);
497         e.getTest().accept(*this);
498     }
499     catch (ScilabException &)
500     {
501         CoverageInstance::stopChrono((void*)&e);
502         throw;
503     }
504
505     bTestStatus = getResult()->isTrue();
506     clearResult();
507     try
508     {
509         if (bTestStatus == true)
510         {
511             e.getThen().accept(*this);
512         }
513         else if (e.hasElse())
514         {
515             const ast::Exp & _else = e.getElse();
516             if (_else.isCommentExp())
517             {
518                 CoverageInstance::invoke(_else);
519             }
520             else
521             {
522                 e.getElse().accept(*this);
523             }
524         }
525     }
526     catch (ScilabException &)
527     {
528         CoverageInstance::stopChrono((void*)&e);
529         throw;
530     }
531
532     if (e.isBreakable()
533             && ((&e.getElse())->isBreak()
534                 || (&e.getThen())->isBreak()))
535     {
536         const_cast<IfExp*>(&e)->setBreak();
537         const_cast<Exp*>(&e.getElse())->resetBreak();
538         const_cast<Exp*>(&e.getThen())->resetBreak();
539     }
540
541     if (e.isContinuable()
542             && ((&e.getElse())->isContinue()
543                 || (&e.getThen())->isContinue()))
544     {
545         const_cast<IfExp*>(&e)->setContinue();
546         const_cast<Exp*>(&e.getElse())->resetContinue();
547         const_cast<Exp*>(&e.getThen())->resetContinue();
548     }
549
550     if (e.isReturnable()
551             && ((&e.getElse())->isReturn()
552                 || (&e.getThen())->isReturn()))
553     {
554         const_cast<IfExp*>(&e)->setReturn();
555         const_cast<Exp*>(&e.getElse())->resetReturn();
556         const_cast<Exp*>(&e.getThen())->resetReturn();
557     }
558
559     CoverageInstance::stopChrono((void*)&e);
560 }
561
562 template <class T>
563 void RunVisitorT<T>::visitprivate(const WhileExp  &e)
564 {
565     CoverageInstance::invokeAndStartChrono((void*)&e);
566
567     //Create local exec visitor
568     ShortCutVisitor SCTest;
569
570     try
571     {
572         //manage & and | like && and ||
573         e.getTest().accept(SCTest);
574         //condition
575         e.getTest().accept(*this);
576     }
577     catch (ScilabException &)
578     {
579         CoverageInstance::stopChrono((void*)&e);
580         throw;
581     }
582
583     types::InternalType* pIT = getResult();
584
585     while (pIT->isTrue())
586     {
587         pIT->killMe();
588         setResult(NULL);
589
590         try
591         {
592             e.getBody().accept(*this);
593         }
594         catch (ScilabException &)
595         {
596             CoverageInstance::stopChrono((void*)&e);
597             throw;
598         }
599
600         //clear old result value before evaluate new one
601         if (getResult() != NULL)
602         {
603             getResult()->killMe();
604         }
605
606         if (e.getBody().isBreak())
607         {
608             const_cast<Exp*>(&(e.getBody()))->resetBreak();
609             break;
610         }
611
612         if (e.getBody().isReturn())
613         {
614             const_cast<WhileExp*>(&e)->setReturn();
615             const_cast<Exp*>(&(e.getBody()))->resetReturn();
616             break;
617         }
618
619         if (e.getBody().isContinue())
620         {
621             const_cast<Exp*>(&(e.getBody()))->resetContinue();
622         }
623
624         try
625         {
626             e.getTest().accept(*this);
627         }
628         catch (ScilabException &)
629         {
630             CoverageInstance::stopChrono((void*)&e);
631             throw;
632         }
633         pIT = getResult();
634     }
635
636     //pIT->killMe();
637     //clear result of condition or result of body
638     clearResult();
639     CoverageInstance::stopChrono((void*)&e);
640 }
641
642 template <class T>
643 void RunVisitorT<T>::visitprivate(const ForExp  &e)
644 {
645     CoverageInstance::invokeAndStartChrono((void*)&e);
646     symbol::Context* ctx = symbol::Context::getInstance();
647     //vardec visit increase its result reference
648     try
649     {
650         e.getVardec().accept(*this);
651     }
652     catch (ScilabException &)
653     {
654         CoverageInstance::stopChrono((void*)&e);
655         throw;
656     }
657     types::InternalType* pIT = getResult();
658
659     if (pIT->isImplicitList())
660     {
661         //get IL
662         types::ImplicitList* pVar = pIT->getAs<types::ImplicitList>();
663         //get IL initial Type
664         types::InternalType * pIL = pVar->getInitalType();
665         //std::cout << "for IL: " << pIL << std::endl;
666         //std::cout << "  for IV: " << pIT << std::endl;
667         //get index stack
668         symbol::Variable* var = e.getVardec().getAs<VarDec>()->getStack();
669
670         if (ctx->isprotected(var))
671         {
672             std::wostringstream os;
673             os << _W("Redefining permanent variable.\n");
674             CoverageInstance::stopChrono((void*)&e);
675             throw ast::InternalError(os.str(), 999, e.getVardec().getLocation());
676         }
677
678         ctx->put(var, pIL);
679         //use ref count to lock var against clear and detect any changes
680         pIL->IncreaseRef();
681
682         int size = static_cast<int>(pVar->getSize());
683         for (int i = 0; i < size; ++i)
684         {
685             //check if loop index has changed, deleted, copy ...
686             if (pIL->getRef() != 2)
687             {
688                 switch (pIL->getRef())
689                 {
690                     case 1:
691                         //someone clear me
692                         ctx->put(var, pIL);
693                         break;
694                     default:
695                         //someone assign me to another var
696                         //a = i;
697                         //unlock me
698                         pIL->DecreaseRef();
699
700                         //no need to destroy, it already assign to another var
701                         //pIL->killMe();
702
703                         //create a new me
704                         pIL = pVar->getInitalType();
705                         //lock loop index
706                         pIL->IncreaseRef();
707                         //update me ( must decrease ref of a )
708                         if (ctx->isprotected(var))
709                         {
710                             std::wostringstream os;
711                             os << _W("Redefining permanent variable.\n");
712                             CoverageInstance::stopChrono((void*)&e);
713                             throw ast::InternalError(os.str(), 999, e.getVardec().getLocation());
714                         }
715
716                         ctx->put(var, pIL);
717                         break;
718                 }
719             }
720
721             pVar->extractValue(i, pIL);
722
723             try
724             {
725                 e.getBody().accept(*this);
726             }
727             catch (const InternalError& ie)
728             {
729                 //unlock loop index and implicit list
730                 pIL->DecreaseRef();
731                 pIL->killMe();
732                 pIT->DecreaseRef();
733                 pIT->killMe();
734
735                 setResult(NULL);
736                 CoverageInstance::stopChrono((void*)&e);
737                 throw ie;
738             }
739
740             if (e.getBody().isBreak())
741             {
742                 const_cast<Exp&>(e.getBody()).resetBreak();
743                 break;
744             }
745
746             if (e.getBody().isContinue())
747             {
748                 const_cast<Exp&>(e.getBody()).resetContinue();
749                 continue;
750             }
751
752             if (e.getBody().isReturn())
753             {
754                 const_cast<ForExp&>(e).setReturn();
755                 const_cast<Exp&>(e.getBody()).resetReturn();
756                 break;
757             }
758         }
759
760         //unlock loop index
761         pIL->DecreaseRef();
762         pIL->killMe();
763     }
764     else if (pIT->isList())
765     {
766         types::List* pL = pIT->getAs<types::List>();
767         const int size = pL->getSize();
768         symbol::Variable* var = e.getVardec().getAs<VarDec>()->getStack();
769         for (int i = 0; i < size; ++i)
770         {
771             types::InternalType* pNew = pL->get(i);
772
773             if (ctx->isprotected(var))
774             {
775                 std::wostringstream os;
776                 os << _W("Redefining permanent variable.\n");
777                 CoverageInstance::stopChrono((void*)&e);
778                 throw ast::InternalError(os.str(), 999, e.getVardec().getLocation());
779             }
780             ctx->put(var, pNew);
781
782             try
783             {
784                 e.getBody().accept(*this);
785             }
786             catch (const InternalError& ie)
787             {
788                 //implicit list
789                 pIT->DecreaseRef();
790                 pIT->killMe();
791                 setResult(NULL);
792                 CoverageInstance::stopChrono((void*)&e);
793                 throw ie;
794             }
795
796             if (e.getBody().isBreak())
797             {
798                 const_cast<Exp*>(&(e.getBody()))->resetBreak();
799                 break;
800             }
801
802             if (e.getBody().isContinue())
803             {
804                 const_cast<Exp*>(&(e.getBody()))->resetContinue();
805                 continue;
806             }
807
808             if (e.getBody().isReturn())
809             {
810                 const_cast<ForExp*>(&e)->setReturn();
811                 const_cast<Exp&>(e.getBody()).resetReturn();
812                 break;
813             }
814         }
815     }
816     else if (pIT->isGenericType())
817     {
818         //Matrix i = [1,3,2,6] or other type
819         types::GenericType* pVar = pIT->getAs<types::GenericType>();
820         if (pVar->getDims() > 2)
821         {
822             pIT->DecreaseRef();
823             pIT->killMe();
824             CoverageInstance::stopChrono((void*)&e);
825             throw InternalError(_W("for expression can only manage 1 or 2 dimensions variables\n"), 999, e.getVardec().getLocation());
826         }
827
828         symbol::Variable* var = e.getVardec().getAs<VarDec>()->getStack();
829         for (int i = 0; i < pVar->getCols(); i++)
830         {
831             types::GenericType* pNew = pVar->getColumnValues(i);
832             if (pNew == NULL)
833             {
834                 pIT->DecreaseRef();
835                 pIT->killMe();
836                 CoverageInstance::stopChrono((void*)&e);
837                 throw InternalError(_W("for expression : Wrong type for loop iterator.\n"), 999, e.getVardec().getLocation());
838             }
839
840             if (ctx->isprotected(var))
841             {
842                 std::wostringstream os;
843                 os << _W("Redefining permanent variable.\n");
844                 CoverageInstance::stopChrono((void*)&e);
845                 throw InternalError(os.str(), 999, e.getVardec().getLocation());
846             }
847             ctx->put(var, pNew);
848
849             try
850             {
851                 e.getBody().accept(*this);
852             }
853             catch (const InternalError& ie)
854             {
855                 //implicit list
856                 pIT->DecreaseRef();
857                 pIT->killMe();
858                 setResult(NULL);
859                 CoverageInstance::stopChrono((void*)&e);
860                 throw ie;
861             }
862
863             if (e.getBody().isBreak())
864             {
865                 const_cast<Exp*>(&(e.getBody()))->resetBreak();
866                 break;
867             }
868
869             if (e.getBody().isContinue())
870             {
871                 const_cast<Exp*>(&(e.getBody()))->resetContinue();
872                 continue;
873             }
874
875             if (e.getBody().isReturn())
876             {
877                 const_cast<ForExp*>(&e)->setReturn();
878                 const_cast<Exp&>(e.getBody()).resetReturn();
879                 break;
880             }
881         }
882     }
883     else
884     {
885         pIT->DecreaseRef();
886         pIT->killMe();
887         CoverageInstance::stopChrono((void*)&e);
888         throw InternalError(_W("for expression : Wrong type for loop iterator.\n"), 999, e.getVardec().getLocation());
889     }
890
891     pIT->DecreaseRef();
892     pIT->killMe();
893
894     setResult(NULL);
895     CoverageInstance::stopChrono((void*)&e);
896 }
897
898 template <class T>
899 void RunVisitorT<T>::visitprivate(const ReturnExp &e)
900 {
901     CoverageInstance::invokeAndStartChrono((void*)&e);
902     if (e.isGlobal())
903     {
904         if (ConfigVariable::getPauseLevel() != 0 && symbol::Context::getInstance()->getScopeLevel() == ConfigVariable::getActivePauseLevel())
905         {
906             if (ConfigVariable::getEnableDebug() == true)
907             {
908                 sciprint(_("%s: function is disabled in debug mode.\n"), "resume");
909                 CoverageInstance::stopChrono((void*)&e);
910                 return;
911             }
912
913             //return or resume
914             ConfigVariable::DecreasePauseLevel();
915             CoverageInstance::stopChrono((void*)&e);
916             return;
917         }
918         else
919         {
920             const_cast<ReturnExp*>(&e)->setReturn();
921         }
922     }
923     else
924     {
925         //return(x)
926
927         if (e.getParent() == nullptr || e.getParent()->isAssignExp() == false)
928         {
929             CoverageInstance::stopChrono((void*)&e);
930             throw InternalError(_W("With input arguments, return / resume expects output arguments.\n"), 999, e.getLocation());
931         }
932         //in case of CallExp, we can return only one values
933         int iSaveExpectedSize = getExpectedSize();
934         setExpectedSize(1);
935         try
936         {
937             e.getExp().accept(*this);
938         }
939         catch (ScilabException &)
940         {
941             CoverageInstance::stopChrono((void*)&e);
942             throw;
943         }
944         setExpectedSize(iSaveExpectedSize);
945         const_cast<ReturnExp*>(&e)->setReturn();
946     }
947
948     CoverageInstance::stopChrono((void*)&e);
949 }
950
951 template <class T>
952 void RunVisitorT<T>::visitprivate(const IntSelectExp &e)
953 {
954     CoverageInstance::invokeAndStartChrono((void*)&e);
955     bool found = false;
956     //e.getSelect()->accept(*this);
957     //InternalType* pIT = getResult();
958     //setResult(nullptr);
959     //if (pIT && pIT->isDouble())
960     //{
961     //    Double * pDbl = static_cast<Double *>(pIT);
962     //    if (!pDbl->isComplex() && pDbl->getSize() == 1)
963     //    {
964     //        int64_t val;
965     //        if (analysis::tools::asInteger<int64_t>(pDbl->get(0), val))
966     //        {
967     //            Exp * exp = e.getExp(val);
968     //            found = true;
969     //            if (exp)
970     //            {
971     //                Exp * body = exp->isCaseExp() ? exp->getAs<CaseExp>()->getBody() : exp;
972     //                if (e.isBreakable())
973     //                {
974     //                    const_cast<IntSelectExp*>(&e)->resetBreak();
975     //                    body->setBreakable();
976     //                }
977
978     //                if (e.isContinuable())
979     //                {
980     //                    const_cast<IntSelectExp*>(&e)->resetContinue();
981     //                    body->setContinuable();
982     //                }
983
984     //                if (e.isReturnable())
985     //                {
986     //                    const_cast<IntSelectExp*>(&e)->resetReturn();
987     //                    body->setReturnable();
988     //                }
989
990     //                try
991     //                {
992     //                    //the good one
993     //                    body->accept(*this);
994     //                }
995     //                catch (const InternalError& ie)
996     //                {
997     //                    pIT->killMe();
998     //                    throw ie;
999     //                }
1000
1001     //                if (e.isBreakable() && body->isBreak())
1002     //                {
1003     //                    const_cast<IntSelectExp*>(&e)->setBreak();
1004     //                    body->resetBreak();
1005     //                }
1006
1007     //                if (e.isContinuable() && body->isContinue())
1008     //                {
1009     //                    const_cast<IntSelectExp*>(&e)->setContinue();
1010     //                    body->resetContinue();
1011     //                }
1012
1013     //                if (e.isReturnable() && body->isReturn())
1014     //                {
1015     //                    const_cast<IntSelectExp*>(&e)->setReturn();
1016     //                    body->resetReturn();
1017     //                }
1018     //            }
1019     //        }
1020     //    }
1021     //}
1022
1023     if (!found)
1024     {
1025         try
1026         {
1027             e.getOriginal()->accept(*this);
1028         }
1029         catch (ScilabException &)
1030         {
1031             CoverageInstance::stopChrono((void*)&e);
1032             throw;
1033         }
1034     }
1035     CoverageInstance::stopChrono((void*)&e);
1036 }
1037
1038 template <class T>
1039 void RunVisitorT<T>::visitprivate(const StringSelectExp &e)
1040 {
1041     CoverageInstance::invokeAndStartChrono((void*)&e);
1042     try
1043     {
1044         e.getSelect()->accept(*this);
1045     }
1046     catch (ScilabException &)
1047     {
1048         CoverageInstance::stopChrono((void*)&e);
1049         throw;
1050     }
1051     types::InternalType* pIT = getResult();
1052     setResult(nullptr);
1053     bool found = false;
1054     if (pIT && pIT->isString())
1055     {
1056         types::String * pStr = static_cast<types::String *>(pIT);
1057         if (pStr->getSize() == 1)
1058         {
1059             if (wchar_t * s = pStr->get(0))
1060             {
1061                 const std::wstring ws(s);
1062                 Exp * exp = e.getExp(ws);
1063                 found = true;
1064                 if (exp)
1065                 {
1066                     Exp * body = exp->isCaseExp() ? exp->getAs<CaseExp>()->getBody() : exp;
1067                     if (e.isBreakable())
1068                     {
1069                         const_cast<StringSelectExp*>(&e)->resetBreak();
1070                         body->setBreakable();
1071                     }
1072
1073                     if (e.isContinuable())
1074                     {
1075                         const_cast<StringSelectExp*>(&e)->resetContinue();
1076                         body->setContinuable();
1077                     }
1078
1079                     if (e.isReturnable())
1080                     {
1081                         const_cast<StringSelectExp*>(&e)->resetReturn();
1082                         body->setReturnable();
1083                     }
1084
1085                     try
1086                     {
1087                         //the good one
1088                         body->accept(*this);
1089                     }
1090                     catch (const InternalError& ie)
1091                     {
1092                         pIT->killMe();
1093                         CoverageInstance::stopChrono((void*)&e);
1094                         throw ie;
1095                     }
1096
1097                     if (e.isBreakable() && body->isBreak())
1098                     {
1099                         const_cast<StringSelectExp*>(&e)->setBreak();
1100                         body->resetBreak();
1101                     }
1102
1103                     if (e.isContinuable() && body->isContinue())
1104                     {
1105                         const_cast<StringSelectExp*>(&e)->setContinue();
1106                         body->resetContinue();
1107                     }
1108
1109                     if (e.isReturnable() && body->isReturn())
1110                     {
1111                         const_cast<StringSelectExp*>(&e)->setReturn();
1112                         body->resetReturn();
1113                     }
1114                 }
1115             }
1116         }
1117     }
1118
1119     if (!found)
1120     {
1121         try
1122         {
1123             e.getOriginal()->accept(*this);
1124         }
1125         catch (ScilabException &)
1126         {
1127             CoverageInstance::stopChrono((void*)&e);
1128             throw;
1129         }
1130     }
1131     CoverageInstance::stopChrono((void*)&e);
1132 }
1133
1134 template <class T>
1135 void RunVisitorT<T>::visitprivate(const SelectExp &e)
1136 {
1137     // FIXME : exec select ... case ... else ... end
1138     CoverageInstance::invokeAndStartChrono((void*)&e);
1139     try
1140     {
1141         e.getSelect()->accept(*this);
1142     }
1143     catch (ScilabException &)
1144     {
1145         CoverageInstance::stopChrono((void*)&e);
1146         throw;
1147     }
1148
1149     bool bCase = false;
1150
1151     types::InternalType* pIT = getResult();
1152     setResult(NULL);
1153     if (pIT)
1154     {
1155         // protect pIT to avoid double free when
1156         // the variable in select is override in the case
1157         pIT->IncreaseRef();
1158
1159         //find good case
1160         exps_t cases = e.getCases();
1161         for (auto exp : cases)
1162         {
1163             CaseExp * pCase = exp->getAs<CaseExp>();
1164             try
1165             {
1166                 pCase->getTest()->accept(*this);
1167             }
1168             catch (ScilabException &)
1169             {
1170                 CoverageInstance::stopChrono((void*)&e);
1171                 throw;
1172             }
1173             types::InternalType *pITCase = getResult();
1174             setResult(NULL);
1175             if (pITCase)
1176             {
1177                 if (pITCase->isContainer()) //WARNING ONLY FOR CELL
1178                 {
1179                     //check each item
1180                 }
1181                 else if (*pITCase == *pIT)
1182                 {
1183                     try
1184                     {
1185                         //the good one
1186                         pCase->getBody()->accept(*this);
1187                     }
1188                     catch (const InternalError& ie)
1189                     {
1190                         pIT->DecreaseRef();
1191                         pIT->killMe();
1192                         CoverageInstance::stopChrono((void*)&e);
1193                         throw ie;
1194                     }
1195
1196                     if (e.isBreakable() && pCase->getBody()->isBreak())
1197                     {
1198                         const_cast<SelectExp*>(&e)->setBreak();
1199                         pCase->getBody()->resetBreak();
1200                     }
1201
1202                     if (e.isContinuable() && pCase->getBody()->isContinue())
1203                     {
1204                         const_cast<SelectExp*>(&e)->setContinue();
1205                         pCase->getBody()->resetContinue();
1206                     }
1207
1208                     if (e.isReturnable() && pCase->getBody()->isReturn())
1209                     {
1210                         const_cast<SelectExp*>(&e)->setReturn();
1211                         pCase->getBody()->resetReturn();
1212                     }
1213
1214                     pITCase->killMe();
1215                     bCase = true;
1216                     break;
1217                 }
1218
1219                 pITCase->killMe();
1220             }
1221         }
1222     }
1223
1224     if (bCase == false && e.getDefaultCase() != NULL)
1225     {
1226         try
1227         {
1228             //default case
1229             e.getDefaultCase()->accept(*this);
1230         }
1231         catch (const InternalError& ie)
1232         {
1233             if (pIT)
1234             {
1235                 pIT->DecreaseRef();
1236                 pIT->killMe();
1237             }
1238             CoverageInstance::stopChrono((void*)&e);
1239             throw ie;
1240         }
1241
1242         if (e.isBreakable() && e.getDefaultCase()->isBreak())
1243         {
1244             const_cast<SelectExp*>(&e)->setBreak();
1245             e.getDefaultCase()->resetBreak();
1246         }
1247
1248         if (e.isContinuable() && e.getDefaultCase()->isContinue())
1249         {
1250             const_cast<SelectExp*>(&e)->setContinue();
1251             e.getDefaultCase()->resetContinue();
1252         }
1253
1254         if (e.isReturnable() && e.getDefaultCase()->isReturn())
1255         {
1256             const_cast<SelectExp*>(&e)->setReturn();
1257             e.getDefaultCase()->resetReturn();
1258         }
1259     }
1260
1261     clearResult();
1262
1263     if (pIT)
1264     {
1265         pIT->DecreaseRef();
1266         pIT->killMe();
1267     }
1268     CoverageInstance::stopChrono((void*)&e);
1269 }
1270
1271 template <class T>
1272 void RunVisitorT<T>::visitprivate(const NotExp &e)
1273 {
1274     CoverageInstance::invokeAndStartChrono((void*)&e);
1275     /*
1276       @ or ~ !
1277       */
1278     try
1279     {
1280         e.getExp().accept(*this);
1281     }
1282     catch (ScilabException &)
1283     {
1284         CoverageInstance::stopChrono((void*)&e);
1285         throw;
1286     }
1287
1288     types::InternalType * pValue = getResult();
1289     types::InternalType * pReturn = NULL;
1290     if (pValue->neg(pReturn))
1291     {
1292         if (pValue != pReturn)
1293         {
1294             pValue->killMe();
1295         }
1296
1297         setResult(pReturn);
1298     }
1299     else
1300     {
1301         // neg returned false so the negation is not possible so we call the overload (%foo_5)
1302         types::typed_list in;
1303         types::typed_list out;
1304
1305         pValue->IncreaseRef();
1306         in.push_back(pValue);
1307
1308         types::Callable::ReturnValue Ret = Overload::call(L"%" + pValue->getShortTypeStr() + L"_5", in, 1, out, true);
1309
1310         if (Ret != types::Callable::OK)
1311         {
1312             cleanInOut(in, out);
1313             CoverageInstance::stopChrono((void*)&e);
1314             throw InternalError(ConfigVariable::getLastErrorMessage(), ConfigVariable::getLastErrorNumber(), e.getLocation());
1315         }
1316
1317         setResult(out);
1318         cleanIn(in, out);
1319     }
1320     CoverageInstance::stopChrono((void*)&e);
1321 }
1322
1323 template <class T>
1324 void RunVisitorT<T>::visitprivate(const TransposeExp &e)
1325 {
1326     CoverageInstance::invokeAndStartChrono((void*)&e);
1327     try
1328     {
1329         e.getExp().accept(*this);
1330     }
1331     catch (ScilabException &)
1332     {
1333         CoverageInstance::stopChrono((void*)&e);
1334         throw;
1335     }
1336
1337     if (getResultSize() != 1)
1338     {
1339         clearResult();
1340         wchar_t szError[bsiz];
1341         os_swprintf(szError, bsiz, _W("%ls: Can not transpose multiple elements.\n").c_str(), L"Transpose");
1342         CoverageInstance::stopChrono((void*)&e);
1343         throw InternalError(szError, 999, e.getLocation());
1344     }
1345
1346     types::InternalType * pValue = getResult();
1347     types::InternalType * pReturn = NULL;
1348     const bool bConjug = e.getConjugate() == TransposeExp::_Conjugate_;
1349
1350     if ((bConjug && pValue->adjoint(pReturn)) || (!bConjug && pValue->transpose(pReturn)))
1351     {
1352         if (pValue != pReturn)
1353         {
1354             pValue->killMe();
1355         }
1356
1357         setResult(pReturn);
1358         CoverageInstance::stopChrono((void*)&e);
1359
1360         return;
1361     }
1362     else
1363     {
1364         // transpose returned false so the negation is not possible so we call the overload (%foo_t or %foo_0)
1365         types::typed_list in;
1366         types::typed_list out;
1367
1368         pValue->IncreaseRef();
1369         in.push_back(pValue);
1370
1371         types::Callable::ReturnValue Ret;
1372         if (bConjug)
1373         {
1374             Ret = Overload::call(L"%" + getResult()->getShortTypeStr() + L"_t", in, 1, out, true);
1375         }
1376         else
1377         {
1378             Ret = Overload::call(L"%" + getResult()->getShortTypeStr() + L"_0", in, 1, out, true);
1379         }
1380
1381         if (Ret != types::Callable::OK)
1382         {
1383             cleanInOut(in, out);
1384             CoverageInstance::stopChrono((void*)&e);
1385             throw InternalError(ConfigVariable::getLastErrorMessage(), ConfigVariable::getLastErrorNumber(), e.getLocation());
1386         }
1387
1388         setResult(out);
1389         cleanIn(in, out);
1390     }
1391
1392     CoverageInstance::stopChrono((void*)&e);
1393 }
1394
1395 template <class T>
1396 void RunVisitorT<T>::visitprivate(const FunctionDec & e)
1397 {
1398     CoverageInstance::invokeAndStartChrono((void*)&e);
1399     symbol::Context* ctx = symbol::Context::getInstance();
1400     /*
1401       function foo
1402       endfunction
1403       */
1404
1405     // funcprot(0) : do nothing
1406     // funcprot(1) && warning(on) : warning
1407     //get input parameters list
1408     std::list<symbol::Variable*> *pVarList = new std::list<symbol::Variable*>();
1409     const exps_t & vars = e.getArgs().getVars();
1410     for (const auto var : vars)
1411     {
1412         pVarList->push_back(var->getAs<SimpleVar>()->getStack());
1413     }
1414
1415     //get output parameters list
1416     std::list<symbol::Variable*> *pRetList = new std::list<symbol::Variable*>();
1417     const exps_t & rets = e.getReturns().getVars();
1418     for (const auto ret : rets)
1419     {
1420         pRetList->push_back(ret->getAs<SimpleVar>()->getStack());
1421     }
1422
1423     types::Macro *pMacro = new types::Macro(e.getSymbol().getName(), *pVarList, *pRetList,
1424                                             const_cast<SeqExp&>(static_cast<const SeqExp&>(e.getBody())), L"script");
1425     pMacro->setLines(e.getLocation().first_line, e.getLocation().last_line);
1426
1427     if (ctx->isprotected(symbol::Symbol(pMacro->getName())))
1428     {
1429         delete pMacro;
1430         std::wostringstream os;
1431         os << _W("Redefining permanent variable.\n");
1432         CoverageInstance::stopChrono((void*)&e);
1433         throw InternalError(os.str(), 999, e.getLocation());
1434     }
1435
1436     if (ctx->addMacro(pMacro) == false)
1437     {
1438         char pstError[1024];
1439         char* pstFuncName = wide_string_to_UTF8(e.getSymbol().getName().c_str());
1440         os_sprintf(pstError, _("It is not possible to redefine the %s primitive this way (see clearfun).\n"), pstFuncName);
1441         wchar_t* pwstError = to_wide_string(pstError);
1442         std::wstring wstError(pwstError);
1443         FREE(pstFuncName);
1444         FREE(pwstError);
1445         pMacro->killMe();
1446         CoverageInstance::stopChrono((void*)&e);
1447         throw InternalError(wstError, 999, e.getLocation());
1448     }
1449
1450     CoverageInstance::stopChrono((void*)&e);
1451 }
1452
1453 template <class T>
1454 void RunVisitorT<T>::visitprivate(const ListExp &e)
1455 {
1456     CoverageInstance::invokeAndStartChrono((void*)&e);
1457     try
1458     {
1459         e.getStart().accept(*this);
1460     }
1461     catch (ScilabException &)
1462     {
1463         CoverageInstance::stopChrono((void*)&e);
1464         throw;
1465     }
1466     types::GenericType* pITStart = static_cast<types::GenericType*>(getResult());
1467     if ((pITStart->getSize() != 1 || (pITStart->isDouble() && pITStart->getAs<types::Double>()->isComplex())) &&
1468             pITStart->isList() == false) // list case => call overload
1469     {
1470         pITStart->killMe();
1471         setResult(NULL);
1472         wchar_t szError[bsiz];
1473         os_swprintf(szError, bsiz, _W("%ls: Wrong type for argument %d: Real scalar expected.\n").c_str(), L"':'", 1);
1474         CoverageInstance::stopChrono((void*)&e);
1475         throw InternalError(szError, 999, e.getLocation());
1476     }
1477     types::InternalType * piStart = pITStart;
1478
1479     try
1480     {
1481         e.getStep().accept(*this);
1482     }
1483     catch (ScilabException &)
1484     {
1485         CoverageInstance::stopChrono((void*)&e);
1486         throw;
1487     }
1488     types::GenericType* pITStep = static_cast<types::GenericType*>(getResult());
1489     setResult(NULL);
1490     if ((pITStep->getSize() != 1 || (pITStep->isDouble() && pITStep->getAs<types::Double>()->isComplex())) &&
1491             pITStep->isList() == false) // list case => call overload
1492     {
1493         pITStart->killMe();
1494         pITStep->killMe();
1495         setResult(NULL);
1496         wchar_t szError[bsiz];
1497         os_swprintf(szError, bsiz, _W("%ls: Wrong type for argument %d: Real scalar expected.\n").c_str(), L"':'", 2);
1498         CoverageInstance::stopChrono((void*)&e);
1499         throw InternalError(szError, 999, e.getLocation());
1500     }
1501     types::InternalType* piStep = pITStep;
1502
1503     try
1504     {
1505         e.getEnd().accept(*this);
1506     }
1507     catch (ScilabException &)
1508     {
1509         CoverageInstance::stopChrono((void*)&e);
1510         throw;
1511     }
1512
1513     types::GenericType* pITEnd = static_cast<types::GenericType*>(getResult());
1514     setResult(NULL);
1515     if ((pITEnd->getSize() != 1 || (pITEnd->isDouble() && pITEnd->getAs<types::Double>()->isComplex())) &&
1516             pITEnd->isList() == false) // list case => call overload
1517     {
1518         pITStart->killMe();
1519         pITStep->killMe();
1520         pITEnd->killMe();
1521         setResult(NULL);
1522         wchar_t szError[bsiz];
1523         os_swprintf(szError, bsiz, _W("%ls: Wrong type for argument %d: Real scalar expected.\n").c_str(), L"':'", 3);
1524         CoverageInstance::stopChrono((void*)&e);
1525         throw InternalError(szError, 999, e.getLocation());
1526     }
1527     types::InternalType* piEnd = pITEnd;
1528
1529     ////check if implicitlist is 1:$ to replace by ':'
1530     //if (piStart->isDouble() && piStep->isDouble() && piEnd->isPoly())
1531     //{
1532     //    if (piStart->getAs<Double>()->get()[0] == 1 && piStep->getAs<Double>()->get()[0] == 1)
1533     //    {
1534     //        SinglePoly* end = piEnd->getAs<Polynom>()->get()[0];
1535     //        if (end->getRank() == 1 && end->get()[0] == 0 && end->get()[1] == 1)
1536     //        {
1537     //            setResult(new Colon());
1538     //            return;
1539     //        }
1540     //    }
1541     //}
1542
1543     //check compatibility
1544     // double : double : double or poly : poly : poly and mix like double : double : poly
1545     if ((piStart->isPoly() || piStart->isDouble()) &&
1546             (piStep->isPoly() || piStep->isDouble()) &&
1547             (piEnd->isPoly() || piEnd->isDouble()))
1548     {
1549         // No need to kill piStart, ... because Implicit list ctor will incref them
1550         setResult(new types::ImplicitList(piStart, piStep, piEnd));
1551         CoverageInstance::stopChrono((void*)&e);
1552         return;
1553     }
1554
1555     // int : double or int : int
1556     if (piStart->isInt() &&
1557             (piStep->isDouble() || piStep->isInt()) &&
1558             piEnd->isInt())
1559     {
1560         // check for same int type int8, int 16 ...
1561         if (piStart->getType() == piEnd->getType() &&
1562                 (piStart->getType() == piStep->getType() ||
1563                  piStep->isDouble()))
1564         {
1565             // No need to kill piStart, ... because Implicit list ctor will incref them
1566             setResult(new types::ImplicitList(piStart, piStep, piEnd));
1567             CoverageInstance::stopChrono((void*)&e);
1568             return;
1569         }
1570     }
1571
1572     // Call Overload
1573     types::Callable::ReturnValue Ret;
1574     types::typed_list in;
1575     types::typed_list out;
1576
1577     piStart->IncreaseRef();
1578     in.push_back(piStart);
1579
1580     try
1581     {
1582         if (e.hasExplicitStep())
1583         {
1584             // 1:2:4
1585             //call overload %typeStart_b_typeStep
1586             piStep->IncreaseRef();
1587             in.push_back(piStep);
1588             piEnd->IncreaseRef();
1589             in.push_back(piEnd);
1590             Ret = Overload::call(L"%" + piStart->getShortTypeStr() + L"_b_" + piStep->getShortTypeStr(), in, 1, out, true);
1591         }
1592         else
1593         {
1594             // 1:2
1595             //call overload %typeStart_b_typeEnd
1596             piStep->killMe();
1597             piEnd->IncreaseRef();
1598             in.push_back(piEnd);
1599             Ret = Overload::call(L"%" + piStart->getShortTypeStr() + L"_b_" + piEnd->getShortTypeStr(), in, 1, out, true);
1600         }
1601     }
1602     catch (const InternalError& error)
1603     {
1604         setResult(NULL);
1605         cleanInOut(in, out);
1606         CoverageInstance::stopChrono((void*)&e);
1607         throw error;
1608     }
1609
1610     if (Ret != types::Callable::OK)
1611     {
1612         setResult(NULL);
1613         cleanInOut(in, out);
1614         CoverageInstance::stopChrono((void*)&e);
1615         throw InternalError(ConfigVariable::getLastErrorMessage(), ConfigVariable::getLastErrorNumber(), e.getLocation());
1616     }
1617
1618     setResult(out);
1619     cleanIn(in, out);
1620     CoverageInstance::stopChrono((void*)&e);
1621 }
1622
1623 template <class T>
1624 void RunVisitorT<T>::visitprivate(const OptimizedExp &e)
1625 {
1626 }
1627
1628 template <class T>
1629 void RunVisitorT<T>::visitprivate(const MemfillExp &e)
1630 {
1631     CoverageInstance::invokeAndStartChrono((void*)&e);
1632     try
1633     {
1634         e.getOriginal()->accept(*this);
1635     }
1636     catch (ScilabException &)
1637     {
1638         CoverageInstance::stopChrono((void*)&e);
1639         throw;
1640     }
1641 }
1642
1643 template <class T>
1644 void RunVisitorT<T>::visitprivate(const DAXPYExp &e)
1645 {
1646     CoverageInstance::invokeAndStartChrono((void*)&e);
1647     types::InternalType* pIT = NULL;
1648     types::Double* ad = NULL;
1649     int ar = 0;
1650     int ac = 0;
1651
1652     types::Double* xd = NULL;
1653     int xr = 0;
1654     int xc = 0;
1655
1656     types::Double* yd = NULL;
1657     int yr = 0;
1658     int yc = 0;
1659
1660     //check types and dimensions
1661
1662     //y must be double
1663     const Exp &ye = e.getY();
1664     try
1665     {
1666         ye.accept(*this);
1667     }
1668     catch (ScilabException &)
1669     {
1670         CoverageInstance::stopChrono((void*)&e);
1671         throw;
1672     }
1673
1674     pIT = getResult();
1675     if (pIT->isDouble())
1676     {
1677         yd = pIT->getAs<types::Double>();
1678         if (yd->getDims() == 2 && yd->isComplex() == false)
1679         {
1680             yr = yd->getRows();
1681             yc = yd->getCols();
1682         }
1683         else
1684         {
1685             yd->killMe();
1686             try
1687             {
1688                 e.getOriginal()->accept(*this);
1689             }
1690             catch (ScilabException &)
1691             {
1692                 CoverageInstance::stopChrono((void*)&e);
1693                 throw;
1694             }
1695             CoverageInstance::stopChrono((void*)&e);
1696             return;
1697         }
1698     }
1699     else
1700     {
1701         pIT->killMe();
1702         try
1703         {
1704             e.getOriginal()->accept(*this);
1705         }
1706         catch (ScilabException &)
1707         {
1708             CoverageInstance::stopChrono((void*)&e);
1709             throw;
1710         }
1711         CoverageInstance::stopChrono((void*)&e);
1712         return;
1713     }
1714
1715     //x
1716     const Exp &xe = e.getX();
1717     try
1718     {
1719         xe.accept(*this);
1720     }
1721     catch (ScilabException &)
1722     {
1723         CoverageInstance::stopChrono((void*)&e);
1724         throw;
1725     }
1726     pIT = getResult();
1727
1728     if (pIT->isDouble())
1729     {
1730         xd = pIT->getAs<types::Double>();
1731         if (xd->isScalar() && xd->isComplex() == false)
1732         {
1733             // x become a
1734             ad = xd;
1735             ar = 1;
1736             ac = 1;
1737         }
1738         else if (xd->getDims() == 2 && xd->isComplex() == false)
1739         {
1740             xr = xd->getRows();
1741             xc = xd->getCols();
1742         }
1743         else
1744         {
1745             yd->killMe();
1746             xd->killMe();
1747             try
1748             {
1749                 e.getOriginal()->accept(*this);
1750             }
1751             catch (ScilabException &)
1752             {
1753                 CoverageInstance::stopChrono((void*)&e);
1754                 throw;
1755             }
1756             CoverageInstance::stopChrono((void*)&e);
1757             return;
1758         }
1759     }
1760     else
1761     {
1762         pIT->killMe();
1763         yd->killMe();
1764         try
1765         {
1766             e.getOriginal()->accept(*this);
1767         }
1768         catch (ScilabException &)
1769         {
1770             CoverageInstance::stopChrono((void*)&e);
1771             throw;
1772         }
1773         CoverageInstance::stopChrono((void*)&e);
1774         return;
1775     }
1776
1777     const Exp &ae = e.getA();
1778     try
1779     {
1780         ae.accept(*this);
1781     }
1782     catch (ScilabException &)
1783     {
1784         CoverageInstance::stopChrono((void*)&e);
1785         throw;
1786     }
1787     pIT = getResult();
1788
1789     if (pIT->isDouble())
1790     {
1791         if (ad)
1792         {
1793             xd = pIT->getAs<types::Double>();
1794             //X is scalar it become A
1795             //now use A as X
1796             if (xd->getDims() == 2 && xd->isComplex() == false)
1797             {
1798                 xr = xd->getRows();
1799                 xc = xd->getCols();
1800             }
1801             else
1802             {
1803                 yd->killMe();
1804                 xd->killMe();
1805                 ad->killMe();
1806                 try
1807                 {
1808                     e.getOriginal()->accept(*this);
1809                 }
1810                 catch (ScilabException &)
1811                 {
1812                     CoverageInstance::stopChrono((void*)&e);
1813                     throw;
1814                 }
1815                 CoverageInstance::stopChrono((void*)&e);
1816                 return;
1817             }
1818         }
1819         else
1820         {
1821             //a is a and it must be scalar
1822             ad = pIT->getAs<types::Double>();
1823             if (/*ad->isScalar() && */ad->isComplex() == false)
1824             {
1825                 ar = ad->getRows(); //1;
1826                 ac = ad->getCols();//1;
1827             }
1828             else
1829             {
1830                 yd->killMe();
1831                 xd->killMe();
1832                 ad->killMe();
1833                 try
1834                 {
1835                     e.getOriginal()->accept(*this);
1836                 }
1837                 catch (ScilabException &)
1838                 {
1839                     CoverageInstance::stopChrono((void*)&e);
1840                     throw;
1841                 }
1842                 throw;
1843                 return;
1844             }
1845         }
1846     }
1847     else
1848     {
1849         pIT->killMe();
1850         yd->killMe();
1851         xd->killMe();
1852         try
1853         {
1854             e.getOriginal()->accept(*this);
1855         }
1856         catch (ScilabException &)
1857         {
1858             CoverageInstance::stopChrono((void*)&e);
1859             throw;
1860         }
1861         CoverageInstance::stopChrono((void*)&e);
1862         return;
1863     }
1864
1865     // If we get here we are certain that ad, xd & yd have been set
1866     if (ac == 1 &&
1867             ar == 1 &&
1868             xr == yr &&
1869             xc == yc)
1870     {
1871         //go !
1872         int one = 1;
1873         int size = xc * xr;
1874         //Double* od = (Double*)yd->clone();
1875         C2F(daxpy)(&size, ad->get(), xd->get(), &one, yd->get(), &one);
1876         //setResult(od);
1877         //yd->killMe();
1878         xd->killMe();
1879         ad->killMe();
1880         CoverageInstance::stopChrono((void*)&e);
1881         return;
1882     }
1883     else if (ac == xr && ar == yr && xc == yc)
1884     {
1885         char n = 'n';
1886         double one = 1;
1887         C2F(dgemm)(&n, &n, &ar, &xc, &ac, &one, ad->get(), &ar, xd->get(), &ac, &one, yd->get(), &ar);
1888         xd->killMe();
1889         ad->killMe();
1890         CoverageInstance::stopChrono((void*)&e);
1891         return;
1892     }
1893
1894     yd->killMe();
1895     xd->killMe();
1896     ad->killMe();
1897
1898     try
1899     {
1900         e.getOriginal()->accept(*this);
1901     }
1902     catch (ScilabException &)
1903     {
1904         CoverageInstance::stopChrono((void*)&e);
1905         throw;
1906     }
1907     CoverageInstance::stopChrono((void*)&e);
1908
1909     return;
1910 }
1911
1912 template <class T>
1913 void RunVisitorT<T>::visitprivate(const TryCatchExp  &e)
1914 {
1915     CoverageInstance::invokeAndStartChrono((void*)&e);
1916     //save current prompt mode
1917     bool oldVal = ConfigVariable::isSilentError();
1918     int oldMode = ConfigVariable::getPromptMode();
1919     //set mode silent for errors
1920     ConfigVariable::setSilentError(true);
1921
1922     symbol::Context* pCtx = symbol::Context::getInstance();
1923     try
1924     {
1925         int scope = pCtx->getScopeLevel();
1926         int level = ConfigVariable::getRecursionLevel();
1927         try
1928         {
1929             e.getTry().accept(*this);
1930             //restore previous prompt mode
1931             ConfigVariable::setSilentError(oldVal);
1932         }
1933         catch (const RecursionException& /* re */)
1934         {
1935             ConfigVariable::setPromptMode(oldMode);
1936
1937             //close opened scope during try
1938             while (pCtx->getScopeLevel() > scope)
1939             {
1940                 pCtx->scope_end();
1941             }
1942
1943             //decrease recursion to init value and close where
1944             while (ConfigVariable::getRecursionLevel() > level)
1945             {
1946                 ConfigVariable::where_end();
1947                 ConfigVariable::decreaseRecursion();
1948             }
1949
1950             //print msg about recursion limit and trigger an error
1951             wchar_t sz[1024];
1952             os_swprintf(sz, 1024, _W("Recursion limit reached (%d).\n").data(), ConfigVariable::getRecursionLimit());
1953             CoverageInstance::stopChrono((void*)&e);
1954             throw ast::InternalError(sz);
1955         }
1956
1957     }
1958     catch (const InternalError& /* ie */)
1959     {
1960         //restore previous prompt mode
1961         ConfigVariable::setSilentError(oldVal);
1962         //to lock lasterror
1963         ConfigVariable::setLastErrorCall();
1964         // reset call stack filled when error occured
1965         ConfigVariable::resetWhereError();
1966         try
1967         {
1968             e.getCatch().accept(*this);
1969         }
1970         catch (ScilabException &)
1971         {
1972             CoverageInstance::stopChrono((void*)&e);
1973             throw;
1974         }
1975     }
1976     CoverageInstance::stopChrono((void*)&e);
1977 }
1978
1979
1980 } /* namespace ast */
1981
1982 #include "run_SeqExp.hpp"
1983 #include "run_CallExp.hpp"
1984 #include "run_MatrixExp.hpp"
1985 #include "run_OpExp.hpp"
1986 #include "run_AssignExp.hpp"
1987
1988 template EXTERN_AST class ast::RunVisitorT<ast::ExecVisitor>;
1989 template EXTERN_AST class ast::RunVisitorT<ast::StepVisitor>;
1990 template EXTERN_AST class ast::RunVisitorT<ast::TimedVisitor>;
1991 template EXTERN_AST class ast::RunVisitorT<ast::DebuggerVisitor>;