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

Support for sized array 'params' parameters

This commit is contained in:
Brian Fiete 2022-01-21 14:23:48 -05:00
parent c1a1baea5f
commit 939d05e401
4 changed files with 59 additions and 6 deletions

View file

@ -1865,7 +1865,7 @@ bool BfMethodMatcher::CheckMethod(BfTypeInstance* targetTypeInstance, BfTypeInst
if (methodInstance->GetParamKind(paramIdx) == BfParamKind_Params)
{
paramsParamIdx = paramIdx;
if ((wantType->IsArray()) || (wantType->IsInstanceOf(mModule->mCompiler->mSpanTypeDef)))
if ((wantType->IsArray()) || (wantType->IsSizedArray()) || (wantType->IsInstanceOf(mModule->mCompiler->mSpanTypeDef)))
wantType = wantType->GetUnderlyingType();
}
@ -1888,6 +1888,26 @@ bool BfMethodMatcher::CheckMethod(BfTypeInstance* targetTypeInstance, BfTypeInst
goto NoMatch;
}
if ((checkMethod->mParams.mSize > 0) && (methodInstance->GetParamKind(checkMethod->mParams.mSize - 1) == BfParamKind_Params))
{
// Handle `params int[C]` generic sized array params case
auto paramsType = methodInstance->GetParamType(checkMethod->mParams.mSize - 1);
if (paramsType->IsUnknownSizedArrayType())
{
auto unknownSizedArray = (BfUnknownSizedArrayType*)paramsType;
if (unknownSizedArray->mElementCountSource->IsMethodGenericParam())
{
auto genericParam = (BfGenericParamType*)unknownSizedArray->mElementCountSource;
if ((*genericArgumentsSubstitute)[genericParam->mGenericParamIdx] == NULL)
{
int paramsCount = (int)mArguments.mSize - inferParamOffset;
(*genericArgumentsSubstitute)[genericParam->mGenericParamIdx] = mModule->CreateConstExprValueType(
BfTypedValue(mModule->mBfIRBuilder->CreateConst(BfTypeCode_IntPtr, paramsCount), mModule->GetPrimitiveType(BfTypeCode_IntPtr)));
}
}
}
}
if (!deferredArgs.IsEmpty())
{
genericInferContext.InferGenericArguments(methodInstance);
@ -6915,6 +6935,7 @@ BfTypedValue BfExprEvaluator::CreateCall(BfAstNode* targetSrc, const BfTypedValu
PushArg(expandedParamsArray, irArgs);
}
continue;
}
else if (wantType->IsArray())
{
@ -6947,10 +6968,11 @@ BfTypedValue BfExprEvaluator::CreateCall(BfAstNode* targetSrc, const BfTypedValu
mModule->mBfIRBuilder->CreateAlignedStore(mModule->GetConstValue32(numElements), addr, 4);
PushArg(expandedParamsArray, irArgs);
continue;
}
else if (wantType->IsInstanceOf(mModule->mCompiler->mSpanTypeDef))
{
auto genericTypeInst = wantType->ToGenericTypeInstance();
auto genericTypeInst = wantType->ToGenericTypeInstance();
expandedParamsElementType = genericTypeInst->mGenericTypeInfo->mTypeGenericArguments[0];
expandedParamsArray = BfTypedValue(mModule->CreateAlloca(wantType), wantType, true);
@ -6959,9 +6981,26 @@ BfTypedValue BfExprEvaluator::CreateCall(BfAstNode* targetSrc, const BfTypedValu
mModule->mBfIRBuilder->CreateStore(mModule->GetConstValue(numElements), mModule->mBfIRBuilder->CreateInBoundsGEP(expandedParamsArray.mValue, 0, 2));
PushArg(expandedParamsArray, irArgs);
continue;
}
else if (wantType->IsSizedArray())
{
BfSizedArrayType* sizedArrayType = (BfSizedArrayType*)wantType;
expandedParamsElementType = wantType->GetUnderlyingType();
continue;
if (numElements != sizedArrayType->mElementCount)
{
BfAstNode* refNode = targetSrc;
if (argExprIdx < (int)argValues.size())
refNode = argValues[argExprIdx].mExpression;
mModule->Fail(StrFormat("Incorrect number of arguments to match params type '%s'", mModule->TypeToString(wantType).c_str()), refNode);
}
expandedParamsArray = BfTypedValue(mModule->CreateAlloca(wantType), wantType, true);
expandedParamAlloca = mModule->mBfIRBuilder->CreateBitCast(expandedParamsArray.mValue, mModule->mBfIRBuilder->GetPointerTo(mModule->mBfIRBuilder->MapType(expandedParamsElementType)));
PushArg(expandedParamsArray, irArgs);
continue;
}
}
}
}
@ -20828,7 +20867,7 @@ void BfExprEvaluator::PerformUnaryOperation_OnResult(BfExpression* unaryOpExpr,
auto genericTypeInst = mResult.mType->ToGenericTypeInstance();
if ((genericTypeInst != NULL) && (genericTypeInst->IsInstanceOf(mModule->mCompiler->mSpanTypeDef)))
isValid = true;
else if (mResult.mType->IsArray())
else if ((mResult.mType->IsArray()) || (mResult.mType->IsSizedArray()))
isValid = true;
if (!isValid)
{

View file

@ -22672,6 +22672,10 @@ void BfModule::DoMethodDeclaration(BfMethodDeclaration* methodDeclaration, bool
// Array is the 'normal' params type
isValid = true;
}
else if (resolvedParamType->IsSizedArray())
{
isValid = true;
}
else if ((resolvedParamType->IsDelegate()) || (resolvedParamType->IsFunction()))
{
hadDelegateParams = true;
@ -22700,7 +22704,7 @@ void BfModule::DoMethodDeclaration(BfMethodDeclaration* methodDeclaration, bool
if (genericParamInstance->mTypeConstraint != NULL)
{
auto typeInstConstraint = genericParamInstance->mTypeConstraint->ToTypeInstance();
if (genericParamInstance->mTypeConstraint->IsArray())
if ((genericParamInstance->mTypeConstraint->IsArray()) || (genericParamInstance->mTypeConstraint->IsSizedArray()))
{
BfMethodParam methodParam;
methodParam.mResolvedType = resolvedParamType;

View file

@ -1081,7 +1081,7 @@ public:
public:
bool IsGenericParam() override { return true; }
bool IsTypeGenericParam() override { return mGenericParamKind == BfGenericParamKind_Type; }
bool IsMethodGenericParam() override { return mGenericParamKind == BfGenericParamKind_Type; }
bool IsMethodGenericParam() override { return mGenericParamKind == BfGenericParamKind_Method; }
virtual bool IsUnspecializedType() override { return true; }
virtual bool IsReified() override { return false; }
};