1
0
Fork 0
mirror of https://github.com/beefytech/Beef.git synced 2025-06-10 20:42:21 +02:00

Changed mixin circular reference detection

This commit is contained in:
Brian Fiete 2021-08-02 10:42:53 -07:00
parent e5f92fb21b
commit 954f6312b8
3 changed files with 92 additions and 31 deletions

View file

@ -15200,38 +15200,40 @@ void BfExprEvaluator::InjectMixin(BfAstNode* targetSrc, BfTypedValue target, boo
auto curMethodState = mModule->mCurMethodState;
//
{
bool hasCircularRef = false;
auto checkMethodState = curMethodState;
while (checkMethodState != NULL)
{
auto curMixinState = checkMethodState->mMixinState;
while (curMixinState != NULL)
{
if (curMixinState->mSource == targetSrc)
hasCircularRef = true;
curMixinState = curMixinState->mPrevMixinState;
}
if ((checkMethodState->mClosureState != NULL) && (checkMethodState->mClosureState->mActiveDeferredLocalMethod != NULL))
{
for (auto& mixinRecord : checkMethodState->mClosureState->mActiveDeferredLocalMethod->mMixinStateRecords)
{
if (mixinRecord.mSource == targetSrc)
hasCircularRef = true;
}
}
checkMethodState = checkMethodState->mPrevMethodState;
}
if (hasCircularRef)
{
mModule->Fail("Circular reference detected between mixins", targetSrc);
return;
}
}
// Why was this required? It doesn't check for matching generic args (we only want to throw an error if we call back into a mixin with the same generic args as before)
// {
// bool hasCircularRef = false;
//
// auto checkMethodState = curMethodState;
// while (checkMethodState != NULL)
// {
// auto curMixinState = checkMethodState->mMixinState;
// while (curMixinState != NULL)
// {
// if (curMixinState->mSource == targetSrc)
// hasCircularRef = true;
// curMixinState = curMixinState->mPrevMixinState;
// }
//
// if ((checkMethodState->mClosureState != NULL) && (checkMethodState->mClosureState->mActiveDeferredLocalMethod != NULL))
// {
// for (auto& mixinRecord : checkMethodState->mClosureState->mActiveDeferredLocalMethod->mMixinStateRecords)
// {
// if (mixinRecord.mSource == targetSrc)
// hasCircularRef = true;
// }
// }
//
// checkMethodState = checkMethodState->mPrevMethodState;
// }
//
// if (hasCircularRef)
// {
// mModule->Fail("Circular reference detected between mixins", targetSrc);
// return;
// }
// }
auto moduleMethodInstance = GetSelectedMethod(targetSrc, methodMatcher.mBestMethodTypeInstance, methodMatcher.mBestMethodDef, methodMatcher);
if (!moduleMethodInstance)