mirror of
https://github.com/beefytech/Beef.git
synced 2025-06-10 04:22:20 +02:00
Added comptype test
This commit is contained in:
parent
83069fa216
commit
8435caf340
8 changed files with 87 additions and 47 deletions
|
@ -2912,6 +2912,9 @@ BfType* BfExprEvaluator::BindGenericType(BfAstNode* node, BfType* bindType)
|
||||||
if (!bindType->IsGenericParam())
|
if (!bindType->IsGenericParam())
|
||||||
return bindType;
|
return bindType;
|
||||||
|
|
||||||
|
if (genericTypeBindings == NULL)
|
||||||
|
return bindType;
|
||||||
|
|
||||||
(*genericTypeBindings)[nodeId] = bindType;
|
(*genericTypeBindings)[nodeId] = bindType;
|
||||||
return bindType;
|
return bindType;
|
||||||
}
|
}
|
||||||
|
@ -5338,6 +5341,10 @@ BfTypedValue BfExprEvaluator::CreateCall(BfAstNode* targetSrc, BfMethodInstance*
|
||||||
// This either generated an error already or this is just the non-const type check pass for a comptime-only method
|
// This either generated an error already or this is just the non-const type check pass for a comptime-only method
|
||||||
doConstReturn = true;
|
doConstReturn = true;
|
||||||
}
|
}
|
||||||
|
else if ((mBfEvalExprFlags & BfEvalExprFlags_DisallowComptime) != 0)
|
||||||
|
{
|
||||||
|
doConstReturn = true;
|
||||||
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
CeEvalFlags evalFlags = CeEvalFlags_None;
|
CeEvalFlags evalFlags = CeEvalFlags_None;
|
||||||
|
|
|
@ -2890,6 +2890,7 @@ BfError* BfModule::Fail(const StringImpl& error, BfAstNode* refNode, bool isPers
|
||||||
return true;
|
return true;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
bool hadMethodInstance = false;
|
||||||
if (mCurMethodState != NULL)
|
if (mCurMethodState != NULL)
|
||||||
{
|
{
|
||||||
auto checkMethodState = mCurMethodState;
|
auto checkMethodState = mCurMethodState;
|
||||||
|
@ -2902,12 +2903,14 @@ BfError* BfModule::Fail(const StringImpl& error, BfAstNode* refNode, bool isPers
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
hadMethodInstance = true;
|
||||||
if (!_CheckMethodInstance(methodInstance))
|
if (!_CheckMethodInstance(methodInstance))
|
||||||
return NULL;
|
return NULL;
|
||||||
checkMethodState = checkMethodState->mPrevMethodState;
|
checkMethodState = checkMethodState->mPrevMethodState;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (mCurMethodInstance != NULL)
|
|
||||||
|
if ((!hadMethodInstance) && (mCurMethodInstance != NULL))
|
||||||
{
|
{
|
||||||
if (!_CheckMethodInstance(mCurMethodInstance))
|
if (!_CheckMethodInstance(mCurMethodInstance))
|
||||||
return NULL;
|
return NULL;
|
||||||
|
@ -7225,7 +7228,11 @@ void BfModule::ResolveGenericParamConstraints(BfGenericParamInstance* genericPar
|
||||||
bfAutocomplete->CheckTypeRef(constraintTypeRef, true);
|
bfAutocomplete->CheckTypeRef(constraintTypeRef, true);
|
||||||
//TODO: Constraints may refer to other generic params (of either type or method)
|
//TODO: Constraints may refer to other generic params (of either type or method)
|
||||||
// TO allow resolution, perhaps move this generic param initalization into GetMethodInstance (passing a genericPass bool)
|
// TO allow resolution, perhaps move this generic param initalization into GetMethodInstance (passing a genericPass bool)
|
||||||
auto constraintType = ResolveTypeRef(constraintTypeRef, BfPopulateType_Declaration, BfResolveTypeRefFlag_AllowGenericMethodParamConstValue);
|
|
||||||
|
BfResolveTypeRefFlags resolveFlags = BfResolveTypeRefFlag_AllowGenericMethodParamConstValue;
|
||||||
|
if (isUnspecialized)
|
||||||
|
resolveFlags = (BfResolveTypeRefFlags)(resolveFlags | BfResolveTypeRefFlag_DisallowComptime);
|
||||||
|
auto constraintType = ResolveTypeRef(constraintTypeRef, BfPopulateType_Declaration, resolveFlags);
|
||||||
if (constraintType != NULL)
|
if (constraintType != NULL)
|
||||||
{
|
{
|
||||||
if ((constraintDef->mGenericParamFlags & BfGenericParamFlag_Const) != 0)
|
if ((constraintDef->mGenericParamFlags & BfGenericParamFlag_Const) != 0)
|
||||||
|
@ -17881,8 +17888,7 @@ void BfModule::ProcessMethod(BfMethodInstance* methodInstance, bool isInlineDup)
|
||||||
}
|
}
|
||||||
|
|
||||||
SetAndRestoreValue<bool> prevIgnoreWrites(mBfIRBuilder->mIgnoreWrites, mWantsIRIgnoreWrites || methodInstance->mIsUnspecialized);
|
SetAndRestoreValue<bool> prevIgnoreWrites(mBfIRBuilder->mIgnoreWrites, mWantsIRIgnoreWrites || methodInstance->mIsUnspecialized);
|
||||||
bool ignoreWrites = mBfIRBuilder->mIgnoreWrites;
|
|
||||||
|
|
||||||
if ((HasCompiledOutput()) && (!mBfIRBuilder->mIgnoreWrites))
|
if ((HasCompiledOutput()) && (!mBfIRBuilder->mIgnoreWrites))
|
||||||
{
|
{
|
||||||
BF_ASSERT(!methodInstance->mIRFunction.IsFake() || (methodInstance->GetImportCallKind() != BfImportCallKind_None));
|
BF_ASSERT(!methodInstance->mIRFunction.IsFake() || (methodInstance->GetImportCallKind() != BfImportCallKind_None));
|
||||||
|
@ -17953,6 +17959,9 @@ void BfModule::ProcessMethod(BfMethodInstance* methodInstance, bool isInlineDup)
|
||||||
auto methodDef = methodInstance->mMethodDef;
|
auto methodDef = methodInstance->mMethodDef;
|
||||||
auto methodDeclaration = methodDef->GetMethodDeclaration();
|
auto methodDeclaration = methodDef->GetMethodDeclaration();
|
||||||
|
|
||||||
|
if ((methodDef->mHasComptime) && (!mIsComptimeModule))
|
||||||
|
mBfIRBuilder->mIgnoreWrites = true;
|
||||||
|
|
||||||
if ((methodInstance->mIsReified) && (methodInstance->mVirtualTableIdx != -1))
|
if ((methodInstance->mIsReified) && (methodInstance->mVirtualTableIdx != -1))
|
||||||
{
|
{
|
||||||
// If we reify a virtual method in a HotCompile then we need to make sure the type data gets written out
|
// If we reify a virtual method in a HotCompile then we need to make sure the type data gets written out
|
||||||
|
@ -18320,7 +18329,7 @@ void BfModule::ProcessMethod(BfMethodInstance* methodInstance, bool isInlineDup)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
bool wantsDIData = (mBfIRBuilder->DbgHasInfo()) && (!methodDef->IsEmptyPartial()) && (!mCurMethodInstance->mIsUnspecialized) && (mHasFullDebugInfo);
|
bool wantsDIData = (mBfIRBuilder->DbgHasInfo()) && (!methodDef->IsEmptyPartial()) && (!mBfIRBuilder->mIgnoreWrites) && (mHasFullDebugInfo);
|
||||||
if (methodDef->mMethodType == BfMethodType_Mixin)
|
if (methodDef->mMethodType == BfMethodType_Mixin)
|
||||||
wantsDIData = false;
|
wantsDIData = false;
|
||||||
|
|
||||||
|
@ -19709,7 +19718,7 @@ void BfModule::ProcessMethod(BfMethodInstance* methodInstance, bool isInlineDup)
|
||||||
mBfIRBuilder->MoveBlockToEnd(mCurMethodState->mIRExitBlock);
|
mBfIRBuilder->MoveBlockToEnd(mCurMethodState->mIRExitBlock);
|
||||||
mBfIRBuilder->SetInsertPoint(mCurMethodState->mIRExitBlock);
|
mBfIRBuilder->SetInsertPoint(mCurMethodState->mIRExitBlock);
|
||||||
|
|
||||||
if (!mCurMethodState->mDIRetVal)
|
if ((!mCurMethodState->mDIRetVal) && (wantsDIData))
|
||||||
CreateDIRetVal();
|
CreateDIRetVal();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -19807,8 +19816,8 @@ void BfModule::ProcessMethod(BfMethodInstance* methodInstance, bool isInlineDup)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Avoid linking any internal funcs that were just supposed to be comptime-accessible
|
// Avoid linking any internal funcs that were just supposed to be comptime-accessible
|
||||||
if ((methodDef->mHasComptime) && (!mIsComptimeModule))
|
/*if ((methodDef->mHasComptime) && (!mIsComptimeModule))
|
||||||
wantsRemoveBody = true;
|
wantsRemoveBody = true;*/
|
||||||
|
|
||||||
if ((hasExternSpecifier) && (!skipBody))
|
if ((hasExternSpecifier) && (!skipBody))
|
||||||
{
|
{
|
||||||
|
|
|
@ -73,9 +73,10 @@ enum BfEvalExprFlags
|
||||||
BfEvalExprFlags_StringInterpolateFormat = 0x20000,
|
BfEvalExprFlags_StringInterpolateFormat = 0x20000,
|
||||||
BfEvalExprFlags_NoLookupError = 0x40000,
|
BfEvalExprFlags_NoLookupError = 0x40000,
|
||||||
BfEvalExprFlags_Comptime = 0x80000,
|
BfEvalExprFlags_Comptime = 0x80000,
|
||||||
BfEvalExprFlags_InCascade = 0x100000,
|
BfEvalExprFlags_DisallowComptime = 0x100000,
|
||||||
BfEvalExprFlags_InferReturnType = 0x200000,
|
BfEvalExprFlags_InCascade = 0x200000,
|
||||||
BfEvalExprFlags_WasMethodRef = 0x400000
|
BfEvalExprFlags_InferReturnType = 0x400000,
|
||||||
|
BfEvalExprFlags_WasMethodRef = 0x800000
|
||||||
};
|
};
|
||||||
|
|
||||||
enum BfCastFlags
|
enum BfCastFlags
|
||||||
|
|
|
@ -9350,7 +9350,7 @@ BfType* BfModule::ResolveTypeRef(BfTypeReference* typeRef, BfPopulateType popula
|
||||||
}
|
}
|
||||||
|
|
||||||
BfResolvedTypeSet::LookupContext lookupCtx;
|
BfResolvedTypeSet::LookupContext lookupCtx;
|
||||||
lookupCtx.mResolveFlags = (BfResolveTypeRefFlags)(resolveFlags & (BfResolveTypeRefFlag_NoCreate | BfResolveTypeRefFlag_IgnoreLookupError));
|
lookupCtx.mResolveFlags = (BfResolveTypeRefFlags)(resolveFlags & (BfResolveTypeRefFlag_NoCreate | BfResolveTypeRefFlag_IgnoreLookupError | BfResolveTypeRefFlag_DisallowComptime));
|
||||||
lookupCtx.mRootTypeRef = typeRef;
|
lookupCtx.mRootTypeRef = typeRef;
|
||||||
lookupCtx.mRootTypeDef = typeDef;
|
lookupCtx.mRootTypeDef = typeDef;
|
||||||
lookupCtx.mModule = this;
|
lookupCtx.mModule = this;
|
||||||
|
|
|
@ -3427,10 +3427,21 @@ int BfResolvedTypeSet::Hash(BfTypeReference* typeRef, LookupContext* ctx, BfHash
|
||||||
SetAndRestoreValue<bool> ignoreWrites(ctx->mModule->mBfIRBuilder->mIgnoreWrites, true);
|
SetAndRestoreValue<bool> ignoreWrites(ctx->mModule->mBfIRBuilder->mIgnoreWrites, true);
|
||||||
SetAndRestoreValue<bool> allowUninitReads(ctx->mModule->mCurMethodState->mAllowUinitReads, true);
|
SetAndRestoreValue<bool> allowUninitReads(ctx->mModule->mCurMethodState->mAllowUinitReads, true);
|
||||||
|
|
||||||
|
BfEvalExprFlags exprFlags = BfEvalExprFlags_None;
|
||||||
|
if ((ctx->mResolveFlags & BfResolveTypeRefFlag_DisallowComptime) != 0)
|
||||||
|
{
|
||||||
|
exprFlags = (BfEvalExprFlags)(exprFlags | BfEvalExprFlags_DisallowComptime);
|
||||||
|
}
|
||||||
|
|
||||||
if (exprModTypeRef->mToken->mToken == BfToken_Comptype)
|
if (exprModTypeRef->mToken->mToken == BfToken_Comptype)
|
||||||
result = ctx->mModule->CreateValueFromExpression(exprModTypeRef->mTarget, ctx->mModule->ResolveTypeDef(ctx->mModule->mCompiler->mTypeTypeDef), BfEvalExprFlags_Comptime);
|
{
|
||||||
|
exprFlags = (BfEvalExprFlags)(exprFlags | BfEvalExprFlags_Comptime);
|
||||||
|
result = ctx->mModule->CreateValueFromExpression(exprModTypeRef->mTarget, ctx->mModule->ResolveTypeDef(ctx->mModule->mCompiler->mTypeTypeDef), exprFlags);
|
||||||
|
}
|
||||||
else
|
else
|
||||||
|
{
|
||||||
result = ctx->mModule->CreateValueFromExpression(exprModTypeRef->mTarget);
|
result = ctx->mModule->CreateValueFromExpression(exprModTypeRef->mTarget);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((result) && (exprModTypeRef->mToken->mToken == BfToken_Comptype))
|
if ((result) && (exprModTypeRef->mToken->mToken == BfToken_Comptype))
|
||||||
|
|
|
@ -31,7 +31,8 @@ enum BfResolveTypeRefFlags
|
||||||
BfResolveTypeRefFlag_Attribute = 0x100,
|
BfResolveTypeRefFlag_Attribute = 0x100,
|
||||||
BfResolveTypeRefFlag_NoReify = 0x200,
|
BfResolveTypeRefFlag_NoReify = 0x200,
|
||||||
BfResolveTypeRefFlag_NoCreate = 0x400,
|
BfResolveTypeRefFlag_NoCreate = 0x400,
|
||||||
BfResolveTypeRefFlag_NoWarnOnMut = 0x800
|
BfResolveTypeRefFlag_NoWarnOnMut = 0x800,
|
||||||
|
BfResolveTypeRefFlag_DisallowComptime = 0x1000
|
||||||
};
|
};
|
||||||
|
|
||||||
enum BfTypeNameFlags : uint16
|
enum BfTypeNameFlags : uint16
|
||||||
|
|
|
@ -74,38 +74,21 @@ namespace Tests
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
struct DoublingEnumerator<TElem, TEnum> : IEnumerator<TElem>
|
static Type GetBiggerType(Type t)
|
||||||
where TElem : operator TElem + TElem
|
|
||||||
where TEnum : concrete, IEnumerator<TElem>
|
|
||||||
{
|
{
|
||||||
TEnum mEnum;
|
switch (t)
|
||||||
|
|
||||||
public this(TEnum e)
|
|
||||||
{
|
{
|
||||||
mEnum = e;
|
case typeof(int8): return typeof(int16);
|
||||||
}
|
case typeof(int16): return typeof(int32);
|
||||||
|
case typeof(int32): return typeof(int64);
|
||||||
public Result<TElem> GetNext() mut
|
case typeof(float): return typeof(double);
|
||||||
{
|
|
||||||
switch (mEnum.GetNext())
|
|
||||||
{
|
|
||||||
case .Ok(let val): return .Ok(val + val);
|
|
||||||
case .Err: return .Err;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
static Type GetConcreteEnumerator<TCollection, TElem>() where TCollection : IEnumerable<TElem>
|
static TTo GetBigger<TFrom, TTo>(TFrom val) where TTo : comptype(GetBiggerType(typeof(TFrom))), operator explicit TFrom
|
||||||
{
|
{
|
||||||
TCollection col = ?;
|
return (.)val;
|
||||||
return col.GetEnumerator().GetType();
|
|
||||||
}
|
|
||||||
|
|
||||||
public static DoublingEnumerator<TElem, comptype(GetConcreteEnumerator<TCollection, TElem>())> GetDoublingEnumerator<TCollection, TElem>(this TCollection it)
|
|
||||||
where TCollection: concrete, IEnumerable<TElem>
|
|
||||||
where TElem : operator TElem + TElem
|
|
||||||
{
|
|
||||||
return .(it.GetEnumerator());
|
|
||||||
}
|
}
|
||||||
|
|
||||||
[Test]
|
[Test]
|
||||||
|
@ -124,13 +107,8 @@ namespace Tests
|
||||||
MethodA(34, 45);
|
MethodA(34, 45);
|
||||||
Debug.Assert(LogAttribute.gLog == "Called Tests.Comptime.MethodA(int a, int b) 34 45");
|
Debug.Assert(LogAttribute.gLog == "Called Tests.Comptime.MethodA(int a, int b) 34 45");
|
||||||
|
|
||||||
List<float> fList = scope .() { 1, 2, 3 };
|
var v0 = GetBigger((int8)123);
|
||||||
var e = fList.GetDoublingEnumerator();
|
Test.Assert(v0.GetType() == typeof(int16));
|
||||||
Test.Assert(e.GetNext().Value == 2);
|
|
||||||
Test.Assert(e.GetNext().Value == 4);
|
|
||||||
Test.Assert(e.GetNext().Value == 6);
|
|
||||||
|
|
||||||
//Test.Assert(fList.DoubleVals() == 12);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -252,6 +252,34 @@ namespace Tests
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
struct DoublingEnumerator<TElem, TEnum> : IEnumerator<TElem>
|
||||||
|
where TElem : operator TElem + TElem
|
||||||
|
where TEnum : concrete, IEnumerator<TElem>
|
||||||
|
{
|
||||||
|
TEnum mEnum;
|
||||||
|
|
||||||
|
public this(TEnum e)
|
||||||
|
{
|
||||||
|
mEnum = e;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Result<TElem> GetNext() mut
|
||||||
|
{
|
||||||
|
switch (mEnum.GetNext())
|
||||||
|
{
|
||||||
|
case .Ok(let val): return .Ok(val + val);
|
||||||
|
case .Err: return .Err;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static DoublingEnumerator<TElem, decltype(default(TCollection).GetEnumerator())> GetDoublingEnumerator<TCollection, TElem>(this TCollection it)
|
||||||
|
where TCollection: concrete, IEnumerable<TElem>
|
||||||
|
where TElem : operator TElem + TElem
|
||||||
|
{
|
||||||
|
return .(it.GetEnumerator());
|
||||||
|
}
|
||||||
|
|
||||||
[Test]
|
[Test]
|
||||||
public static void TestBasics()
|
public static void TestBasics()
|
||||||
{
|
{
|
||||||
|
@ -306,6 +334,11 @@ namespace Tests
|
||||||
Test.Assert(MethodF(floatList) == 0);
|
Test.Assert(MethodF(floatList) == 0);
|
||||||
|
|
||||||
Test.Assert(floatList.Sum((x) => x * 2) == 12);
|
Test.Assert(floatList.Sum((x) => x * 2) == 12);
|
||||||
|
|
||||||
|
var e = floatList.GetDoublingEnumerator();
|
||||||
|
Test.Assert(e.GetNext().Value == 2);
|
||||||
|
Test.Assert(e.GetNext().Value == 4);
|
||||||
|
Test.Assert(e.GetNext().Value == 6);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue