_Formatting flags

This commit is contained in:
2025-12-26 21:43:59 +02:00
parent 24b8ad77fe
commit ff6816396c

View File

@@ -9,9 +9,20 @@ using BuildData = Flax.Build.Builder.BuildData;
namespace Flax.Build.Bindings
{
[Flags]
public enum ParameterFormattingFlags
{
None = 0,
/// <summary>
/// The parameter needs to be assigned to local variable first.
/// </summary>
NeedLocalVariable = 1 << 0,
}
partial class BindingsGenerator
{
private static readonly bool[] CppParamsThatNeedLocalVariable = new bool[64];
private static readonly ParameterFormattingFlags[] CppParamsFormattingFlags = new ParameterFormattingFlags[64];
private static readonly bool[] CppParamsThatNeedConversion = new bool[64];
private static readonly string[] CppParamsThatNeedConversionWrappers = new string[64];
private static readonly string[] CppParamsThatNeedConversionTypes = new string[64];
@@ -77,6 +88,11 @@ namespace Flax.Build.Bindings
"Rectangle",
};
private static ParameterFormattingFlags SetFlag(this ParameterFormattingFlags flags, ParameterFormattingFlags value, bool enable)
{
return enable ? (flags | value) : (flags & ~value);
}
private static bool GenerateCppIsTemplateInstantiationType(ApiTypeInfo typeInfo)
{
return typeInfo.Instigator != null && typeInfo.Instigator.TypeInfo is ClassStructInfo classStructInfo && classStructInfo.IsTemplate;
@@ -102,9 +118,9 @@ namespace Flax.Build.Bindings
return result;
}
private static string GenerateCppWrapperNativeToManagedParam(BuildData buildData, StringBuilder contents, TypeInfo paramType, string paramName, ApiTypeInfo caller, bool isRef, out bool useLocalVar)
private static string GenerateCppWrapperNativeToManagedParam(BuildData buildData, StringBuilder contents, TypeInfo paramType, string paramName, ApiTypeInfo caller, bool isRef, out ParameterFormattingFlags formattingFlags)
{
useLocalVar = false;
formattingFlags = ParameterFormattingFlags.None;
var nativeToManaged = GenerateCppWrapperNativeToManaged(buildData, paramType, caller, out var managedTypeAsNative, null);
string result;
if (!string.IsNullOrEmpty(nativeToManaged))
@@ -122,7 +138,7 @@ namespace Flax.Build.Bindings
contents.Append($" auto __param_orig_{paramName} = {result};").AppendLine();
contents.Append($" auto __param_{paramName} = __param_orig_{paramName};").AppendLine();
result = $"&__param_{paramName}";
useLocalVar = true;
formattingFlags.SetFlag(ParameterFormattingFlags.NeedLocalVariable, true);
}
}
else
@@ -676,9 +692,9 @@ namespace Flax.Build.Bindings
}
}
private static string GenerateCppWrapperManagedToNative(BuildData buildData, TypeInfo typeInfo, ApiTypeInfo caller, out string type, out ApiTypeInfo apiType, FunctionInfo functionInfo, out bool needLocalVariable)
private static string GenerateCppWrapperManagedToNative(BuildData buildData, TypeInfo typeInfo, ApiTypeInfo caller, out string type, out ApiTypeInfo apiType, FunctionInfo functionInfo, out ParameterFormattingFlags formattingFlags)
{
needLocalVariable = false;
formattingFlags = ParameterFormattingFlags.None;
// Register any API types usage
apiType = FindApiTypeInfo(buildData, typeInfo, caller);
@@ -688,7 +704,7 @@ namespace Flax.Build.Bindings
if (typeInfo.IsArray)
{
var arrayType = new TypeInfo { Type = "Array", GenericArgs = new List<TypeInfo> { new TypeInfo(typeInfo) { IsArray = false } } };
var result = GenerateCppWrapperManagedToNative(buildData, arrayType, caller, out type, out _, functionInfo, out needLocalVariable);
var result = GenerateCppWrapperManagedToNative(buildData, arrayType, caller, out type, out _, functionInfo, out formattingFlags);
return result + ".Get()";
}
@@ -755,7 +771,7 @@ namespace Flax.Build.Bindings
// Array
if (typeInfo.Type == "Array" && typeInfo.GenericArgs != null)
{
needLocalVariable = true;
formattingFlags.SetFlag(ParameterFormattingFlags.NeedLocalVariable, true);
var arrayTypeInfo = typeInfo.GenericArgs[0];
var arrayApiType = FindApiTypeInfo(buildData, arrayTypeInfo, caller);
if (arrayApiType != null && arrayApiType.MarshalAs != null)
@@ -837,7 +853,7 @@ namespace Flax.Build.Bindings
// BytesContainer
if (typeInfo.Type == "BytesContainer" && typeInfo.GenericArgs == null)
{
needLocalVariable = true;
formattingFlags.SetFlag(FormattingFlags.NeedLocalVariable, true);
type = "MArray*";
return "MUtils::LinkArray({0})";
}
@@ -860,7 +876,7 @@ namespace Flax.Build.Bindings
if (apiType != null)
{
if (apiType.MarshalAs != null)
return GenerateCppWrapperManagedToNative(buildData, apiType.MarshalAs, caller, out type, out apiType, functionInfo, out needLocalVariable);
return GenerateCppWrapperManagedToNative(buildData, apiType.MarshalAs, caller, out type, out apiType, functionInfo, out formattingFlags);
// Scripting Object (for non-pod types converting only, other API converts managed to unmanaged object in C# wrapper code)
if (CppNonPodTypesConvertingGeneration && apiType.IsScriptingObject && typeInfo.IsPtr)
@@ -873,7 +889,7 @@ namespace Flax.Build.Bindings
if (apiType.IsStruct && !apiType.IsPod)
{
// Use wrapper structure that represents the memory layout of the managed data
needLocalVariable = true;
formattingFlags.SetFlag(ParameterFormattingFlags.NeedLocalVariable, true);
if (!CppUsedNonPodTypes.Contains(apiType))
CppUsedNonPodTypes.Add(apiType);
type = GenerateCppManagedWrapperName(apiType);
@@ -1122,7 +1138,7 @@ namespace Flax.Build.Bindings
separator = true;
CppParamsThatNeedConversion[i] = false;
CppParamsWrappersCache[i] = GenerateCppWrapperManagedToNative(buildData, parameterInfo.Type, caller, out var managedType, out var apiType, functionInfo, out CppParamsThatNeedLocalVariable[i]);
CppParamsWrappersCache[i] = GenerateCppWrapperManagedToNative(buildData, parameterInfo.Type, caller, out var managedType, out var apiType, functionInfo, out CppParamsFormattingFlags[i]);
// Out parameters that need additional converting will be converted at the native side (eg. object reference)
var isOutWithManagedConverter = parameterInfo.IsOut && !string.IsNullOrEmpty(GenerateCSharpManagedToNativeConverter(buildData, parameterInfo.Type, caller));
@@ -1323,7 +1339,7 @@ namespace Flax.Build.Bindings
}
}
// Special case for parameter that cannot be passed directly to the function from the wrapper method input parameter (eg. MArray* converted into BytesContainer uses as BytesContainer&)
else if (CppParamsThatNeedLocalVariable[i])
else if (CppParamsFormattingFlags[i].HasFlag(ParameterFormattingFlags.NeedLocalVariable))
{
contents.Append(indent).AppendFormat("auto {0}Temp = {1};", parameterInfo.Name, param).AppendLine();
if (parameterInfo.Type.IsPtr)
@@ -1647,7 +1663,7 @@ namespace Flax.Build.Bindings
paramValue = $"&__param_{parameterInfo.Name}";
useLocalVar = true;
}
CppParamsThatNeedLocalVariable[i] = useLocalVar;
CppParamsFormattingFlags[i].SetFlag(ParameterFormattingFlags.NeedLocalVariable, useLocalVar);
if (separator)
thunkParams += ", ";
@@ -1695,7 +1711,7 @@ namespace Flax.Build.Bindings
{
var parameterInfo = functionInfo.Parameters[i];
var paramIsRef = parameterInfo.IsRef || parameterInfo.IsOut;
var paramValue = GenerateCppWrapperNativeToManagedParam(buildData, contents, parameterInfo.Type, parameterInfo.Name, classInfo, paramIsRef, out CppParamsThatNeedLocalVariable[i]);
var paramValue = GenerateCppWrapperNativeToManagedParam(buildData, contents, parameterInfo.Type, parameterInfo.Name, classInfo, paramIsRef, out CppParamsFormattingFlags[i]);
contents.Append($" params[{i}] = {paramValue};").AppendLine();
}
}
@@ -2266,7 +2282,7 @@ namespace Flax.Build.Bindings
var paramType = eventInfo.Type.GenericArgs[i];
var paramName = "arg" + i;
var paramIsRef = paramType.IsRef && !paramType.IsConst;
var paramValue = GenerateCppWrapperNativeToManagedParam(buildData, contents, paramType, paramName, classInfo, paramIsRef, out CppParamsThatNeedConversion[i]);
var paramValue = GenerateCppWrapperNativeToManagedParam(buildData, contents, paramType, paramName, classInfo, paramIsRef, out CppParamsFormattingFlags[i]);
contents.Append($" params[{i}] = {paramValue};").AppendLine();
}
if (eventInfo.IsStatic)