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

Fixed GC marking of static sized array fields

This commit is contained in:
Brian Fiete 2022-01-22 10:38:47 -05:00
parent 46611ee8f2
commit f6e8c64a20

View file

@ -17706,8 +17706,9 @@ void BfModule::EmitIteratorBlock(bool& skipBody)
void BfModule::EmitGCMarkValue(BfTypedValue markVal, BfModuleMethodInstance markFromGCThreadMethodInstance) void BfModule::EmitGCMarkValue(BfTypedValue markVal, BfModuleMethodInstance markFromGCThreadMethodInstance)
{ {
auto fieldTypeInst = markVal.mType->ToTypeInstance(); auto fieldType = markVal.mType;
if (fieldTypeInst == NULL) auto fieldTypeInst = fieldType->ToTypeInstance();
if (fieldType == NULL)
return; return;
if (!markVal.mType->IsComposite()) if (!markVal.mType->IsComposite())
@ -17723,7 +17724,56 @@ void BfModule::EmitGCMarkValue(BfTypedValue markVal, BfModuleMethodInstance mark
args.push_back(val); args.push_back(val);
exprEvaluator.CreateCall(NULL, markFromGCThreadMethodInstance.mMethodInstance, markFromGCThreadMethodInstance.mFunc, false, args); exprEvaluator.CreateCall(NULL, markFromGCThreadMethodInstance.mMethodInstance, markFromGCThreadMethodInstance.mFunc, false, args);
} }
else if ((fieldTypeInst->IsComposite()) && (!fieldTypeInst->IsTypedPrimitive())) else if (fieldType->IsSizedArray())
{
BfSizedArrayType* sizedArrayType = (BfSizedArrayType*)fieldType;
if (sizedArrayType->mElementType->WantsGCMarking())
{
BfTypedValue arrayValue = markVal;
auto _SizedIndex = [&](BfIRValue target, BfIRValue index)
{
if (sizedArrayType->mElementType->IsSizeAligned())
{
auto ptrType = CreatePointerType(sizedArrayType->mElementType);
auto ptrValue = mBfIRBuilder->CreateBitCast(target, mBfIRBuilder->MapType(ptrType));
auto gepResult = mBfIRBuilder->CreateInBoundsGEP(ptrValue, index);
return BfTypedValue(gepResult, sizedArrayType->mElementType, BfTypedValueKind_Addr);
}
else
{
auto indexResult = CreateIndexedValue(sizedArrayType->mElementType, target, index);
return BfTypedValue(indexResult, sizedArrayType->mElementType, BfTypedValueKind_Addr);
}
};
auto intPtrType = GetPrimitiveType(BfTypeCode_IntPtr);
auto itr = CreateAlloca(intPtrType);
mBfIRBuilder->CreateStore(GetDefaultValue(intPtrType), itr);
auto loopBB = mBfIRBuilder->CreateBlock("loop", true);
auto bodyBB = mBfIRBuilder->CreateBlock("body", true);
auto doneBB = mBfIRBuilder->CreateBlock("done", true);
mBfIRBuilder->CreateBr(loopBB);
mBfIRBuilder->SetInsertPoint(loopBB);
auto loadedItr = mBfIRBuilder->CreateLoad(itr);
auto cmpRes = mBfIRBuilder->CreateCmpGTE(loadedItr, mBfIRBuilder->CreateConst(BfTypeCode_IntPtr, (uint64)sizedArrayType->mElementCount), true);
mBfIRBuilder->CreateCondBr(cmpRes, doneBB, bodyBB);
mBfIRBuilder->SetInsertPoint(bodyBB);
BfTypedValue value = _SizedIndex(arrayValue.mValue, loadedItr);
EmitGCMarkValue(value, markFromGCThreadMethodInstance);
auto incValue = mBfIRBuilder->CreateAdd(loadedItr, mBfIRBuilder->CreateConst(BfTypeCode_IntPtr, 1));
mBfIRBuilder->CreateStore(incValue, itr);
mBfIRBuilder->CreateBr(loopBB);
mBfIRBuilder->SetInsertPoint(doneBB);
}
}
else if ((fieldType->IsComposite()) && (!fieldType->IsTypedPrimitive()) && (fieldTypeInst != NULL))
{ {
auto markMemberMethodInstance = GetMethodByName(fieldTypeInst, BF_METHODNAME_MARKMEMBERS, 0, true); auto markMemberMethodInstance = GetMethodByName(fieldTypeInst, BF_METHODNAME_MARKMEMBERS, 0, true);
if (markMemberMethodInstance) if (markMemberMethodInstance)
@ -18611,21 +18661,19 @@ void BfModule::EmitGCMarkMembers()
if (!fieldInst.mFieldIncluded) if (!fieldInst.mFieldIncluded)
continue; continue;
auto fieldTypeInst = fieldInst.mResolvedType->ToTypeInstance(); auto fieldType = fieldInst.mResolvedType;
if (fieldTypeInst != NULL)
{
auto fieldDef = fieldInst.GetFieldDef(); auto fieldDef = fieldInst.GetFieldDef();
BfTypedValue markVal; BfTypedValue markVal;
if (fieldDef->mIsConst) if (fieldDef->mIsConst)
continue; continue;
if ((!fieldTypeInst->IsObjectOrInterface()) && (!fieldTypeInst->IsComposite())) if ((!fieldType->IsObjectOrInterface()) && (!fieldType->IsComposite()))
continue; continue;
mBfIRBuilder->PopulateType(fieldTypeInst); mBfIRBuilder->PopulateType(fieldType);
if (fieldTypeInst->IsValuelessType()) if (fieldType->IsValuelessType())
continue; continue;
if ((fieldDef->mIsStatic) && (!fieldDef->mIsConst)) if ((fieldDef->mIsStatic) && (!fieldDef->mIsConst))
@ -18646,7 +18694,6 @@ void BfModule::EmitGCMarkMembers()
} }
} }
} }
}
if (mCurMethodInstance->mChainType == BfMethodChainType_ChainHead) if (mCurMethodInstance->mChainType == BfMethodChainType_ChainHead)
CallChainedMethods(mCurMethodInstance, false); CallChainedMethods(mCurMethodInstance, false);