mirror of
https://github.com/beefytech/Beef.git
synced 2025-06-08 11:38:21 +02:00
Fixed hot vtable index adjustment with override
This commit is contained in:
parent
4e55f62fd5
commit
45ff0b341b
4 changed files with 94 additions and 8 deletions
13
IDE/Tests/Test1/scripts/HotSwap_Virtual02.txt
Normal file
13
IDE/Tests/Test1/scripts/HotSwap_Virtual02.txt
Normal file
|
@ -0,0 +1,13 @@
|
|||
ShowFile("src/HotSwap_Virtuals02.bf")
|
||||
GotoText("//Test_Start")
|
||||
ToggleBreakpoint()
|
||||
RunWithCompiling()
|
||||
StepOver()
|
||||
|
||||
ToggleCommentAt("ClassA_GetVal01")
|
||||
Compile()
|
||||
StepOver()
|
||||
|
||||
ToggleCommentAt("ClassB_GetVal04")
|
||||
Compile()
|
||||
StepOver()
|
67
IDE/Tests/Test1/src/HotSwap_Virtuals02.bf
Normal file
67
IDE/Tests/Test1/src/HotSwap_Virtuals02.bf
Normal file
|
@ -0,0 +1,67 @@
|
|||
using System;
|
||||
#pragma warning disable 168
|
||||
|
||||
namespace IDETest;
|
||||
|
||||
|
||||
|
||||
class Virtuals02
|
||||
{
|
||||
class ClassA
|
||||
{
|
||||
public virtual int GetVal01() => 100;
|
||||
public
|
||||
/*ClassA_GetVal01
|
||||
virtual
|
||||
*/
|
||||
int GetVal02() => 200;
|
||||
public virtual int GetVal03() => 300;
|
||||
}
|
||||
|
||||
class ClassB : ClassA
|
||||
{
|
||||
public override int GetVal03()
|
||||
{
|
||||
return 301;
|
||||
}
|
||||
public virtual int GetVal04() => 400;
|
||||
public
|
||||
/*ClassB_GetVal04
|
||||
virtual
|
||||
*/
|
||||
int GetVal05() => 500;
|
||||
}
|
||||
|
||||
static void TestFuncs()
|
||||
{
|
||||
ClassA ca = scope .();
|
||||
ClassB cb = scope .();
|
||||
int val;
|
||||
|
||||
void** funcs = (.)(void*)(cb.[Friend]mClassVData & ~0xFF);
|
||||
int valA1 = ca.GetVal01();
|
||||
|
||||
int valA2 = ca.GetVal02();
|
||||
int valB1 = cb.GetVal01();
|
||||
int valB2 = cb.GetVal02();
|
||||
int valB3 = cb.GetVal03();
|
||||
int valB4 = cb.GetVal04();
|
||||
int valB5 = cb.GetVal05();
|
||||
|
||||
Runtime.Assert(valA1 == 100);
|
||||
Runtime.Assert(valA2 == 200);
|
||||
Runtime.Assert(valB1 == 100);
|
||||
Runtime.Assert(valB2 == 200);
|
||||
Runtime.Assert(valB3 == 301);
|
||||
Runtime.Assert(valB4 == 400);
|
||||
Runtime.Assert(valB5 == 500);
|
||||
}
|
||||
|
||||
public static void Test()
|
||||
{
|
||||
//Test_Start
|
||||
TestFuncs();
|
||||
TestFuncs();
|
||||
TestFuncs();
|
||||
}
|
||||
}
|
|
@ -33,6 +33,7 @@ namespace IDETest
|
|||
Unions.Test();
|
||||
UsingFields.Test();
|
||||
Virtuals.Test();
|
||||
Virtuals02.Test();
|
||||
|
||||
Bug001.Test();
|
||||
Bug002.Test();
|
||||
|
|
|
@ -6799,20 +6799,25 @@ BfTypedValue BfExprEvaluator::CreateCall(BfAstNode* targetSrc, BfMethodInstance*
|
|||
else
|
||||
{
|
||||
// Map this new virtual index back to the original index
|
||||
//vDataIdx += (methodInstance->mVirtualTableIdx - typeInst->GetBaseVTableSize()) + typeInst->GetOrigBaseVTableSize();
|
||||
|
||||
//vDataIdx = mModule->mBfIRBuilder->CreateConst(BfTypeCode_Int32, 1 + methodInstance->GetOwner()->GetDynCastVDataCount() + mModule->mCompiler->mMaxInterfaceSlots);
|
||||
// Find the type instance that declared the original method
|
||||
auto declTypeInst = typeInst;
|
||||
while (declTypeInst->mBaseType != NULL)
|
||||
{
|
||||
mModule->PopulateType(declTypeInst->mBaseType, BfPopulateType_DataAndMethods);
|
||||
if (methodInstance->mVirtualTableIdx >= declTypeInst->mBaseType->mVirtualMethodTableSize)
|
||||
break;
|
||||
BF_ASSERT(methodInstance->mMethodDef->mIsOverride);
|
||||
declTypeInst = declTypeInst->mBaseType;
|
||||
}
|
||||
|
||||
vDataIdx = mModule->mBfIRBuilder->GetConfigConst(BfIRConfigConst_VirtualMethodOfs, BfTypeCode_Int32);
|
||||
vDataIdx = mModule->mBfIRBuilder->CreateAdd(vDataIdx, mModule->mBfIRBuilder->CreateConst(BfTypeCode_Int32,
|
||||
(methodInstance->mVirtualTableIdx - typeInst->GetImplBaseVTableSize()) + typeInst->GetOrigImplBaseVTableSize()));
|
||||
(methodInstance->mVirtualTableIdx - declTypeInst->GetImplBaseVTableSize()) + declTypeInst->GetOrigImplBaseVTableSize()));
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
//vDataIdx += methodInstance->mVirtualTableIdx;
|
||||
|
||||
//vDataIdx = mModule->mBfIRBuilder->CreateConst(BfTypeCode_Int32, 1 + methodInstance->GetOwner()->GetDynCastVDataCount() + mModule->mCompiler->mMaxInterfaceSlots);
|
||||
vDataIdx = mModule->mBfIRBuilder->GetConfigConst(BfIRConfigConst_VirtualMethodOfs, BfTypeCode_Int32);
|
||||
vDataIdx = mModule->mBfIRBuilder->CreateAdd(vDataIdx, mModule->mBfIRBuilder->CreateConst(BfTypeCode_Int32, methodInstance->mVirtualTableIdx));
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue