Skip to content

Commit

Permalink
Merge pull request #1126 from gircore/fix-1098
Browse files Browse the repository at this point in the history
Differentiate between Long and CLong
  • Loading branch information
badcel authored Sep 26, 2024
2 parents 5a0ef8b + 699e2a8 commit 4edc18a
Show file tree
Hide file tree
Showing 69 changed files with 1,153 additions and 307 deletions.
2 changes: 2 additions & 0 deletions src/Generation/Generator/Model/Type.cs
Original file line number Diff line number Diff line change
Expand Up @@ -19,9 +19,11 @@ public static string GetName(GirModel.Type type)
GirModel.SignedByte => "sbyte",
GirModel.Short => "short",
GirModel.Long => "long",
GirModel.CLong => "long",
GirModel.UnsignedShort => "ushort",
GirModel.UnsignedInteger => "uint",
GirModel.UnsignedLong => "ulong",
GirModel.UnsignedCLong => "ulong",
GirModel.Byte => "byte",
GirModel.Bool => "bool",
GirModel.Void => "void",
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
namespace Generator.Renderer.Internal.Field;

internal class CLong : FieldConverter
{
public bool Supports(GirModel.Field field)
{
return field.AnyTypeOrCallback.TryPickT0(out var anyType, out _) && anyType.Is<GirModel.CLong>();
}

public RenderableField Convert(GirModel.Field field)
{
return new RenderableField(
Name: Model.Field.GetName(field),
Attribute: null,
NullableTypeName: GetNullableTypeName(field)
);
}

private static string GetNullableTypeName(GirModel.Field field)
{
return field.IsPointer
? Model.Type.Pointer
: "CLong";
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,6 @@ private static string GetNullableTypeName(GirModel.Field field)
{
return field.IsPointer
? Model.Type.Pointer
: "CLong";
: Model.Type.GetName(field.AnyTypeOrCallback.AsT0.AsT0);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
namespace Generator.Renderer.Internal.Field;

internal class UnsignedCLong : FieldConverter
{
public bool Supports(GirModel.Field field)
{
return field.AnyTypeOrCallback.TryPickT0(out var anyType, out _) && anyType.Is<GirModel.UnsignedCLong>();
}

public RenderableField Convert(GirModel.Field field)
{
return new RenderableField(
Name: Model.Field.GetName(field),
Attribute: null,
NullableTypeName: GetNullableTypeName(field)
);
}

private static string GetNullableTypeName(GirModel.Field field)
{
return field.IsPointer
? Model.Type.Pointer
: "CULong";
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,6 @@ private static string GetNullableTypeName(GirModel.Field field)
{
return field.IsPointer
? Model.Type.Pointer
: "CULong";
: Model.Type.GetName(field.AnyTypeOrCallback.AsT0.AsT0);
}
}
2 changes: 2 additions & 0 deletions src/Generation/Generator/Renderer/Internal/Field/Fields.cs
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,8 @@ internal static class Fields
new Field.PointerArray(),
new Field.Long(), //Must be before primitive value
new Field.UnsignedLong(), //Must be before primitive value
new Field.CLong(), //Must be before primitive value
new Field.UnsignedCLong(), //Must be before primitive value
new Field.PrimitiveValueType(),
new Field.PrimitiveValueTypeAlias(),
new Field.PrimitiveValueTypeArray(),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,8 @@ internal static class CallbackParameters
new Parameter.PointerGLibPtrArray(),
new Parameter.Long(), //Must be before primitive value type
new Parameter.UnsignedLong(), //Must be before primitive value type
new Parameter.CLong(), //Must be before primitive value type
new Parameter.UnsignedCLong(), //Must be before primitive value type
new Parameter.PrimitiveValueType(),
new Parameter.PrimitiveValueTypeAlias(),
new Parameter.PrimitiveValueTypeArray(),
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
using System;

namespace Generator.Renderer.Internal.Parameter;

internal class CLong : ParameterConverter
{
public bool Supports(GirModel.AnyType anyType)
{
return anyType.Is<GirModel.CLong>();
}

public RenderableParameter Convert(GirModel.Parameter parameter)
{
// If the parameter is both nullable and optional this implies a parameter type like 'int **' and possibly
// ownership transfer (this combination does not currently occur for any functions).
if (parameter is { Nullable: true, Optional: true })
throw new System.NotImplementedException($"{parameter.AnyTypeOrVarArgs} - Long value type with nullable=true and optional=true not yet supported");

// Nullable-only parameters likely have incorrect annotations and should be marked optional instead.
if (parameter.Nullable)
Log.Information($"Long value type '{parameter.Name}' with nullable=true is likely an incorrect annotation");

// The caller-allocates flag is not meaningful for primitive types (https://gitlab.gnome.org/GNOME/gobject-introspection/-/issues/446)
if (parameter.CallerAllocates)
Log.Information($"Long value type '{parameter.Name}' with caller-allocates=true is an incorrect annotation");

return new RenderableParameter(
Attribute: string.Empty,
Direction: GetDirection(parameter),
NullableTypeName: "CLong",
Name: Model.Parameter.GetName(parameter)
);
}

private static string GetDirection(GirModel.Parameter parameter) => parameter switch
{
// - Optional inout and out types are just exposed as non-nullable ref / out parameters which the user can ignore if desired.
{ Direction: GirModel.Direction.In, IsPointer: true } => ParameterDirection.Ref(),
{ Direction: GirModel.Direction.InOut } => ParameterDirection.Ref(),
{ Direction: GirModel.Direction.Out } => ParameterDirection.Out(),
{ Direction: GirModel.Direction.In } => ParameterDirection.In(),
_ => throw new Exception($"Can't figure out direction for internal long value type parameter {parameter}.")
};
}
Original file line number Diff line number Diff line change
Expand Up @@ -14,20 +14,20 @@ public RenderableParameter Convert(GirModel.Parameter parameter)
// If the parameter is both nullable and optional this implies a parameter type like 'int **' and possibly
// ownership transfer (this combination does not currently occur for any functions).
if (parameter is { Nullable: true, Optional: true })
throw new System.NotImplementedException($"{parameter.AnyTypeOrVarArgs} - Long value type with nullable=true and optional=true not yet supported");
throw new System.NotImplementedException($"{parameter.AnyTypeOrVarArgs} - Primitive value type with nullable=true and optional=true not yet supported");

// Nullable-only parameters likely have incorrect annotations and should be marked optional instead.
if (parameter.Nullable)
Log.Information($"Long value type '{parameter.Name}' with nullable=true is likely an incorrect annotation");
Log.Information($"Primitive value type '{parameter.Name}' with nullable=true is likely an incorrect annotation");

// The caller-allocates flag is not meaningful for primitive types (https://gitlab.gnome.org/GNOME/gobject-introspection/-/issues/446)
if (parameter.CallerAllocates)
Log.Information($"Long value type '{parameter.Name}' with caller-allocates=true is an incorrect annotation");
Log.Information($"Primitive value type '{parameter.Name}' with caller-allocates=true is an incorrect annotation");

return new RenderableParameter(
Attribute: string.Empty,
Direction: GetDirection(parameter),
NullableTypeName: "CLong",
NullableTypeName: Model.Type.GetName(parameter.AnyTypeOrVarArgs.AsT0.AsT0),
Name: Model.Parameter.GetName(parameter)
);
}
Expand All @@ -39,6 +39,6 @@ public RenderableParameter Convert(GirModel.Parameter parameter)
{ Direction: GirModel.Direction.InOut } => ParameterDirection.Ref(),
{ Direction: GirModel.Direction.Out } => ParameterDirection.Out(),
{ Direction: GirModel.Direction.In } => ParameterDirection.In(),
_ => throw new Exception($"Can't figure out direction for internal long value type parameter {parameter}.")
_ => throw new Exception($"Can't figure out direction for internal primitive value type parameter {parameter}.")
};
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
using System;

namespace Generator.Renderer.Internal.Parameter;

internal class UnsignedCLong : ParameterConverter
{
public bool Supports(GirModel.AnyType anyType)
{
return anyType.Is<GirModel.UnsignedCLong>();
}

public RenderableParameter Convert(GirModel.Parameter parameter)
{
// If the parameter is both nullable and optional this implies a parameter type like 'int **' and possibly
// ownership transfer (this combination does not currently occur for any functions).
if (parameter is { Nullable: true, Optional: true })
throw new System.NotImplementedException($"{parameter.AnyTypeOrVarArgs} - Unsigned long value type with nullable=true and optional=true not yet supported");

// Nullable-only parameters likely have incorrect annotations and should be marked optional instead.
if (parameter.Nullable)
Log.Information($"Unsigned long value type '{parameter.Name}' with nullable=true is likely an incorrect annotation");

// The caller-allocates flag is not meaningful for primitive types (https://gitlab.gnome.org/GNOME/gobject-introspection/-/issues/446)
if (parameter.CallerAllocates)
Log.Information($"Unsigned long value type '{parameter.Name}' with caller-allocates=true is an incorrect annotation");

return new RenderableParameter(
Attribute: string.Empty,
Direction: GetDirection(parameter),
NullableTypeName: "CULong",
Name: Model.Parameter.GetName(parameter)
);
}

private static string GetDirection(GirModel.Parameter parameter) => parameter switch
{
// - Optional inout and out types are just exposed as non-nullable ref / out parameters which the user can ignore if desired.
{ Direction: GirModel.Direction.In, IsPointer: true } => ParameterDirection.Ref(),
{ Direction: GirModel.Direction.InOut } => ParameterDirection.Ref(),
{ Direction: GirModel.Direction.Out } => ParameterDirection.Out(),
{ Direction: GirModel.Direction.In } => ParameterDirection.In(),
_ => throw new Exception($"Can't figure out direction for internal unsigned long value type parameter {parameter}.")
};
}
Original file line number Diff line number Diff line change
Expand Up @@ -14,20 +14,20 @@ public RenderableParameter Convert(GirModel.Parameter parameter)
// If the parameter is both nullable and optional this implies a parameter type like 'int **' and possibly
// ownership transfer (this combination does not currently occur for any functions).
if (parameter is { Nullable: true, Optional: true })
throw new System.NotImplementedException($"{parameter.AnyTypeOrVarArgs} - Unsigned long value type with nullable=true and optional=true not yet supported");
throw new System.NotImplementedException($"{parameter.AnyTypeOrVarArgs} - Primitive value type with nullable=true and optional=true not yet supported");

// Nullable-only parameters likely have incorrect annotations and should be marked optional instead.
if (parameter.Nullable)
Log.Information($"Unsigned long value type '{parameter.Name}' with nullable=true is likely an incorrect annotation");
Log.Information($"Primitive value type '{parameter.Name}' with nullable=true is likely an incorrect annotation");

// The caller-allocates flag is not meaningful for primitive types (https://gitlab.gnome.org/GNOME/gobject-introspection/-/issues/446)
if (parameter.CallerAllocates)
Log.Information($"Unsigned long value type '{parameter.Name}' with caller-allocates=true is an incorrect annotation");
Log.Information($"Primitive value type '{parameter.Name}' with caller-allocates=true is an incorrect annotation");

return new RenderableParameter(
Attribute: string.Empty,
Direction: GetDirection(parameter),
NullableTypeName: "CULong",
NullableTypeName: Model.Type.GetName(parameter.AnyTypeOrVarArgs.AsT0.AsT0),
Name: Model.Parameter.GetName(parameter)
);
}
Expand All @@ -39,6 +39,6 @@ public RenderableParameter Convert(GirModel.Parameter parameter)
{ Direction: GirModel.Direction.InOut } => ParameterDirection.Ref(),
{ Direction: GirModel.Direction.Out } => ParameterDirection.Out(),
{ Direction: GirModel.Direction.In } => ParameterDirection.In(),
_ => throw new Exception($"Can't figure out direction for internal unsigned long value type parameter {parameter}.")
_ => throw new Exception($"Can't figure out direction for internal primitive value type parameter {parameter}.")
};
}
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,8 @@ internal static class Parameters
new Parameter.PointerGLibPtrArray(),
new Parameter.Long(), //Must be before primitive value type
new Parameter.UnsignedLong(), //Must be before primitive value type
new Parameter.CLong(), //Must be before primitive value type
new Parameter.UnsignedCLong(), //Must be before primitive value type
new Parameter.PrimitiveValueType(),
new Parameter.PrimitiveValueTypeAlias(),
new Parameter.PrimitiveValueTypeArray(),
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
using System;
using System.Collections.Generic;

namespace Generator.Renderer.Internal.ParameterToManagedExpressions;

internal class CLong : ToManagedParameterConverter
{
public bool Supports(GirModel.AnyType type)
=> type.Is<GirModel.CLong>();

public void Initialize(ParameterToManagedData parameterData, IEnumerable<ParameterToManagedData> parameters)
{
switch (parameterData.Parameter)
{
case { Direction: GirModel.Direction.In, IsPointer: false }:
Direct(parameterData);
break;
default:
throw new NotImplementedException($"This kind of internal long value type (pointed: {parameterData.Parameter.IsPointer}, direction: {parameterData.Parameter.Direction} can't be converted to managed currently.");
}
}

private static void Direct(ParameterToManagedData parameterData)
{
var variableName = Model.Parameter.GetName(parameterData.Parameter);

parameterData.SetSignatureName(() => variableName);
parameterData.SetCallName(() => $"{variableName}.Value");
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -12,19 +12,41 @@ public void Initialize(ParameterToManagedData parameterData, IEnumerable<Paramet
{
switch (parameterData.Parameter)
{
case { Direction: GirModel.Direction.In, IsPointer: true }:
Ref(parameterData);
break;
case { Direction: GirModel.Direction.In, IsPointer: false }:
Direct(parameterData);
break;
case { Direction: GirModel.Direction.Out, IsPointer: true }:
Out(parameterData);
break;
default:
throw new NotImplementedException($"This kind of internal long value type (pointed: {parameterData.Parameter.IsPointer}, direction: {parameterData.Parameter.Direction} can't be converted to managed currently.");
throw new NotImplementedException($"This kind of internal primitive value type (pointed: {parameterData.Parameter.IsPointer}, direction: {parameterData.Parameter.Direction} can't be converted to managed currently.");
}
}

private static void Ref(ParameterToManagedData parameterData)
{
var variableName = Model.Parameter.GetName(parameterData.Parameter);

parameterData.SetSignatureName(() => variableName);
parameterData.SetCallName(() => $"ref {variableName}");
}

private static void Direct(ParameterToManagedData parameterData)
{
var variableName = Model.Parameter.GetName(parameterData.Parameter);

parameterData.SetSignatureName(() => variableName);
parameterData.SetCallName(() => $"{variableName}.Value");
parameterData.SetCallName(() => variableName);
}

private static void Out(ParameterToManagedData parameterData)
{
var variableName = Model.Parameter.GetName(parameterData.Parameter);

parameterData.SetSignatureName(() => variableName);
parameterData.SetCallName(() => $"out {variableName}");
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
using System;
using System.Collections.Generic;

namespace Generator.Renderer.Internal.ParameterToManagedExpressions;

internal class UnsignedCLong : ToManagedParameterConverter
{
public bool Supports(GirModel.AnyType type)
=> type.Is<GirModel.UnsignedCLong>();

public void Initialize(ParameterToManagedData parameterData, IEnumerable<ParameterToManagedData> parameters)
{
switch (parameterData.Parameter)
{
case { Direction: GirModel.Direction.In, IsPointer: false }:
Direct(parameterData);
break;
default:
throw new NotImplementedException($"This kind of internal unsigned long value type (pointed: {parameterData.Parameter.IsPointer}, direction: {parameterData.Parameter.Direction} can't be converted to managed currently.");
}
}

private static void Direct(ParameterToManagedData parameterData)
{
var variableName = Model.Parameter.GetName(parameterData.Parameter);

parameterData.SetSignatureName(() => variableName);
parameterData.SetCallName(() => $"{variableName}.Value");
}
}
Loading

0 comments on commit 4edc18a

Please sign in to comment.