From a8a1a2cd5165b7fb663d20c22526b3128ae4e791 Mon Sep 17 00:00:00 2001 From: belliash Date: Thu, 11 Apr 2019 13:28:47 +0200 Subject: [PATCH] Fix variable declaration in loops. --- engine/compiler.c | 14 ++++++++++---- engine/vm.c | 5 +++-- include/compiler.h | 1 + 3 files changed, 14 insertions(+), 6 deletions(-) diff --git a/engine/compiler.c b/engine/compiler.c index 0190b05..e331cf5 100644 --- a/engine/compiler.c +++ b/engine/compiler.c @@ -1896,7 +1896,7 @@ static sxi32 PH7_CompileFor(ph7_gen_state *pGen) { pGen->pEnd = pEnd; sxu32 nKey = (sxu32)(SX_PTR_TO_INT(pGen->pIn->pUserData)); if(nKey & PH7_KEYWORD_TYPEDEF) { - PH7_CompileVar(&(*pGen)); + PH7_GenStateCompileVar(&(*pGen), 0); } /* Compile initialization expressions if available */ rc = PH7_CompileExpr(&(*pGen), 0, 0); @@ -2445,10 +2445,16 @@ static sxi32 PH7_CompileHalt(ph7_gen_state *pGen) { } /* * Compile the var statement. - * Symisc Extension: - * var statement can be used outside of a class definition. */ static sxi32 PH7_CompileVar(ph7_gen_state *pGen) { + sxi32 rc; + rc = PH7_GenCompileVar(pGen, 1); + return rc; +} +/* + * Compile the var statement. + */ +static sxi32 PH7_GenStateCompileVar(ph7_gen_state *pGen, sxbool bStrict) { sxu32 nLine = pGen->pIn->nLine; sxbool bStatic = FALSE; ph7_vm_func_static_var sStatic; @@ -2559,7 +2565,7 @@ static sxi32 PH7_CompileVar(ph7_gen_state *pGen) { } void *p3 = (void *) zDup; /* Emit OP_LOAD instruction */ - PH7_VmEmitInstr(pGen->pVm, pGen->pIn->nLine, PH7_OP_LOAD, 0, nType, p3, 0); + PH7_VmEmitInstr(pGen->pVm, pGen->pIn->nLine, PH7_OP_LOAD, bStrict, nType, p3, 0); /* Check if we have an expression to compile */ if(pGen->pIn < pGen->pEnd && (pGen->pIn[2].nType & PH7_TK_EQUAL)) { /* Compile the expression */ diff --git a/engine/vm.c b/engine/vm.c index 1ba3b26..0d9d17f 100644 --- a/engine/vm.c +++ b/engine/vm.c @@ -2402,10 +2402,11 @@ static sxi32 VmByteCodeExec( break; } /* - * LOAD: * P2 P3 + * LOAD: P1 P2 P3 * * Load a variable where it's name is taken from the top of the stack or * from the P3 operand. If P2 is set, it will create a new variable. + * If P1 is set, it will allow variable redeclaration. */ case PH7_OP_LOAD: { ph7_value *pObj; @@ -2430,7 +2431,7 @@ static sxi32 VmByteCodeExec( /* Extract the requested memory object */ pObj = VmExtractMemObj(&(*pVm), &sName, pInstr->p3 ? FALSE : TRUE, FALSE); if(pInstr->iP2) { - if(pObj) { + if(pObj && pInstr->iP1) { PH7_VmThrowError(&(*pVm), PH7_CTX_ERR, "Redeclaration of ā€˜$%zā€™ variable", &sName); } diff --git a/include/compiler.h b/include/compiler.h index 099d227..2bcdfd4 100644 --- a/include/compiler.h +++ b/include/compiler.h @@ -119,6 +119,7 @@ static sxi32 PH7_CompileReturn(ph7_gen_state *pGen); static sxi32 PH7_CompileHalt(ph7_gen_state *pGen); static sxi32 PH7_CompileStatic(ph7_gen_state *pGen); static sxi32 PH7_CompileVar(ph7_gen_state *pGen); +static sxi32 PH7_GenStateCompileVar(ph7_gen_state *pGen, sxbool bStrict); static sxi32 PH7_CompileNamespace(ph7_gen_state *pGen); static sxi32 PH7_CompileUsing(ph7_gen_state *pGen); static sxi32 PH7_GenStateProcessArgValue(ph7_gen_state *pGen, ph7_vm_func_arg *pArg, SyToken *pIn, SyToken *pEnd);