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

Added [MangleConst] support

This commit is contained in:
Brian Fiete 2020-11-16 11:05:08 -08:00
parent 3c131632b4
commit fa0e712c2b
8 changed files with 78 additions and 22 deletions

View file

@ -206,6 +206,12 @@ namespace System
} }
} }
[AttributeUsage(.Parameter | .ReturnValue)]
public struct MangleConstAttribute : Attribute
{
}
[AttributeUsage(.Method | .Constructor | .Delegate | .Function)] [AttributeUsage(.Method | .Constructor | .Delegate | .Function)]
public struct CallingConventionAttribute : Attribute public struct CallingConventionAttribute : Attribute
{ {

View file

@ -2929,8 +2929,7 @@ class BfMethodDeclaration : public BfMemberDeclaration
public: public:
BF_AST_TYPE(BfMethodDeclaration, BfMemberDeclaration); BF_AST_TYPE(BfMethodDeclaration, BfMemberDeclaration);
BfCommentNode* mDocumentation; BfCommentNode* mDocumentation;
BfAttributeDirective* mReturnAttributes;
BfTokenNode* mExternSpecifier; BfTokenNode* mExternSpecifier;
BfTokenNode* mVirtualSpecifier; // either 'virtual', 'override', or 'abstract' BfTokenNode* mVirtualSpecifier; // either 'virtual', 'override', or 'abstract'
BfTokenNode* mNewSpecifier; BfTokenNode* mNewSpecifier;

View file

@ -999,8 +999,7 @@ void BfElementVisitor::Visit(BfMethodDeclaration* methodDeclaration)
VisitChild(methodDeclaration->mProtectionSpecifier); VisitChild(methodDeclaration->mProtectionSpecifier);
VisitChild(methodDeclaration->mReadOnlySpecifier); VisitChild(methodDeclaration->mReadOnlySpecifier);
VisitChild(methodDeclaration->mStaticSpecifier); VisitChild(methodDeclaration->mStaticSpecifier);
VisitChild(methodDeclaration->mReturnAttributes);
VisitChild(methodDeclaration->mExternSpecifier); VisitChild(methodDeclaration->mExternSpecifier);
VisitChild(methodDeclaration->mVirtualSpecifier); // either 'virtual', 'override', or 'abstract' VisitChild(methodDeclaration->mVirtualSpecifier); // either 'virtual', 'override', or 'abstract'
VisitChild(methodDeclaration->mNewSpecifier); VisitChild(methodDeclaration->mNewSpecifier);

View file

@ -1452,7 +1452,7 @@ void BfMSMangler::AddPrefix(MangleContext& mangleContext, StringImpl& name, int
name.Insert(startIdx, prefix); name.Insert(startIdx, prefix);
} }
void BfMSMangler::Mangle(MangleContext& mangleContext, StringImpl& name, BfType* type, bool useTypeList) void BfMSMangler::Mangle(MangleContext& mangleContext, StringImpl& name, BfType* type, bool useTypeList, bool isConst)
{ {
bool isLongPrim = false; bool isLongPrim = false;
@ -1612,11 +1612,16 @@ void BfMSMangler::Mangle(MangleContext& mangleContext, StringImpl& name, BfType*
auto pointerType = (BfPointerType*)type; auto pointerType = (BfPointerType*)type;
const char* strAdd = mangleContext.mIs64Bit ? "PEA" : "PA"; const char* strAdd = mangleContext.mIs64Bit ? "PEA" : "PA";
//if (!FindOrCreateNameSub(mangleContext, name, NameSubstitute(BfMangler::NameSubstitute::Kind_Prefix, strAdd, pointerType->mTypeId)))
{ if (mangleContext.mIs64Bit)
name += strAdd; name += "PE";
Mangle(mangleContext, name, pointerType->mElementType); else
} name += "P";
if (isConst)
name += "B";
else
name += "A";
Mangle(mangleContext, name, pointerType->mElementType);
} }
else if (type->IsRef()) else if (type->IsRef())
{ {
@ -1624,7 +1629,10 @@ void BfMSMangler::Mangle(MangleContext& mangleContext, StringImpl& name, BfType*
name += "A"; name += "A";
if (mangleContext.mIs64Bit) if (mangleContext.mIs64Bit)
name += "E"; name += "E";
name += "A"; if (isConst)
name += "B";
else
name += "A";
if (refType->mRefKind == BfRefType::RefKind_Mut) if (refType->mRefKind == BfRefType::RefKind_Mut)
name += "mut$"; name += "mut$";
else if (refType->mRefKind == BfRefType::RefKind_Out) else if (refType->mRefKind == BfRefType::RefKind_Out)
@ -1788,6 +1796,7 @@ void BfMSMangler::Mangle(StringImpl& name, bool is64Bit, BfMethodInstance* metho
} }
auto methodDef = methodInst->mMethodDef; auto methodDef = methodInst->mMethodDef;
auto methodDeclaration = BfNodeDynCastExact<BfMethodDeclaration>(methodDef->mMethodDeclaration);
auto typeInst = methodInst->GetOwner(); auto typeInst = methodInst->GetOwner();
auto typeDef = typeInst->mTypeDef; auto typeDef = typeInst->mTypeDef;
@ -2119,8 +2128,12 @@ void BfMSMangler::Mangle(StringImpl& name, bool is64Bit, BfMethodInstance* metho
// //
if (!isSpecialFunc) if (!isSpecialFunc)
{ {
bool isConst = false;
if (methodDeclaration != NULL)
HandleParamCustomAttributes(methodDeclaration->mAttributes, true, isConst);
mangleContext.mInRet = true; mangleContext.mInRet = true;
Mangle(mangleContext, name, methodInst->mReturnType); Mangle(mangleContext, name, methodInst->mReturnType, false, isConst);
mangleContext.mInRet = false; mangleContext.mInRet = false;
} }
if ((methodInst->mParams.size() == 0) && (!doExplicitThis)) if ((methodInst->mParams.size() == 0) && (!doExplicitThis))
@ -2139,7 +2152,16 @@ void BfMSMangler::Mangle(StringImpl& name, bool is64Bit, BfMethodInstance* metho
Mangle(mangleContext, name, typeInst->GetUnderlyingType(), true); Mangle(mangleContext, name, typeInst->GetUnderlyingType(), true);
} }
for (auto& param : methodInst->mParams) for (auto& param : methodInst->mParams)
Mangle(mangleContext, name, param.mResolvedType, true); {
bool isConst = false;
if ((param.mParamDefIdx >= 0) && (methodDeclaration != NULL) && (param.mParamDefIdx < methodDeclaration->mParams.mSize))
{
auto paramDecl = methodDeclaration->mParams[param.mParamDefIdx];
HandleParamCustomAttributes(paramDecl->mAttributes, false, isConst);
}
Mangle(mangleContext, name, param.mResolvedType, true, isConst);
}
name += '@'; name += '@';
} }
@ -2311,3 +2333,17 @@ void BfMangler::HandleCustomAttributes(BfCustomAttributes* customAttributes, BfI
} }
} }
void BfMangler::HandleParamCustomAttributes(BfAttributeDirective* attributes, bool isReturn, bool& isConst)
{
while (attributes != NULL)
{
if (attributes->mAttributeTypeRef != NULL)
{
auto typeRefName = attributes->mAttributeTypeRef->ToString();
if (typeRefName == "MangleConst")
isConst = true;
}
attributes = attributes->mNextAttribute;
}
}

View file

@ -85,6 +85,7 @@ public:
static void MangleMethodName(StringImpl& outStr, MangleKind mangleKind, BfTypeInstance* type, const StringImpl& methodName); static void MangleMethodName(StringImpl& outStr, MangleKind mangleKind, BfTypeInstance* type, const StringImpl& methodName);
static void MangleStaticFieldName(StringImpl& outStr, MangleKind mangleKind, BfTypeInstance* owner, const StringImpl& fieldName, BfType* fieldType = NULL); static void MangleStaticFieldName(StringImpl& outStr, MangleKind mangleKind, BfTypeInstance* owner, const StringImpl& fieldName, BfType* fieldType = NULL);
static void HandleCustomAttributes(BfCustomAttributes* customAttributes, BfIRConstHolder* constHolder, BfModule* module, StringImpl& name, bool& isCMangle, bool& isCPPMangle); static void HandleCustomAttributes(BfCustomAttributes* customAttributes, BfIRConstHolder* constHolder, BfModule* module, StringImpl& name, bool& isCMangle, bool& isCPPMangle);
static void HandleParamCustomAttributes(BfAttributeDirective* attributes, bool isReturn, bool& isConst);
}; };
class BfGNUMangler : public BfMangler class BfGNUMangler : public BfMangler
@ -169,7 +170,7 @@ public:
static void AddGenericArgs(MangleContext& mangleContext, StringImpl& name, const SizedArrayImpl<BfType*>& genericArgs, int numOuterGenericParams = 0); static void AddGenericArgs(MangleContext& mangleContext, StringImpl& name, const SizedArrayImpl<BfType*>& genericArgs, int numOuterGenericParams = 0);
static void AddStr(MangleContext& mangleContext, StringImpl& name, const StringImpl& str); static void AddStr(MangleContext& mangleContext, StringImpl& name, const StringImpl& str);
static void Mangle(MangleContext& mangleContext, StringImpl& name, BfType* type, bool useTypeList = false); static void Mangle(MangleContext& mangleContext, StringImpl& name, BfType* type, bool useTypeList = false, bool isConst = false);
static void Mangle(MangleContext& mangleContext, StringImpl& name, BfTypeInstance* typeInst, bool isAlreadyStarted, bool isOuterType = false); static void Mangle(MangleContext& mangleContext, StringImpl& name, BfTypeInstance* typeInst, bool isAlreadyStarted, bool isOuterType = false);
static void MangleConst(MangleContext& mangleContext, StringImpl& name, int64 val); static void MangleConst(MangleContext& mangleContext, StringImpl& name, int64 val);

View file

@ -6226,15 +6226,18 @@ BfIRValue BfModule::CreateTypeData(BfType* type, Dictionary<int, int>& usedStrin
if (!typeInstance->IsTypeMemberAccessible(methodDef->mDeclaringType, mProject)) if (!typeInstance->IsTypeMemberAccessible(methodDef->mDeclaringType, mProject))
continue; continue;
if (auto methodDeclaration = methodDef->GetMethodDeclaration())
{ //
for (BfParameterDeclaration* paramDecl : methodDeclaration->mParams) {
{ SetAndRestoreValue<BfTypeInstance*> prevTypeInstance(mCurTypeInstance, typeInstance);
if (paramDecl->mAttributes != NULL) if (auto methodDeclaration = methodDef->GetMethodDeclaration())
methodReflectKind = (BfReflectKind)(methodReflectKind | _GetReflectUserFromDirective(paramDecl->mAttributes, BfAttributeTargets_Parameter)); {
for (BfParameterDeclaration* paramDecl : methodDeclaration->mParams)
{
if (paramDecl->mAttributes != NULL)
methodReflectKind = (BfReflectKind)(methodReflectKind | _GetReflectUserFromDirective(paramDecl->mAttributes, BfAttributeTargets_Parameter));
}
} }
if (methodDeclaration->mReturnAttributes != NULL)
methodReflectKind = (BfReflectKind)(methodReflectKind | _GetReflectUserFromDirective(methodDeclaration->mReturnAttributes, BfAttributeTargets_ReturnValue));
} }
if ((methodReflectKind & (BfReflectKind_Methods | BfReflectKind_User)) != 0) if ((methodReflectKind & (BfReflectKind_Methods | BfReflectKind_User)) != 0)

View file

@ -21,6 +21,11 @@ namespace Tests
ret.mA = mA + other.mA + arg0; ret.mA = mA + other.mA + arg0;
return ret; return ret;
} }
const float& MethodA2(const float& val)
{
return val;
}
}; };
struct StructB struct StructB
@ -534,6 +539,8 @@ void UseIt()
Interop::StructA sa; Interop::StructA sa;
sa.MethodA0(0); sa.MethodA0(0);
sa.MethodA1(sa, 1); sa.MethodA1(sa, 1);
float f = 123;
sa.MethodA2(f);
Interop::StructB sb; Interop::StructB sb;
sb.MethodB0(0); sb.MethodB0(0);
sb.MethodB1(sb, 1); sb.MethodB1(sb, 1);

View file

@ -16,6 +16,9 @@ namespace Tests
public extern int32 MethodA0(int32 arg0) mut; public extern int32 MethodA0(int32 arg0) mut;
[LinkName(.CPP)] [LinkName(.CPP)]
public extern StructA MethodA1(StructA sa, int32 arg0) mut; public extern StructA MethodA1(StructA sa, int32 arg0) mut;
[LinkName(.CPP)]
[return: MangleConst]
public extern ref float MethodA2([MangleConst]ref float val);
} }
[CRepr] [CRepr]
@ -391,6 +394,8 @@ namespace Tests
} }
Test.Assert(StructA.sVal == 1234); Test.Assert(StructA.sVal == 1234);
float f = 123;
Test.Assert(sa0.MethodA2(ref f) == 123);
StartTest("Func0"); StartTest("Func0");
Test.Assert(Func0(12, 34) == 3412); Test.Assert(Func0(12, 34) == 3412);