clone cppast.net

This commit is contained in:
ouczbs 2024-06-15 10:12:27 +08:00
parent 961cb5cd97
commit 8471e5b5c9
21 changed files with 367 additions and 452 deletions

175
src/CppAst/CXUtil.cs Normal file
View File

@ -0,0 +1,175 @@
using ClangSharp.Interop;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Xml.Linq;
namespace CppAst
{
static internal unsafe class CXUtil
{
#region Cursor
public static string GetCursorSpelling(CXCursor cursor)
{
var cursorSpelling = cursor.Spelling;
string cursorSpellingStr = cursorSpelling.ToString();
cursorSpelling.Dispose();
return cursorSpellingStr.StartsWith("(") ? string.Empty : cursorSpellingStr;
}
public static string GetCursorUsrString(CXCursor cursor)
{
var cursorUsr = cursor.Usr;
string cursorUsrStr = cursorUsr.ToString();
cursorUsr.Dispose();
return cursorUsrStr;
}
public static string GetCursorDisplayName(CXCursor cursor)
{
var cursorDisplayName = cursor.DisplayName;
string cursorDisplayNameStr = cursorDisplayName.ToString();
cursorDisplayName.Dispose();
return cursorDisplayNameStr;
}
#endregion Cursor
#region Comment
public static string GetComment_TextComment_Text(CXComment comment)
{
var textComment_Text = comment.TextComment_Text;
string textComment_TextStr = textComment_Text.ToString();
textComment_Text.Dispose();
return textComment_TextStr;
}
public static string GetComment_InlineCommandComment_CommandName(CXComment comment)
{
var inlineCommandComment_CommandName = comment.InlineCommandComment_CommandName;
string inlineCommandComment_CommandNameStr = inlineCommandComment_CommandName.ToString();
inlineCommandComment_CommandName.Dispose();
return inlineCommandComment_CommandNameStr;
}
public static string GetComment_InlineCommandComment_ArgText(CXComment comment, uint index)
{
var inlineCommandComment_ArgText = comment.InlineCommandComment_GetArgText(index);
string inlineCommandComment_ArgTextStr = inlineCommandComment_ArgText.ToString();
inlineCommandComment_ArgText.Dispose();
return inlineCommandComment_ArgTextStr;
}
public static string GetComment_HtmlTagComment_TagName(CXComment comment)
{
var htmlTagComment_TagName = comment.HtmlTagComment_TagName;
string htmlTagComment_TagNameStr = htmlTagComment_TagName.ToString();
htmlTagComment_TagName.Dispose();
return htmlTagComment_TagNameStr;
}
public static string GetComment_HtmlStartTag_AttrName(CXComment comment, uint index)
{
var htmlStartTag_AttrName = comment.HtmlStartTag_GetAttrName(index);
string htmlStartTag_AttrNameStr = htmlStartTag_AttrName.ToString();
htmlStartTag_AttrName.Dispose();
return htmlStartTag_AttrNameStr;
}
public static string GetComment_HtmlStartTag_AttrValue(CXComment comment, uint index)
{
var htmlStartTag_AttrValue = comment.HtmlStartTag_GetAttrValue(index);
string htmlStartTag_AttrValueStr = htmlStartTag_AttrValue.ToString();
htmlStartTag_AttrValue.Dispose();
return htmlStartTag_AttrValueStr;
}
public static string GetComment_BlockCommandComment_CommandName(CXComment comment)
{
var blockCommandComment_CommandName = comment.BlockCommandComment_CommandName;
string blockCommandComment_CommandNameStr = blockCommandComment_CommandName.ToString();
blockCommandComment_CommandName.Dispose();
return blockCommandComment_CommandNameStr;
}
public static string GetComment_BlockCommandComment_ArgText(CXComment comment, uint index)
{
var blockCommandComment_ArgText = comment.BlockCommandComment_GetArgText(index);
string blockCommandComment_ArgTextStr = blockCommandComment_ArgText.ToString();
blockCommandComment_ArgText.Dispose();
return blockCommandComment_ArgTextStr;
}
public static string GetComment_ParamCommandComment_ParamName(CXComment comment)
{
var paramCommandComment_ParamName = comment.ParamCommandComment_ParamName;
string paramCommandComment_ParamNameStr = paramCommandComment_ParamName.ToString();
paramCommandComment_ParamName.Dispose();
return paramCommandComment_ParamNameStr;
}
public static string GetComment_TParamCommandComment_ParamName(CXComment comment)
{
var tParamCommandComment_ParamName = comment.TParamCommandComment_ParamName;
string tParamCommandComment_ParamNameStr = tParamCommandComment_ParamName.ToString();
tParamCommandComment_ParamName.Dispose();
return tParamCommandComment_ParamNameStr;
}
public static string GetComment_VerbatimBlockLineComment_Text(CXComment comment)
{
var verbatimBlockLineComment_Text = comment.VerbatimBlockLineComment_Text;
string verbatimBlockLineComment_TextStr = verbatimBlockLineComment_Text.ToString();
verbatimBlockLineComment_Text.Dispose();
return verbatimBlockLineComment_TextStr;
}
public static string GetComment_VerbatimLineComment_Text(CXComment comment)
{
var verbatimLineComment_Text = comment.VerbatimLineComment_Text;
string verbatimLineComment_TextStr = verbatimLineComment_Text.ToString();
verbatimLineComment_Text.Dispose();
return verbatimLineComment_TextStr;
}
#endregion Comment
#region Token
public static string GetTokenSpelling(CXToken token, CXTranslationUnit tu)
{
var tokenSpelling = token.GetSpelling(tu);
string tokenSpellingStr = tokenSpelling.ToString();
tokenSpelling.Dispose();
return tokenSpellingStr;
}
#endregion Token
#region File
public static string GetFileName(CXFile file)
{
var fileName = file.Name;
string fileNameStr = fileName.ToString();
fileName.Dispose();
return fileNameStr;
}
#endregion File
#region Type
public static string GetTypeKindSpelling(CXType type)
{
var kindSpelling= type.KindSpelling;
string kindSpellingStr = kindSpelling.ToString();
kindSpelling.Dispose();
return kindSpellingStr;
}
public static string GetTypeSpelling(CXType type)
{
var spelling = type.Spelling;
string spellingStr = spelling.ToString();
spelling.Dispose();
return spellingStr;
}
#endregion Type
}
}

View File

@ -9,7 +9,7 @@ namespace CppAst
/// <summary>
/// A C++ array (e.g int[5] or int[])
/// </summary>
public sealed class CppArrayType : CppTypeWithElementType, IEquatable<CppArrayType>
public sealed class CppArrayType : CppTypeWithElementType
{
/// <summary>
/// Constructor of a C++ array.
@ -32,26 +32,6 @@ namespace CppAst
set => throw new InvalidOperationException("Cannot set the SizeOf an array type. The SizeOf is calculated by the SizeOf its ElementType and the number of elements in the fixed array");
}
public bool Equals(CppArrayType other)
{
if (ReferenceEquals(null, other)) return false;
if (ReferenceEquals(this, other)) return true;
return base.Equals(other) && Size == other.Size;
}
public override bool Equals(object obj)
{
return ReferenceEquals(this, obj) || obj is CppArrayType other && Equals(other);
}
public override int GetHashCode()
{
unchecked
{
return (base.GetHashCode() * 397) ^ Size;
}
}
public override CppType GetCanonicalType()
{
var elementTypeCanonical = ElementType.GetCanonicalType();

View File

@ -163,11 +163,6 @@ namespace CppAst
public bool IsAbstract { get; set; }
private bool Equals(CppClass other)
{
return base.Equals(other) && Equals(Parent, other.Parent) && Name.Equals(other.Name);
}
/// <inheritdoc />
public override int SizeOf { get; set; }
@ -176,32 +171,6 @@ namespace CppAst
/// </summary>
public int AlignOf { get; set; }
/// <inheritdoc />
public override bool Equals(object obj)
{
return ReferenceEquals(this, obj) || obj is CppClass other && Equals(other);
}
/// <inheritdoc />
public override int GetHashCode()
{
unchecked
{
int hashCode = base.GetHashCode();
hashCode = (hashCode * 397) ^ (Parent != null ? Parent.GetHashCode() : 0);
hashCode = (hashCode * 397) ^ Name.GetHashCode();
foreach (var templateParameter in TemplateParameters)
{
hashCode = (hashCode * 397) ^ templateParameter.GetHashCode();
}
foreach (var templateArgument in TemplateSpecializedArguments)
{
hashCode = (hashCode * 397) ^ templateArgument.GetHashCode();
}
return hashCode;
}
}
/// <inheritdoc />
public override CppType GetCanonicalType()
{

View File

@ -3,6 +3,7 @@
// See license.txt file in the project root for full license information.
using System;
using System.Runtime.CompilerServices;
namespace CppAst
{
@ -21,6 +22,10 @@ namespace CppAst
/// </summary>
public ICppContainer Parent { get; internal set; }
public sealed override bool Equals(object obj) => ReferenceEquals(this, obj);
public sealed override int GetHashCode() => RuntimeHelpers.GetHashCode(this);
public string FullParentName
{
get
@ -53,8 +58,7 @@ namespace CppAst
}
else
{
p = null;
//throw new NotImplementedException("Can not be here, not support type here!");
throw new NotImplementedException("Can not be here, not support type here!");
}
}

View File

@ -74,11 +74,6 @@ namespace CppAst
public MetaAttributeMap MetaAttributes { get; private set; } = new MetaAttributeMap();
private bool Equals(CppEnum other)
{
return base.Equals(other) && Equals(Parent, other.Parent) && Equals(Name, other.Name);
}
/// <inheritdoc />
public override int SizeOf
{
@ -86,24 +81,6 @@ namespace CppAst
set => throw new InvalidOperationException("Cannot set the SizeOf an enum as it is determined only by the SizeOf of its underlying IntegerType");
}
/// <inheritdoc />
public override bool Equals(object obj)
{
return ReferenceEquals(this, obj) || obj is CppEnum other && Equals(other);
}
/// <inheritdoc />
public override int GetHashCode()
{
unchecked
{
int hashCode = base.GetHashCode();
hashCode = (hashCode * 397) ^ (Parent != null ? Parent.GetHashCode() : 0);
hashCode = (hashCode * 397) ^ (Name != null ? Name.GetHashCode() : 0);
return hashCode;
}
}
/// <inheritdoc />
public override CppType GetCanonicalType() => IntegerType;

View File

@ -38,31 +38,6 @@ namespace CppAst
/// </summary>
public CppContainerList<CppParameter> Parameters { get; }
private bool Equals(CppFunctionType other)
{
if (base.Equals(other) && ReturnType.Equals(other.ReturnType))
{
if (Parameters.Count != other.Parameters.Count)
{
return false;
}
for (int i = 0; i < Parameters.Count; i++)
{
var fromType = Parameters[i].Type;
var otherType = other.Parameters[i].Type;
if (!fromType.Equals(otherType))
{
return false;
}
}
return true;
}
return false;
}
/// <inheritdoc />
public override int SizeOf
{
@ -71,27 +46,6 @@ namespace CppAst
set => throw new InvalidOperationException("This type does not support SizeOf");
}
/// <inheritdoc />
public override bool Equals(object obj)
{
return ReferenceEquals(this, obj) || obj is CppFunctionType other && Equals(other);
}
/// <inheritdoc />
public override int GetHashCode()
{
unchecked
{
int hashCode = base.GetHashCode();
hashCode = (hashCode * 397) ^ ReturnType.GetHashCode();
foreach (var parameter in Parameters)
{
hashCode = (hashCode * 397) ^ parameter.Type.GetHashCode();
}
return hashCode;
}
}
/// <inheritdoc />
public override IEnumerable<ICppDeclaration> Children() => Parameters;

View File

@ -59,7 +59,7 @@ namespace CppAst
{
case CXCursorKind.CXCursor_TemplateTypeParameter:
{
var parameterTypeName = new CppTemplateParameterType(GetCursorSpelling(cursor));
var parameterTypeName = new CppTemplateParameterType(CXUtil.GetCursorSpelling(cursor));
return parameterTypeName;
}
case CXCursorKind.CXCursor_NonTypeTemplateParameter:
@ -67,7 +67,7 @@ namespace CppAst
//Just use low level ClangSharp object to do the logic
var tmptype = cursor.Type;
var tmpcpptype = GetCppType(tmptype.Declaration, tmptype, cursor, data);
var tmpname = cursor.Spelling.ToString();
var tmpname = CXUtil.GetCursorSpelling(cursor);
var noneTypeParam = new CppTemplateParameterNonType(tmpname, tmpcpptype);
return noneTypeParam;
@ -76,7 +76,7 @@ namespace CppAst
{
//ToDo: add template template parameter support here~~
Debug.WriteLine("[Warning] template template parameter maybe not handle right here!");
var tmplparam = new CppTemplateParameterType(GetCursorSpelling(cursor));
var tmplparam = new CppTemplateParameterType(CXUtil.GetCursorSpelling(cursor));
return tmplparam;
}
}
@ -86,10 +86,10 @@ namespace CppAst
private CppContainerContext GetOrCreateDeclarationContainer(CXCursor cursor, void* data)
{
var typeAsCString = clang.getCursorUSR(cursor).CString.ToString();
var typeAsCString = CXUtil.GetCursorUsrString(cursor);
if (string.IsNullOrEmpty(typeAsCString))
{
typeAsCString = clang.getCursorDisplayName(cursor).ToString();
typeAsCString = CXUtil.GetCursorDisplayName(cursor);
}
// Try to workaround anonymous types
var typeKey = $"{cursor.Kind}:{typeAsCString}{(cursor.IsAnonymous ? "/" + cursor.Hash : string.Empty)}";
@ -114,7 +114,7 @@ namespace CppAst
{
case CXCursorKind.CXCursor_Namespace:
Debug.Assert(parentGlobalDeclarationContainer != null);
var ns = new CppNamespace(GetCursorSpelling(cursor));
var ns = new CppNamespace(CXUtil.GetCursorSpelling(cursor));
symbol = ns;
ns.IsInlineNamespace = cursor.IsInlineNamespace;
defaultContainerVisibility = CppVisibility.Default;
@ -123,7 +123,7 @@ namespace CppAst
case CXCursorKind.CXCursor_EnumDecl:
Debug.Assert(parent != null);
var cppEnum = new CppEnum(GetCursorSpelling(cursor))
var cppEnum = new CppEnum(CXUtil.GetCursorSpelling(cursor))
{
IsAnonymous = cursor.IsAnonymous,
Visibility = GetVisibility(cursor.CXXAccessSpecifier)
@ -138,7 +138,7 @@ namespace CppAst
case CXCursorKind.CXCursor_StructDecl:
case CXCursorKind.CXCursor_UnionDecl:
Debug.Assert(parent != null);
var cppClass = new CppClass(GetCursorSpelling(cursor));
var cppClass = new CppClass(CXUtil.GetCursorSpelling(cursor));
parentDeclarationContainer.Classes.Add(cppClass);
symbol = cppClass;
cppClass.IsAnonymous = cursor.IsAnonymous;
@ -220,12 +220,12 @@ namespace CppAst
break;
default:
{
Debug.WriteLine($"[Warning]template argument in class:{cppClass.FullName} with type: {arg.kind.ToString()} do not handle right now!");
Debug.WriteLine($"[Warning]template argument in class:{cppClass.FullName} with type: {arg.kind} do not handle right now!");
cppClass.TemplateSpecializedArguments.Add(new CppTemplateArgument(tempParams[(int)i], arg.ToString()));
}
break;
}
arg.Dispose();
}
}
else
@ -305,7 +305,7 @@ namespace CppAst
{
var containerContext = GetOrCreateDeclarationContainer(parent, data);
var cppEnum = (CppEnum)containerContext.Container;
var enumItem = new CppEnumItem(GetCursorSpelling(cursor), cursor.EnumConstantDeclValue);
var enumItem = new CppEnumItem(CXUtil.GetCursorSpelling(cursor), cursor.EnumConstantDeclValue);
ParseAttributes(cursor, enumItem, true);
VisitInitValue(cursor, data, out var enumItemExpression, out var enumValue);
@ -428,7 +428,7 @@ namespace CppAst
// Don't emit warning
break;
default:
//WarningUnhandled(cursor, parent);
WarningUnhandled(cursor, parent);
break;
}
@ -483,13 +483,13 @@ namespace CppAst
case CppCommentKind.Text:
cppComment = new CppCommentText()
{
Text = cxComment.TextComment_Text.ToString()?.TrimStart()
Text = CXUtil.GetComment_TextComment_Text(cxComment)?.TrimStart()
};
break;
case CppCommentKind.InlineCommand:
var inline = new CppCommentInlineCommand();
inline.CommandName = cxComment.InlineCommandComment_CommandName.ToString();
inline.CommandName = CXUtil.GetComment_InlineCommandComment_CommandName(cxComment);
cppComment = inline;
switch (cxComment.InlineCommandComment_RenderKind)
{
@ -509,19 +509,19 @@ namespace CppAst
for (uint i = 0; i < cxComment.InlineCommandComment_NumArgs; i++)
{
inline.Arguments.Add(cxComment.InlineCommandComment_GetArgText(i).ToString());
inline.Arguments.Add(CXUtil.GetComment_InlineCommandComment_ArgText(cxComment, i));
}
break;
case CppCommentKind.HtmlStartTag:
var htmlStartTag = new CppCommentHtmlStartTag();
htmlStartTag.TagName = cxComment.HtmlTagComment_TagName.ToString();
htmlStartTag.TagName = CXUtil.GetComment_HtmlTagComment_TagName(cxComment);
htmlStartTag.IsSelfClosing = cxComment.HtmlStartTagComment_IsSelfClosing;
for (uint i = 0; i < cxComment.HtmlStartTag_NumAttrs; i++)
{
htmlStartTag.Attributes.Add(new KeyValuePair<string, string>(
cxComment.HtmlStartTag_GetAttrName(i).ToString(),
cxComment.HtmlStartTag_GetAttrValue(i).ToString()
CXUtil.GetComment_HtmlStartTag_AttrName(cxComment, i),
CXUtil.GetComment_HtmlStartTag_AttrValue(cxComment, i)
));
}
cppComment = htmlStartTag;
@ -529,7 +529,7 @@ namespace CppAst
case CppCommentKind.HtmlEndTag:
var htmlEndTag = new CppCommentHtmlEndTag();
htmlEndTag.TagName = cxComment.HtmlTagComment_TagName.ToString();
htmlEndTag.TagName = CXUtil.GetComment_HtmlTagComment_TagName(cxComment);
cppComment = htmlEndTag;
break;
@ -539,10 +539,10 @@ namespace CppAst
case CppCommentKind.BlockCommand:
var blockComment = new CppCommentBlockCommand();
blockComment.CommandName = cxComment.BlockCommandComment_CommandName.ToString();
blockComment.CommandName = CXUtil.GetComment_BlockCommandComment_CommandName(cxComment);
for (uint i = 0; i < cxComment.BlockCommandComment_NumArgs; i++)
{
blockComment.Arguments.Add(cxComment.BlockCommandComment_GetArgText(i).ToString());
blockComment.Arguments.Add(CXUtil.GetComment_BlockCommandComment_ArgText(cxComment, i));
}
removeTrailingEmptyText = true;
@ -552,7 +552,7 @@ namespace CppAst
case CppCommentKind.ParamCommand:
var paramComment = new CppCommentParamCommand();
paramComment.CommandName = "param";
paramComment.ParamName = cxComment.ParamCommandComment_ParamName.ToString();
paramComment.ParamName = CXUtil.GetComment_ParamCommandComment_ParamName(cxComment);
paramComment.IsDirectionExplicit = cxComment.ParamCommandComment_IsDirectionExplicit;
paramComment.IsParamIndexValid = cxComment.ParamCommandComment_IsParamIndexValid;
paramComment.ParamIndex = (int)cxComment.ParamCommandComment_ParamIndex;
@ -576,7 +576,7 @@ namespace CppAst
case CppCommentKind.TemplateParamCommand:
var tParamComment = new CppCommentTemplateParamCommand();
tParamComment.CommandName = "tparam";
tParamComment.ParamName = cxComment.TParamCommandComment_ParamName.ToString();
tParamComment.ParamName = CXUtil.GetComment_TParamCommandComment_ParamName(cxComment);
tParamComment.Depth = (int)cxComment.TParamCommandComment_Depth;
// TODO: index
tParamComment.IsPositionValid = cxComment.TParamCommandComment_IsParamPositionValid;
@ -586,15 +586,15 @@ namespace CppAst
break;
case CppCommentKind.VerbatimBlockCommand:
var verbatimBlock = new CppCommentVerbatimBlockCommand();
verbatimBlock.CommandName = cxComment.BlockCommandComment_CommandName.ToString();
verbatimBlock.CommandName = CXUtil.GetComment_BlockCommandComment_CommandName(cxComment);
for (uint i = 0; i < cxComment.BlockCommandComment_NumArgs; i++)
{
verbatimBlock.Arguments.Add(cxComment.BlockCommandComment_GetArgText(i).ToString());
verbatimBlock.Arguments.Add(CXUtil.GetComment_BlockCommandComment_ArgText(cxComment, i));
}
cppComment = verbatimBlock;
break;
case CppCommentKind.VerbatimBlockLine:
var text = cxComment.VerbatimBlockLineComment_Text.ToString();
var text = CXUtil.GetComment_VerbatimBlockLineComment_Text(cxComment);
// For some reason, VerbatimBlockLineComment_Text can return the rest of the file instead of just the line
// So we explicitly trim the line here
@ -612,7 +612,7 @@ namespace CppAst
case CppCommentKind.VerbatimLine:
cppComment = new CppCommentVerbatimLine()
{
Text = cxComment.VerbatimLineComment_Text.ToString()
Text = CXUtil.GetComment_VerbatimLineComment_Text(cxComment)
};
break;
case CppCommentKind.Full:
@ -716,10 +716,11 @@ namespace CppAst
var tokens = tu.Tokenize(range);
var name = GetCursorSpelling(cursor);
var name = CXUtil.GetCursorSpelling(cursor);
if (name.StartsWith("__cppast"))
{
//cppast system macros, just ignore here
tu.DisposeTokens(tokens);
return null;
}
@ -741,7 +742,7 @@ namespace CppAst
{
break;
}
var tokenStr = token.GetSpelling(tu).CString;
var tokenStr = CXUtil.GetTokenSpelling(token, tu);
// If we are parsing the token right after the MACRO name token
// if the `(` is right after the name without
@ -805,6 +806,7 @@ namespace CppAst
var globalContainer = (CppGlobalDeclarationContainer)_rootContainerContext.DeclarationContainer;
globalContainer.Macros.Add(cppMacro);
tu.DisposeTokens(tokens);
return cppMacro;
}
@ -834,22 +836,43 @@ namespace CppAst
public static CppSourceLocation GetSourceLocation(CXSourceLocation start)
{
start.GetFileLocation(out var file, out var line, out var column, out var offset);
return new CppSourceLocation(file.Name.CString, (int)offset, (int)line, (int)column);
var fileNameStr = CXUtil.GetFileName(file);
return new CppSourceLocation(fileNameStr, (int)offset, (int)line, (int)column);
}
private static bool IsAnonymousTypeUsed(CppType type, CppType anonymousType)
{
return IsAnonymousTypeUsed(type, anonymousType, new HashSet<CppType>());
}
private static bool IsAnonymousTypeUsed(CppType type, CppType anonymousType, HashSet<CppType> visited)
{
if (!visited.Add(type)) return false;
if (ReferenceEquals(type, anonymousType)) return true;
if (type is CppTypeWithElementType typeWithElementType)
{
return IsAnonymousTypeUsed(typeWithElementType.ElementType, anonymousType);
}
return false;
}
private CppField VisitFieldOrVariable(CppContainerContext containerContext, CXCursor cursor, void* data)
{
var fieldName = GetCursorSpelling(cursor);
var fieldName = CXUtil.GetCursorSpelling(cursor);
var type = GetCppType(cursor.Type.Declaration, cursor.Type, cursor, data);
var previousField = containerContext.DeclarationContainer.Fields.Count > 0 ? containerContext.DeclarationContainer.Fields[containerContext.DeclarationContainer.Fields.Count - 1] : null;
CppField cppField;
// This happen in the type is anonymous, we create implicitly a field for it, but if type is the same
// we should reuse the anonymous field we created just before
if (previousField != null && previousField.IsAnonymous && ReferenceEquals(previousField.Type, type))
if (previousField != null && previousField.IsAnonymous && IsAnonymousTypeUsed(type, previousField.Type))
{
cppField = previousField;
cppField.Name = fieldName;
cppField.Type = type;
cppField.Offset = cursor.OffsetOfField / 8;
}
else
@ -905,8 +928,8 @@ namespace CppAst
return CXChildVisitResult.CXChildVisit_Continue;
}, new CXClientData((IntPtr)data));
// Still tries to extract the compiled value
var resultEval = new CXEvalResult((IntPtr)clang.Cursor_Evaluate(cursor));
// Still tries to extract the compiled value
CXEvalResult resultEval = cursor.Evaluate;
switch (resultEval.Kind)
{
@ -924,12 +947,13 @@ namespace CppAst
case CXEvalResultKind.CXEval_UnExposed:
break;
default:
RootCompilation.Diagnostics.Warning($"Not supported field default value {cursor}", GetSourceLocation(cursor.Location));
RootCompilation.Diagnostics.Warning($"Not supported field default value {CXUtil.GetCursorSpelling(cursor)}", GetSourceLocation(cursor.Location));
break;
}
expression = localExpression;
value = localValue;
resultEval.Dispose();
}
private static bool IsExpression(CXCursor cursor)
@ -1226,7 +1250,7 @@ namespace CppAst
return null;
}
var functionName = GetCursorSpelling(cursor);
var functionName = CXUtil.GetCursorSpelling(cursor);
//We need ignore the function define out in the class definition here(Otherwise it will has two same functions here~)!
var semKind = cursor.SemanticParent.Kind;
@ -1336,9 +1360,9 @@ namespace CppAst
switch (argCursor.Kind)
{
case CXCursorKind.CXCursor_ParmDecl:
var argName = GetCursorSpelling(argCursor);
var argName = CXUtil.GetCursorSpelling(argCursor);
var parameter = new CppParameter(GetCppType(argCursor.Type.Declaration, argCursor.Type, functionCursor, clientData), argName);
var parameter = new CppParameter(GetCppType(argCursor.Type.Declaration, argCursor.Type, argCursor, clientData), argName);
cppFunction.Parameters.Add(parameter);
@ -1440,14 +1464,14 @@ namespace CppAst
cursor.VisitChildren((argCursor, parentCursor, clientData) =>
{
var sourceSpan = new CppSourceSpan(GetSourceLocation(argCursor.SourceRange.Start), GetSourceLocation(argCursor.SourceRange.End));
var meta = argCursor.Spelling.CString;
var meta = CXUtil.GetCursorSpelling(argCursor);
switch (argCursor.Kind)
{
case CXCursorKind.CXCursor_VisibilityAttr:
{
CppAttribute attribute = new CppAttribute("visibility", AttributeKind.CxxSystemAttribute);
AssignSourceSpan(argCursor, attribute);
attribute.Arguments = string.Format("\"{0}\"", argCursor.DisplayName.ToString());
attribute.Arguments = string.Format("\"{0}\"", CXUtil.GetCursorDisplayName(argCursor));
collectAttributes.Add(attribute);
}
break;
@ -1589,7 +1613,7 @@ namespace CppAst
if (!string.IsNullOrEmpty(errorMessage))
{
var element = (CppElement)attrContainer;
//throw new Exception($"handle meta not right, detail: `{errorMessage}, location: `{element.Span}`");
throw new Exception($"handle meta not right, detail: `{errorMessage}, location: `{element.Span}`");
}
AppendToMetaAttributes(attrContainer.MetaAttributes.MetaList, metaAttr);
@ -1646,7 +1670,7 @@ namespace CppAst
private CppType VisitTypeAliasDecl(CXCursor cursor, void* data)
{
var fulltypeDefName = clang.getCursorUSR(cursor).CString;
var fulltypeDefName = CXUtil.GetCursorUsrString(cursor);
if (_typedefs.TryGetValue(fulltypeDefName, out var type))
{
return type;
@ -1663,7 +1687,7 @@ namespace CppAst
}
var underlyingTypeDefType = GetCppType(usedCursor.TypedefDeclUnderlyingType.Declaration, usedCursor.TypedefDeclUnderlyingType, usedCursor, data);
var typedefName = GetCursorSpelling(usedCursor);
var typedefName = CXUtil.GetCursorSpelling(usedCursor);
if (AutoSquashTypedef && underlyingTypeDefType is ICppMember cppMember && (string.IsNullOrEmpty(cppMember.Name) || typedefName == cppMember.Name))
{
@ -1693,7 +1717,7 @@ namespace CppAst
private CppType VisitTypeDefDecl(CXCursor cursor, void* data)
{
var fulltypeDefName = clang.getCursorUSR(cursor).CString;
var fulltypeDefName = CXUtil.GetCursorUsrString(cursor);
if (_typedefs.TryGetValue(fulltypeDefName, out var type))
{
return type;
@ -1701,8 +1725,8 @@ namespace CppAst
var contextContainer = GetOrCreateDeclarationContainer(cursor.SemanticParent, data);
var underlyingTypeDefType = GetCppType(cursor.TypedefDeclUnderlyingType.Declaration, cursor.TypedefDeclUnderlyingType, cursor, data);
var typedefName = GetCursorSpelling(cursor);
var typedefName = CXUtil.GetCursorSpelling(cursor);
if (AutoSquashTypedef && underlyingTypeDefType is ICppMember cppMember && (string.IsNullOrEmpty(cppMember.Name) || typedefName == cppMember.Name))
{
@ -1732,8 +1756,9 @@ namespace CppAst
private CppType VisitElaboratedDecl(CXCursor cursor, CXType type, CXCursor parent, void* data)
{
var fulltypeDefName = clang.getCursorUSR(cursor).CString;
if (_typedefs.TryGetValue(fulltypeDefName, out var typeRef)) {
var fulltypeDefName = CXUtil.GetCursorUsrString(cursor);
if (_typedefs.TryGetValue(fulltypeDefName, out var typeRef))
{
return typeRef;
}
@ -1763,8 +1788,6 @@ namespace CppAst
return builder.ToString();
}
private string GetCursorSpelling(CXCursor cursor) => cursor.Spelling.ToString();
private CppType GetCppType(CXCursor cursor, CXType type, CXCursor parent, void* data)
{
var cppType = GetCppTypeInternal(cursor, type, parent, data);
@ -1813,7 +1836,7 @@ namespace CppAst
return CppPrimitiveType.UnsignedInt;
case CXTypeKind.CXType_ULong:
return type.SizeOf == 8 ? CppPrimitiveType.UnsignedLongLong : CppPrimitiveType.UnsignedInt;
return CppPrimitiveType.UnsignedLong;
case CXTypeKind.CXType_ULongLong:
return CppPrimitiveType.UnsignedLongLong;
@ -1834,7 +1857,7 @@ namespace CppAst
return CppPrimitiveType.Int;
case CXTypeKind.CXType_Long:
return CppPrimitiveType.Int;
return CppPrimitiveType.Long;
case CXTypeKind.CXType_LongLong:
return CppPrimitiveType.LongLong;
@ -1879,7 +1902,7 @@ namespace CppAst
case CXTypeKind.CXType_DependentSizedArray:
{
// TODO: this is not yet supported
//RootCompilation.Diagnostics.Warning($"Dependent sized arrays `{type}` from `{parent}` is not supported", GetSourceLocation(parent.Location));
RootCompilation.Diagnostics.Warning($"Dependent sized arrays `{CXUtil.GetTypeSpelling(type)}` from `{CXUtil.GetCursorSpelling(parent)}` is not supported", GetSourceLocation(parent.Location));
var elementType = GetCppType(type.ArrayElementType.Declaration, type.ArrayElementType, parent, data);
return new CppArrayType(elementType, (int)type.ArraySize);
}
@ -1893,7 +1916,7 @@ namespace CppAst
return GetCppType(type.Declaration, type.Declaration.Type, parent, data);
}
var cppUnexposedType = new CppUnexposedType(type.ToString()) { SizeOf = (int)type.SizeOf };
var cppUnexposedType = new CppUnexposedType(CXUtil.GetTypeSpelling(type)) { SizeOf = (int)type.SizeOf };
var templateParameters = ParseTemplateSpecializedArguments(cursor, type, new CXClientData((IntPtr)data));
if (templateParameters != null)
{
@ -1910,8 +1933,8 @@ namespace CppAst
default:
{
//WarningUnhandled(cursor, parent, type);
return new CppUnexposedType(type.ToString()) { SizeOf = (int)type.SizeOf };
WarningUnhandled(cursor, parent, type);
return new CppUnexposedType(CXUtil.GetTypeSpelling(type)) { SizeOf = (int)type.SizeOf };
}
}
}
@ -1936,12 +1959,12 @@ namespace CppAst
// }
bool isParsingParameter = false;
parent.VisitChildren((cxCursor, parent1, clientData) =>
parent.VisitChildren((argCursor, functionCursor, clientData) =>
{
if (cxCursor.Kind == CXCursorKind.CXCursor_ParmDecl)
if (argCursor.Kind == CXCursorKind.CXCursor_ParmDecl)
{
var name = GetCursorSpelling(cxCursor);
var parameterType = GetCppType(cxCursor.Type.Declaration, cxCursor.Type, cxCursor, data);
var name = CXUtil.GetCursorSpelling(argCursor);
var parameterType = GetCppType(argCursor.Type.Declaration, argCursor.Type, argCursor, data);
cppFunction.Parameters.Add(new CppParameter(parameterType, name));
isParsingParameter = true;
@ -1955,7 +1978,7 @@ namespace CppAst
private void Unhandled(CXCursor cursor)
{
var cppLocation = GetSourceLocation(cursor.Location);
RootCompilation.Diagnostics.Warning($"Unhandled declaration: {cursor.Kind}/{cursor}.", cppLocation);
RootCompilation.Diagnostics.Warning($"Unhandled declaration: {cursor.Kind}/{CXUtil.GetCursorSpelling(cursor)}.", cppLocation);
}
private void WarningUnhandled(CXCursor cursor, CXCursor parent, CXType type)
@ -1965,7 +1988,7 @@ namespace CppAst
{
cppLocation = GetSourceLocation(parent.Location);
}
RootCompilation.Diagnostics.Warning($"The type {cursor.Kind}/`{type}` of kind `{type.KindSpelling}` is not supported in `{parent}`", cppLocation);
RootCompilation.Diagnostics.Warning($"The type {cursor.Kind}/`{CXUtil.GetTypeSpelling(type)}` of kind `{CXUtil.GetTypeKindSpelling(type)}` is not supported in `{CXUtil.GetCursorSpelling(parent)}`", cppLocation);
}
protected void WarningUnhandled(CXCursor cursor, CXCursor parent)
@ -1975,7 +1998,7 @@ namespace CppAst
{
cppLocation = GetSourceLocation(parent.Location);
}
RootCompilation.Diagnostics.Warning($"Unhandled declaration: {cursor.Kind}/{cursor} in {parent}.", cppLocation);
RootCompilation.Diagnostics.Warning($"Unhandled declaration: {cursor.Kind}/{CXUtil.GetCursorSpelling(cursor)} in {CXUtil.GetCursorSpelling(parent)}.", cppLocation);
}
private List<CppType> ParseTemplateSpecializedArguments(CXCursor cursor, CXType type, CXClientData data)

View File

@ -64,27 +64,6 @@ namespace CppAst
public MetaAttributeMap MetaAttributes { get; private set; } = new MetaAttributeMap();
protected bool Equals(CppNamespace other)
{
return Equals(Parent, other.Parent) && Name.Equals(other.Name);
}
public override bool Equals(object obj)
{
if (ReferenceEquals(null, obj)) return false;
if (ReferenceEquals(this, obj)) return true;
if (obj.GetType() != this.GetType()) return false;
return Equals((CppNamespace)obj);
}
public override int GetHashCode()
{
unchecked
{
return ((Parent != null ? Parent.GetHashCode() : 0) * 397) ^ (Name != null ? Name.GetHashCode() : 0);
}
}
public override string ToString()
{
return $"namespace {Name} {{...}}";

View File

@ -42,24 +42,6 @@ namespace CppAst
/// </summary>
public CppExpression InitExpression { get; set; }
private bool Equals(CppParameter other)
{
return Equals(Type, other.Type) && Equals(Name, other.Name);
}
public override bool Equals(object obj)
{
return ReferenceEquals(this, obj) || obj is CppParameter other && Equals(other);
}
public override int GetHashCode()
{
unchecked
{
return ((Type != null ? Type.GetHashCode() : 0) * 397) ^ (Name != null ? Name.GetHashCode() : 0);
}
}
public override string ToString()
{
if (string.IsNullOrEmpty(Name))

View File

@ -164,72 +164,64 @@ namespace CppAst
// TODO: Add debug
rootFileContent = tempBuilder.ToString();
var rootFileContentUTF8 = Encoding.UTF8.GetBytes(rootFileContent);
compilation.InputText = rootFileContent;
fixed (void* rootFileContentUTF8Ptr = rootFileContentUTF8)
CXTranslationUnit translationUnit;
using (CXUnsavedFile unsavedFile = CXUnsavedFile.Create(rootFileName, rootFileContent))
{
CXTranslationUnit translationUnit;
ReadOnlySpan<CXUnsavedFile> unsavedFiles = stackalloc CXUnsavedFile[] { unsavedFile };
var rootFileNameUTF8 = Marshal.StringToHGlobalAnsi(rootFileName);
translationUnit = CXTranslationUnit.Parse(createIndex
, rootFileName
, argumentsArray
, unsavedFiles
, translationFlags);
}
translationUnit = CXTranslationUnit.Parse(createIndex, rootFileName, argumentsArray,new CXUnsavedFile[]
bool skipProcessing = false;
if (translationUnit.NumDiagnostics != 0)
{
for (uint i = 0; i < translationUnit.NumDiagnostics; ++i)
{
new CXUnsavedFile()
using (var diagnostic = translationUnit.GetDiagnostic(i))
{
Contents = (sbyte*) rootFileContentUTF8Ptr,
Filename = (sbyte*) rootFileNameUTF8,
Length = new UIntPtr((uint)rootFileContentUTF8.Length)
var message = GetMessageAndLocation(rootFileContent, diagnostic, out var location);
}
}, translationFlags);
bool skipProcessing = false;
if (translationUnit.NumDiagnostics != 0)
{
for (uint i = 0; i < translationUnit.NumDiagnostics; ++i)
{
using (var diagnostic = translationUnit.GetDiagnostic(i))
switch (diagnostic.Severity)
{
var message = GetMessageAndLocation(rootFileContent, diagnostic, out var location);
switch (diagnostic.Severity)
{
case CXDiagnosticSeverity.CXDiagnostic_Ignored:
case CXDiagnosticSeverity.CXDiagnostic_Note:
compilation.Diagnostics.Info(message, location);
break;
case CXDiagnosticSeverity.CXDiagnostic_Warning:
// Avoid warning from clang (0, 0): warning: argument unused during compilation: '-fsyntax-only'
if (!message.Contains("-fsyntax-only"))
{
compilation.Diagnostics.Warning(message, location);
}
break;
case CXDiagnosticSeverity.CXDiagnostic_Error:
case CXDiagnosticSeverity.CXDiagnostic_Fatal:
compilation.Diagnostics.Error(message, location);
skipProcessing = true;
break;
}
case CXDiagnosticSeverity.CXDiagnostic_Ignored:
case CXDiagnosticSeverity.CXDiagnostic_Note:
compilation.Diagnostics.Info(message, location);
break;
case CXDiagnosticSeverity.CXDiagnostic_Warning:
// Avoid warning from clang (0, 0): warning: argument unused during compilation: '-fsyntax-only'
if (!message.Contains("-fsyntax-only"))
{
compilation.Diagnostics.Warning(message, location);
}
break;
case CXDiagnosticSeverity.CXDiagnostic_Error:
case CXDiagnosticSeverity.CXDiagnostic_Fatal:
compilation.Diagnostics.Error(message, location);
skipProcessing = true;
break;
}
}
}
if (skipProcessing && false)
{
compilation.Diagnostics.Warning($"Compilation aborted due to one or more errors listed above.", new CppSourceLocation(rootFileName, 0, 1, 1));
}
else
{
using (translationUnit)
{
translationUnit.Cursor.VisitChildren(builder.VisitTranslationUnit, clientData: default);
}
}
}
if (skipProcessing)
{
compilation.Diagnostics.Warning($"Compilation aborted due to one or more errors listed above.", new CppSourceLocation(rootFileName, 0, 1, 1));
}
else
{
translationUnit.Cursor.VisitChildren(builder.VisitTranslationUnit, clientData: default);
}
translationUnit.Dispose();
return compilation;
}
}
@ -263,6 +255,7 @@ namespace CppAst
}
}
diagnostic.Dispose();
return builder.ToString();
}

View File

@ -39,6 +39,11 @@ namespace CppAst
/// </summary>
Int,
/// <summary>
/// C++ `long`
/// </summary>
Long,
/// <summary>
/// C++ `long long` (64bits)
/// </summary>
@ -59,6 +64,11 @@ namespace CppAst
/// </summary>
UnsignedInt,
/// <summary>
/// C++ `unsigned long`
/// </summary>
UnsignedLong,
/// <summary>
/// C++ `unsigned long long` (64 bits)
/// </summary>

View File

@ -41,6 +41,11 @@ namespace CppAst
/// </summary>
public static readonly CppPrimitiveType Int = new CppPrimitiveType(CppPrimitiveKind.Int);
/// <summary>
/// Singleton instance of the `long` type.
/// </summary>
public static readonly CppPrimitiveType Long = new CppPrimitiveType(CppPrimitiveKind.Long);
/// <summary>
/// Singleton instance of the `long long` type.
/// </summary>
@ -61,6 +66,11 @@ namespace CppAst
/// </summary>
public static readonly CppPrimitiveType UnsignedInt = new CppPrimitiveType(CppPrimitiveKind.UnsignedInt);
/// <summary>
/// Singleton instance of the `unsigned long` type.
/// </summary>
public static readonly CppPrimitiveType UnsignedLong = new CppPrimitiveType(CppPrimitiveKind.UnsignedLong);
/// <summary>
/// Singleton instance of the `unsigned long long` type.
/// </summary>
@ -120,6 +130,10 @@ namespace CppAst
case CppPrimitiveKind.Int:
sizeOf = 4;
break;
case CppPrimitiveKind.Long:
case CppPrimitiveKind.UnsignedLong:
sizeOf = 4; // This is incorrect
break;
case CppPrimitiveKind.LongLong:
sizeOf = 8;
break;
@ -164,6 +178,10 @@ namespace CppAst
return "short";
case CppPrimitiveKind.Int:
return "int";
case CppPrimitiveKind.Long:
return "long";
case CppPrimitiveKind.UnsignedLong:
return "unsigned long";
case CppPrimitiveKind.LongLong:
return "long long";
case CppPrimitiveKind.UnsignedChar:
@ -199,21 +217,6 @@ namespace CppAst
set => throw new InvalidOperationException("Cannot set the SizeOf of a primitive type");
}
/// <inheritdoc />
public override bool Equals(object obj)
{
return ReferenceEquals(this, obj) || obj is CppPrimitiveType other && Equals(other);
}
/// <inheritdoc />
public override int GetHashCode()
{
unchecked
{
return (base.GetHashCode() * 397) ^ (int)Kind;
}
}
/// <inheritdoc />
public override CppType GetCanonicalType()
{

View File

@ -25,26 +25,6 @@ namespace CppAst
/// </summary>
public CppTypeQualifier Qualifier { get; }
private bool Equals(CppQualifiedType other)
{
return base.Equals(other) && Qualifier == other.Qualifier;
}
/// <inheritdoc />
public override bool Equals(object obj)
{
return ReferenceEquals(this, obj) || obj is CppQualifiedType other && Equals(other);
}
/// <inheritdoc />
public override int GetHashCode()
{
unchecked
{
return (base.GetHashCode() * 397) ^ (int)Qualifier;
}
}
/// <inheritdoc />
public override CppType GetCanonicalType()
{

View File

@ -77,22 +77,6 @@ namespace CppAst
set => throw new InvalidOperationException("This type does not support SizeOf");
}
/// <inheritdoc />
public override bool Equals(object obj)
{
return ReferenceEquals(this, obj) || obj is CppTemplateArgument other && Equals(other);
}
/// <inheritdoc />
public override int GetHashCode()
{
unchecked
{
return (base.GetHashCode() * 397) ^ SourceParam.GetHashCode() ^ ArgString.GetHashCode();
}
}
/// <inheritdoc />
public override CppType GetCanonicalType() => this;

View File

@ -41,21 +41,6 @@ namespace CppAst
set => throw new InvalidOperationException("This type does not support SizeOf");
}
/// <inheritdoc />
public override bool Equals(object obj)
{
return ReferenceEquals(this, obj) || obj is CppTemplateParameterNonType other && Equals(other);
}
/// <inheritdoc />
public override int GetHashCode()
{
unchecked
{
return (base.GetHashCode() * 397) ^ Name.GetHashCode();
}
}
/// <inheritdoc />
public override CppType GetCanonicalType() => this;

View File

@ -37,21 +37,6 @@ namespace CppAst
set => throw new InvalidOperationException("This type does not support SizeOf");
}
/// <inheritdoc />
public override bool Equals(object obj)
{
return ReferenceEquals(this, obj) || obj is CppTemplateParameterType other && Equals(other);
}
/// <inheritdoc />
public override int GetHashCode()
{
unchecked
{
return (base.GetHashCode() * 397) ^ Name.GetHashCode();
}
}
/// <inheritdoc />
public override CppType GetCanonicalType() => this;

View File

@ -439,21 +439,20 @@ namespace CppAst
[DebuggerTypeProxy(typeof(TokenizerDebuggerType))]
internal class Tokenizer
{
private readonly CXToken[] _tokens;
private readonly CXSourceRange _range;
private CppToken[] _cppTokens;
protected readonly CXTranslationUnit _tu;
public Tokenizer(CXCursor cursor)
{
_tu = cursor.TranslationUnit;
var range = GetRange(cursor);
_tokens = _tu.Tokenize(range).ToArray();
_range = GetRange(cursor);
}
public Tokenizer(CXTranslationUnit tu, CXSourceRange range)
{
_tu = tu;
_tokens = _tu.Tokenize(range).ToArray();
_range = range;
}
public virtual CXSourceRange GetRange(CXCursor cursor)
@ -461,7 +460,16 @@ namespace CppAst
return cursor.Extent;
}
public int Count => _tokens?.Length ?? 0;
public int Count
{
get
{
var tokens = _tu.Tokenize(_range);
int length = tokens.Length;
_tu.DisposeTokens(tokens);
return length;
}
}
public CppToken this[int i]
{
@ -470,7 +478,7 @@ namespace CppAst
// Only create a tokenizer if necessary
if (_cppTokens == null)
{
_cppTokens = new CppToken[_tokens.Length];
_cppTokens = new CppToken[Count];
}
ref var cppToken = ref _cppTokens[i];
@ -478,8 +486,9 @@ namespace CppAst
{
return cppToken;
}
var tokens = _tu.Tokenize(_range);
var token = tokens[i];
var token = _tokens[i];
CppTokenKind cppTokenKind = 0;
switch (token.Kind)
{
@ -502,7 +511,7 @@ namespace CppAst
break;
}
var tokenStr = token.GetSpelling(_tu).CString;
var tokenStr = CXUtil.GetTokenSpelling(token, _tu);
var tokenLocation = token.GetLocation(_tu);
var tokenRange = token.GetExtent(_tu);
@ -510,26 +519,30 @@ namespace CppAst
{
Span = new CppSourceSpan(CppModelBuilder.GetSourceLocation(tokenRange.Start), CppModelBuilder.GetSourceLocation(tokenRange.End))
};
_tu.DisposeTokens(tokens);
return cppToken;
}
}
public string GetString(int i)
{
var token = _tokens[i];
return token.GetSpelling(_tu).CString;
var tokens = _tu.Tokenize(_range);
var TokenSpelling = CXUtil.GetTokenSpelling(tokens[i], _tu);
_tu.DisposeTokens(tokens);
return TokenSpelling;
}
public string TokensToString()
{
if (_tokens == null)
int length = Count;
if (length <= 0)
{
return null;
}
var tokens = new List<CppToken>(_tokens.Length);
var tokens = new List<CppToken>(length);
for (int i = 0; i < _tokens.Length; i++)
for (int i = 0; i < length; i++)
{
tokens.Add(this[i]);
}

View File

@ -25,24 +25,6 @@ namespace CppAst
public abstract int SizeOf { get; set; }
protected bool Equals(CppType other)
{
return TypeKind == other.TypeKind;
}
public override bool Equals(object obj)
{
if (ReferenceEquals(null, obj)) return false;
if (ReferenceEquals(this, obj)) return true;
return obj is CppType type && Equals(type);
}
/// <inheritdoc />
public override int GetHashCode()
{
return (int)TypeKind;
}
/// <summary>
/// Gets the canonical type of this type instance.
/// </summary>

View File

@ -18,30 +18,7 @@ namespace CppAst
public CppType ElementType { get; }
protected bool Equals(CppTypeWithElementType other)
{
return base.Equals(other) && ElementType.Equals(other.ElementType);
}
/// <inheritdoc />
public override int SizeOf { get; set; }
/// <inheritdoc />
public override bool Equals(object obj)
{
if (ReferenceEquals(null, obj)) return false;
if (ReferenceEquals(this, obj)) return true;
if (obj.GetType() != GetType()) return false;
return Equals((CppTypeWithElementType)obj);
}
/// <inheritdoc />
public override int GetHashCode()
{
unchecked
{
return (base.GetHashCode() * 397) ^ ElementType.GetHashCode();
}
}
}
}

View File

@ -61,11 +61,6 @@ namespace CppAst
}
}
private bool Equals(CppTypedef other)
{
return base.Equals(other) && string.Equals(Name, other.Name);
}
/// <inheritdoc />
public override int SizeOf
{
@ -73,21 +68,6 @@ namespace CppAst
set => throw new InvalidOperationException("Cannot set the SizeOf a TypeDef. The SizeOf is determined by the underlying ElementType");
}
/// <inheritdoc />
public override bool Equals(object obj)
{
return ReferenceEquals(this, obj) || obj is CppTypedef other && Equals(other);
}
/// <inheritdoc />
public override int GetHashCode()
{
unchecked
{
return (base.GetHashCode() * 397) ^ Name.GetHashCode();
}
}
/// <inheritdoc />
public override CppType GetCanonicalType()
{

View File

@ -30,32 +30,12 @@ namespace CppAst
/// </summary>
public string Name { get; }
private bool Equals(CppTemplateParameterType other)
{
return base.Equals(other) && Name.Equals(other.Name);
}
/// <inheritdoc />
public override int SizeOf { get; set; }
/// <inheritdoc />
public List<CppType> TemplateParameters { get; }
/// <inheritdoc />
public override bool Equals(object obj)
{
return ReferenceEquals(this, obj) || obj is CppTemplateParameterType other && Equals(other);
}
/// <inheritdoc />
public override int GetHashCode()
{
unchecked
{
return (base.GetHashCode() * 397) ^ Name.GetHashCode();
}
}
/// <inheritdoc />
public override CppType GetCanonicalType() => this;