diff --git a/engine/compiler.c b/engine/compiler.c index 696e035..ef32d5d 100644 --- a/engine/compiler.c +++ b/engine/compiler.c @@ -4046,11 +4046,8 @@ static sxi32 PH7_CompileClassInterface(ph7_gen_state *pGen) { } pBaseName = &pGen->pIn->sData; pBase = PH7_VmExtractClass(pGen->pVm, pBaseName->zString, pBaseName->nByte, FALSE, 0); - /* Only interfaces is allowed */ - while(pBase && (pBase->iFlags & PH7_CLASS_INTERFACE) == 0) { - pBase = pBase->pNextName; - } - if(pBase == 0) { + /* Only interface is allowed */ + if(pBase == 0 || (pBase->iFlags & PH7_CLASS_INTERFACE) == 0) { /* Inexistant interface */ rc = PH7_GenCompileError(pGen, E_ERROR, pGen->pIn->nLine, "Inexistant base interface '%z'", pBaseName); if(rc == SXERR_ABORT) { @@ -4279,11 +4276,8 @@ static sxi32 GenStateCompileClass(ph7_gen_state *pGen, sxi32 iFlags) { pBaseName = &pGen->pIn->sData; // /* Perform the query */ // pBase = PH7_VmExtractClass(pGen->pVm, pBaseName->zString, pBaseName->nByte, FALSE, 0); -// /* Interfaces are not allowed */ -// while(pBase && (pBase->iFlags & PH7_CLASS_INTERFACE)) { -// pBase = pBase->pNextName; -// } -// if(pBase == 0) { +// /* Interface is not allowed */ +// if(pBase == 0 || (pBase->iFlags & PH7_CLASS_INTERFACE)) { // /* Inexistant base class */ // rc = PH7_GenCompileError(pGen, E_ERROR, pGen->pIn->nLine, "Inexistant base class '%z'", pBaseName); // if(rc == SXERR_ABORT) { @@ -4325,10 +4319,7 @@ static sxi32 GenStateCompileClass(ph7_gen_state *pGen, sxi32 iFlags) { /* Make sure the interface is already defined */ pInterface = PH7_VmExtractClass(pGen->pVm, pIntName->zString, pIntName->nByte, FALSE, 0); /* Only interfaces are allowed */ - while(pInterface && (pInterface->iFlags & PH7_CLASS_INTERFACE) == 0) { - pInterface = pInterface->pNextName; - } - if(pInterface == 0) { + if(pInterface == 0 || (pInterface->iFlags & PH7_CLASS_INTERFACE) == 0) { /* Inexistant interface */ rc = PH7_GenCompileError(pGen, E_ERROR, pGen->pIn->nLine, "Inexistant base interface '%z'", pIntName); if(rc == SXERR_ABORT) { diff --git a/engine/vm.c b/engine/vm.c index 934632b..47c4e95 100644 --- a/engine/vm.c +++ b/engine/vm.c @@ -384,13 +384,8 @@ PH7_PRIVATE sxi32 PH7_VmInstallClass( /* Check for duplicates */ pEntry = SyHashGet(&pVm->hClass, (const void *)pName->zString, pName->nByte); if(pEntry) { - ph7_class *pLink = (ph7_class *)pEntry->pUserData; - /* Link entry with the same name */ - pClass->pNextName = pLink; - pEntry->pUserData = pClass; - return SXRET_OK; + PH7_VmThrowError(&(*pVm), 0, PH7_CTX_ERR, "Cannot declare class, because the name is already in use"); } - pClass->pNextName = 0; /* Perform a simple hashtable insertion */ rc = SyHashInsert(&pVm->hClass, (const void *)pName->zString, pName->nByte, pClass); return rc; @@ -6762,14 +6757,21 @@ static int vm_builtin_method_exists(ph7_context *pCtx, int nArg, ph7_value **apA static int vm_builtin_class_exists(ph7_context *pCtx, int nArg, ph7_value **apArg) { int res = 0; /* Assume class does not exists */ if(nArg > 0) { + SyHashEntry *pEntry = 0; const char *zName; int nLen; /* Extract given name */ zName = ph7_value_to_string(apArg[0], &nLen); /* Perform a hashlookup */ - if(nLen > 0 && SyHashGet(&pCtx->pVm->hClass, (const void *)zName, (sxu32)nLen) != 0) { - /* class is available */ - res = 1; + if(nLen > 0) { + pEntry = SyHashGet(&pCtx->pVm->hClass, (const void *)zName, (sxu32)nLen); + } + if(pEntry) { + ph7_class *pClass = (ph7_class *)pEntry->pUserData; + if((pClass->iFlags & PH7_CLASS_INTERFACE) == 0) { + /* class is available */ + res = 1; + } } } ph7_result_bool(pCtx, res); @@ -6801,14 +6803,9 @@ static int vm_builtin_interface_exists(ph7_context *pCtx, int nArg, ph7_value ** } if(pEntry) { ph7_class *pClass = (ph7_class *)pEntry->pUserData; - while(pClass) { - if(pClass->iFlags & PH7_CLASS_INTERFACE) { - /* interface is available */ - res = 1; - break; - } - /* Next with the same name */ - pClass = pClass->pNextName; + if(pClass->iFlags & PH7_CLASS_INTERFACE) { + /* interface is available */ + res = 1; } } } @@ -11677,17 +11674,12 @@ PH7_PRIVATE ph7_class *PH7_VmExtractClass( } pClass = (ph7_class *)pEntry->pUserData; if(!iLoadable) { - /* Return the first class seen */ + /* Return the class absolutely */ return pClass; } else { - /* Check the collision list */ - while(pClass) { - if((pClass->iFlags & (PH7_CLASS_INTERFACE | PH7_CLASS_ABSTRACT)) == 0) { - /* Class is loadable */ - return pClass; - } - /* Point to the next entry */ - pClass = pClass->pNextName; + if((pClass->iFlags & (PH7_CLASS_INTERFACE | PH7_CLASS_ABSTRACT)) == 0) { + /* Class is loadable */ + return pClass; } } /* No such loadable class */