Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -300,7 +300,7 @@ internal Binding (BindingInfo bindingInfo, string name, ImmutableArray<string> @
var bucket = ImmutableArray.CreateBuilder<EnumMember> ();
// loop over the fields and add those that contain a FieldAttribute
var enumValueDeclarations = enumDeclaration.Members.OfType<EnumMemberDeclarationSyntax> ();
foreach (var enumValueDeclaration in enumValueDeclarations) {
foreach (var (index, enumValueDeclaration) in enumValueDeclarations.Index ()) {
if (Skip (enumValueDeclaration, context.SemanticModel))
continue;
if (context.SemanticModel.GetDeclaredSymbol (enumValueDeclaration) is not IFieldSymbol enumValueSymbol) {
Expand All @@ -314,6 +314,7 @@ internal Binding (BindingInfo bindingInfo, string name, ImmutableArray<string> @
// could not calculate the library for the enum add it with bad data for the analyzer to pick it up
var enumMember = new EnumMember (
name: enumValueDeclaration.Identifier.ToFullString ().Trim (),
index: (uint) index,
libraryName: string.Empty,
libraryPath: null,
fieldData: enumValueSymbol.GetFieldData (),
Expand All @@ -326,6 +327,7 @@ internal Binding (BindingInfo bindingInfo, string name, ImmutableArray<string> @
} else {
var enumMember = new EnumMember (
name: enumValueDeclaration.Identifier.ToFullString ().Trim (),
index: (uint) index,
libraryName: libraryName,
libraryPath: libraryPath,
fieldData: enumValueSymbol.GetFieldData (),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -30,19 +30,21 @@ readonly partial struct EnumMember {
/// Create a new change that happened on a member.
/// </summary>
/// <param name="name">The name of the changed member.</param>
/// <param name="index">The position of the enum member starting at 0.</param>
/// <param name="libraryName">The library name of the smart enum.</param>
/// <param name="libraryPath">The library path to the library, null if it is a known frameworl.</param>
/// <param name="fieldData">The binding data attached to this enum value.</param>
/// <param name="symbolAvailability">The symbol availability of the member.</param>
/// <param name="attributes">The list of attribute changes in the member.</param>
public EnumMember (string name,
uint index,
string libraryName,
string? libraryPath,
FieldData<EnumValue>? fieldData,
SymbolAvailability symbolAvailability,
ImmutableArray<AttributeCodeChange> attributes)
ImmutableArray<AttributeCodeChange> attributes) : this (StructState.Initialized, name)
{
Name = name;
Index = index;
FieldInfo = fieldData is null ? null : new (fieldData.Value, libraryName, libraryPath);
SymbolAvailability = symbolAvailability;
Attributes = attributes;
Expand All @@ -52,11 +54,13 @@ public EnumMember (string name,
/// Create a new change that happened on a member.
/// </summary>
/// <param name="name">The name of the changed member.</param>
/// <param name="index">The position of the enum member starting at 0.</param>
/// <param name="libraryName">The library name of the smart enum.</param>
/// <param name="libraryPath">The library path to the library, null if it is a known frameworl.</param>
public EnumMember (string name, string libraryName, string? libraryPath)
public EnumMember (string name, uint index, string libraryName, string? libraryPath)
: this (
name: name,
index: index,
libraryName: libraryName,
libraryPath: libraryPath,
fieldData: null,
Expand Down
50 changes: 48 additions & 2 deletions src/rgen/Microsoft.Macios.Generator/DataModel/EnumMember.cs
Original file line number Diff line number Diff line change
Expand Up @@ -17,11 +17,32 @@ namespace Microsoft.Macios.Generator.DataModel;
/// </summary>
[StructLayout (LayoutKind.Auto)]
readonly partial struct EnumMember : IEquatable<EnumMember> {

/// <summary>
/// The initialization state of the struct.
/// </summary>
StructState State { get; init; } = StructState.Default;

/// <summary>
/// Gets the default, uninitialized instance of <see cref="EnumMember"/>.
/// </summary>
public static EnumMember Default { get; } = new (StructState.Default, string.Empty);

/// <summary>
/// Gets a value indicating whether the instance is the default, uninitialized instance.
/// </summary>
public bool IsNullOrDefault => State == StructState.Default;

/// <summary>
/// Get the name of the member.
/// </summary>
public string Name { get; }

/// <summary>
/// Gets the index of the enum member.
/// </summary>
public uint Index { get; init; }

/// <summary>
/// The platform availability of the enum value.
/// </summary>
Expand All @@ -37,6 +58,8 @@ public bool Equals (EnumMember other)
{
if (Name != other.Name)
return false;
if (Index != other.Index)
return false;
if (SymbolAvailability != other.SymbolAvailability)
return false;
if (FieldInfo != other.FieldInfo)
Expand All @@ -55,24 +78,47 @@ public override bool Equals (object? obj)
/// <inheritdoc />
public override int GetHashCode ()
{
return HashCode.Combine (Name, SymbolAvailability, Attributes);
return HashCode.Combine (Name, Index, SymbolAvailability, FieldInfo, Attributes);
}

/// <summary>
/// Compares two <see cref="EnumMember"/> instances for equality.
/// </summary>
/// <param name="x">The first <see cref="EnumMember"/> to compare.</param>
/// <param name="y">The second <see cref="EnumMember"/> to compare.</param>
/// <returns><c>true</c> if the instances are equal; otherwise, <c>false</c>.</returns>
public static bool operator == (EnumMember x, EnumMember y)
{
return x.Equals (y);
}

/// <summary>
/// Compares two <see cref="EnumMember"/> instances for inequality.
/// </summary>
/// <param name="x">The first <see cref="EnumMember"/> to compare.</param>
/// <param name="y">The second <see cref="EnumMember"/> to compare.</param>
/// <returns><c>true</c> if the instances are not equal; otherwise, <c>false</c>.</returns>
public static bool operator != (EnumMember x, EnumMember y)
{
return !(x == y);
}

/// <summary>
/// Initializes a new instance of the <see cref="EnumMember"/> struct.
/// </summary>
/// <param name="state">The initialization state of the struct.</param>
/// <param name="name">The name of the enum member.</param>
public EnumMember (StructState state, string name)
{
State = state;
Name = name;
}

/// <inheritdoc />
public override string ToString ()
{
var sb = new StringBuilder (
$"{{ Name: '{Name}' SymbolAvailability: {SymbolAvailability} FieldInfo: {FieldInfo} Attributes: [");
$"{{ Name: '{Name}', Index: {Index}, SymbolAvailability: {SymbolAvailability} FieldInfo: {FieldInfo} Attributes: [");
sb.AppendJoin (", ", Attributes);
sb.Append ("] }");
return sb.ToString ();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -90,7 +90,7 @@ internal Binding (EnumDeclarationSyntax enumDeclaration, INamedTypeSymbol symbol
var bindingType = HasErrorDomainAttribute ? BindingType.SmartEnum : BindingType.Unknown;
var bucket = ImmutableArray.CreateBuilder<EnumMember> ();
var enumValueDeclarations = enumDeclaration.Members.OfType<EnumMemberDeclarationSyntax> ();
foreach (var enumValueDeclaration in enumValueDeclarations) {
foreach (var (index, enumValueDeclaration) in enumValueDeclarations.Index ()) {
if (context.SemanticModel.GetDeclaredSymbol (enumValueDeclaration) is not IFieldSymbol enumValueSymbol) {
continue;
}
Expand All @@ -106,6 +106,7 @@ internal Binding (EnumDeclarationSyntax enumDeclaration, INamedTypeSymbol symbol
}
enumMember = new EnumMember (
name: enumValueDeclaration.Identifier.ToFullString ().Trim (),
index: (uint) index,
libraryName: string.Empty,
libraryPath: null,
fieldData: enumValueSymbol.GetFieldData (),
Expand All @@ -120,6 +121,7 @@ internal Binding (EnumDeclarationSyntax enumDeclaration, INamedTypeSymbol symbol
bindingType = BindingType.SmartEnum;
enumMember = new EnumMember (
name: enumValueDeclaration.Identifier.ToFullString ().Trim (),
index: (uint) index,
libraryName: libraryName,
libraryPath: libraryPath,
fieldData: enumValueSymbol.GetFieldData (),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -40,12 +40,13 @@ public EnumMember (string name,
}

public EnumMember (string name,
uint index,
string libraryName,
string? libraryPath,
FieldData? fieldData,
SymbolAvailability symbolAvailability)
SymbolAvailability symbolAvailability) : this (StructState.Initialized, name)
{
Name = name;
Index = index;
SymbolAvailability = symbolAvailability;
FieldInfo = new (fieldData, libraryName, libraryPath);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -196,6 +196,7 @@ public void CompareDifferentMembersLength ()
EnumMembers = [
new EnumMember (
name: "name",
index: 0,
libraryName: "Test",
libraryPath: "/path/to/library",
fieldData: new (),
Expand All @@ -218,6 +219,7 @@ public void CompareDifferentMembers ()
EnumMembers = [
new EnumMember (
name: "name",
index: 0,
libraryName: "Test",
libraryPath: "/path/to/library",
fieldData: new (),
Expand All @@ -234,6 +236,7 @@ public void CompareDifferentMembers ()
EnumMembers = [
new EnumMember (
name: "name2",
index: 0,
libraryName: "Test",
libraryPath: "/path/to/library",
fieldData: new (),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -115,6 +115,7 @@ public void CompareDifferentMembersLength ()
EnumMembers = [
new EnumMember (
name: "name",
index: 0,
libraryName: "Test",
libraryPath: "/path/to/library",
fieldData: new (),
Expand All @@ -137,6 +138,7 @@ public void CompareDifferentMembers ()
EnumMembers = [
new EnumMember (
name: "name",
index: 0,
libraryName: "Test",
libraryPath: "/path/to/library",
fieldData: new (),
Expand All @@ -153,6 +155,7 @@ public void CompareDifferentMembers ()
EnumMembers = [
new EnumMember (
name: "name2",
index: 0,
libraryName: "Test",
libraryPath: "/path/to/library",
fieldData: new (),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -275,6 +275,7 @@ public void EnumIndexTest ()
EnumMembers = [
new (
name: "BuiltInMicrophone",
index: 0,
libraryName: "AVCaptureDeviceTypeBuiltInMicrophone",
libraryPath: null,
fieldData: new (presentSelector),
Expand Down
Loading