Skip to content

Commit d21c101

Browse files
authored
Merge pull request #4041 from tamasvajk/feature/update-roslyn
C#: upgrade Roslyn dependencies to version 3.7
2 parents f5f4b8e + 0fb9dc5 commit d21c101

File tree

14 files changed

+3877
-41
lines changed

14 files changed

+3877
-41
lines changed

csharp/extractor/Semmle.Extraction.CSharp/Entities/Symbol.cs

Lines changed: 20 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -136,16 +136,32 @@ protected void PopulateMetadataHandle(TextWriter trapFile)
136136
trapFile.metadata_handle(this, Location, MetadataTokens.GetToken(handle.Value));
137137
}
138138

139+
static System.Reflection.PropertyInfo GetPropertyInfo(object o, string name) =>
140+
o.GetType().GetProperty(name, System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.GetProperty);
141+
139142
public Handle? MetadataHandle
140143
{
141144
get
142145
{
143-
var propertyInfo = symbol.GetType().GetProperty("Handle",
144-
System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.GetProperty);
146+
var handleProp = GetPropertyInfo(symbol, "Handle");
147+
object handleObj = symbol;
148+
149+
if (handleProp is null)
150+
{
151+
var underlyingSymbolProp = GetPropertyInfo(symbol, "UnderlyingSymbol");
152+
if (underlyingSymbolProp is object)
153+
{
154+
if (underlyingSymbolProp.GetValue(symbol) is object underlying)
155+
{
156+
handleProp = GetPropertyInfo(underlying, "Handle");
157+
handleObj = underlying;
158+
}
159+
}
160+
}
145161

146-
if (propertyInfo != null)
162+
if (handleProp is object)
147163
{
148-
switch (propertyInfo.GetValue(symbol))
164+
switch (handleProp.GetValue(handleObj))
149165
{
150166
case MethodDefinitionHandle md: return md;
151167
case TypeDefinitionHandle td: return td;

csharp/extractor/Semmle.Extraction.CSharp/Entities/Types/NamedType.cs

Lines changed: 29 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -11,13 +11,24 @@ namespace Semmle.Extraction.CSharp.Entities
1111
{
1212
class NamedType : Type<INamedTypeSymbol>
1313
{
14-
NamedType(Context cx, INamedTypeSymbol init)
14+
NamedType(Context cx, INamedTypeSymbol init, bool constructUnderlyingTupleType)
1515
: base(cx, init)
1616
{
1717
typeArgumentsLazy = new Lazy<Type[]>(() => symbol.TypeArguments.Select(t => Create(cx, t)).ToArray());
18+
this.constructUnderlyingTupleType = constructUnderlyingTupleType;
1819
}
1920

20-
public static NamedType Create(Context cx, INamedTypeSymbol type) => NamedTypeFactory.Instance.CreateEntityFromSymbol(cx, type);
21+
public static NamedType Create(Context cx, INamedTypeSymbol type) =>
22+
NamedTypeFactory.Instance.CreateEntityFromSymbol(cx, type);
23+
24+
/// <summary>
25+
/// Creates a named type entity from a tuple type. Unlike `Create`, this
26+
/// will create an entity for the underlying `System.ValueTuple` struct.
27+
/// For example, `(int, string)` will result in an entity for
28+
/// `System.ValueTuple<int, string>`.
29+
/// </summary>
30+
public static NamedType CreateNamedTypeFromTupleType(Context cx, INamedTypeSymbol type) =>
31+
UnderlyingTupleTypeFactory.Instance.CreateEntity(cx, (new SymbolEqualityWrapper(type), typeof(TupleType)), type);
2132

2233
public override bool NeedsPopulation => base.NeedsPopulation || symbol.TypeKind == TypeKind.Error;
2334

@@ -51,7 +62,10 @@ public override void Populate(TextWriter trapFile)
5162
}
5263
else
5364
{
54-
trapFile.constructed_generic(this, Type.Create(Context, symbol.ConstructedFrom).TypeRef);
65+
var unbound = constructUnderlyingTupleType
66+
? CreateNamedTypeFromTupleType(Context, symbol.ConstructedFrom)
67+
: Type.Create(Context, symbol.ConstructedFrom);
68+
trapFile.constructed_generic(this, unbound.TypeRef);
5569

5670
for (int i = 0; i < symbol.TypeArguments.Length; ++i)
5771
{
@@ -60,7 +74,7 @@ public override void Populate(TextWriter trapFile)
6074
}
6175
}
6276

63-
PopulateType(trapFile);
77+
PopulateType(trapFile, constructUnderlyingTupleType);
6478

6579
if (symbol.EnumUnderlyingType != null)
6680
{
@@ -76,6 +90,8 @@ public override void Populate(TextWriter trapFile)
7690
}
7791

7892
readonly Lazy<Type[]> typeArgumentsLazy;
93+
private readonly bool constructUnderlyingTupleType;
94+
7995
public Type[] TypeArguments => typeArgumentsLazy.Value;
8096

8197
public override IEnumerable<Type> TypeMentions => TypeArguments;
@@ -115,7 +131,7 @@ public override void WriteId(TextWriter trapFile)
115131
trapFile.Write('*');
116132
else
117133
{
118-
symbol.BuildTypeId(Context, trapFile, symbol);
134+
symbol.BuildTypeId(Context, trapFile, symbol, constructUnderlyingTupleType);
119135
trapFile.Write(";type");
120136
}
121137
}
@@ -161,7 +177,14 @@ class NamedTypeFactory : ICachedEntityFactory<INamedTypeSymbol, NamedType>
161177
{
162178
public static readonly NamedTypeFactory Instance = new NamedTypeFactory();
163179

164-
public NamedType Create(Context cx, INamedTypeSymbol init) => new NamedType(cx, init);
180+
public NamedType Create(Context cx, INamedTypeSymbol init) => new NamedType(cx, init, false);
181+
}
182+
183+
class UnderlyingTupleTypeFactory : ICachedEntityFactory<INamedTypeSymbol, NamedType>
184+
{
185+
public static readonly UnderlyingTupleTypeFactory Instance = new UnderlyingTupleTypeFactory();
186+
187+
public NamedType Create(Context cx, INamedTypeSymbol init) => new NamedType(cx, init, true);
165188
}
166189

167190
// Do not create typerefs of constructed generics as they are always in the current trap file.

csharp/extractor/Semmle.Extraction.CSharp/Entities/Types/TupleType.cs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,8 @@ public override void Populate(TextWriter trapFile)
4141
PopulateType(trapFile);
4242
PopulateGenerics();
4343

44-
var underlyingType = NamedType.Create(Context, symbol.TupleUnderlyingType);
44+
var underlyingType = NamedType.CreateNamedTypeFromTupleType(Context, symbol.TupleUnderlyingType ?? symbol);
45+
4546
trapFile.tuple_underlying_type(this, underlyingType);
4647

4748
int index = 0;

csharp/extractor/Semmle.Extraction.CSharp/Entities/Types/Type.cs

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,7 @@ public static bool ConstructedOrParentIsConstructed(INamedTypeSymbol symbol)
4747
symbol.ContainingType != null && ConstructedOrParentIsConstructed(symbol.ContainingType);
4848
}
4949

50-
static Kinds.TypeKind GetClassType(Context cx, ITypeSymbol t)
50+
static Kinds.TypeKind GetClassType(Context cx, ITypeSymbol t, bool constructUnderlyingTupleType)
5151
{
5252
switch (t.SpecialType)
5353
{
@@ -72,7 +72,9 @@ static Kinds.TypeKind GetClassType(Context cx, ITypeSymbol t)
7272
{
7373
case TypeKind.Class: return Kinds.TypeKind.CLASS;
7474
case TypeKind.Struct:
75-
return ((INamedTypeSymbol)t).IsTupleType ? Kinds.TypeKind.TUPLE : Kinds.TypeKind.STRUCT;
75+
return ((INamedTypeSymbol)t).IsTupleType && !constructUnderlyingTupleType
76+
? Kinds.TypeKind.TUPLE
77+
: Kinds.TypeKind.STRUCT;
7678
case TypeKind.Interface: return Kinds.TypeKind.INTERFACE;
7779
case TypeKind.Array: return Kinds.TypeKind.ARRAY;
7880
case TypeKind.Enum: return Kinds.TypeKind.ENUM;
@@ -85,17 +87,17 @@ static Kinds.TypeKind GetClassType(Context cx, ITypeSymbol t)
8587
}
8688
}
8789

88-
protected void PopulateType(TextWriter trapFile)
90+
protected void PopulateType(TextWriter trapFile, bool constructUnderlyingTupleType = false)
8991
{
9092
PopulateMetadataHandle(trapFile);
9193
PopulateAttributes();
9294

9395
trapFile.Write("types(");
9496
trapFile.WriteColumn(this);
9597
trapFile.Write(',');
96-
trapFile.WriteColumn((int)GetClassType(Context, symbol));
98+
trapFile.WriteColumn((int)GetClassType(Context, symbol, constructUnderlyingTupleType));
9799
trapFile.Write(",\"");
98-
symbol.BuildDisplayName(Context, trapFile);
100+
symbol.BuildDisplayName(Context, trapFile, constructUnderlyingTupleType);
99101
trapFile.WriteLine("\")");
100102

101103
// Visit base types

csharp/extractor/Semmle.Extraction.CSharp/Semmle.Extraction.CSharp.csproj

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@
2020
</ItemGroup>
2121

2222
<ItemGroup>
23-
<PackageReference Include="Microsoft.CodeAnalysis.CSharp" Version="3.4.0" />
23+
<PackageReference Include="Microsoft.CodeAnalysis.CSharp" Version="3.7.0" />
2424
</ItemGroup>
2525

2626
</Project>

csharp/extractor/Semmle.Extraction.CSharp/SymbolExtensions.cs

Lines changed: 19 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -117,7 +117,7 @@ bool IdDependsOnImpl(ITypeSymbol type)
117117
case TypeKind.Delegate:
118118
case TypeKind.Error:
119119
var named = (INamedTypeSymbol)type;
120-
if (named.IsTupleType)
120+
if (named.IsTupleType && named.TupleUnderlyingType is object)
121121
named = named.TupleUnderlyingType;
122122
if (IdDependsOnImpl(named.ContainingType))
123123
return true;
@@ -152,10 +152,11 @@ bool IdDependsOnImpl(ITypeSymbol type)
152152
/// <param name="cx">The extraction context.</param>
153153
/// <param name="trapFile">The trap builder used to store the result.</param>
154154
/// <param name="symbolBeingDefined">The outer symbol being defined (to avoid recursive ids).</param>
155-
public static void BuildTypeId(this ITypeSymbol type, Context cx, TextWriter trapFile, ISymbol symbolBeingDefined) =>
156-
type.BuildTypeId(cx, trapFile, symbolBeingDefined, true);
155+
/// <param name="constructUnderlyingTupleType">Whether to build a type ID for the underlying `System.ValueTuple` struct in the case of tuple types.</param>
156+
public static void BuildTypeId(this ITypeSymbol type, Context cx, TextWriter trapFile, ISymbol symbolBeingDefined, bool constructUnderlyingTupleType = false) =>
157+
type.BuildTypeId(cx, trapFile, symbolBeingDefined, true, constructUnderlyingTupleType);
157158

158-
static void BuildTypeId(this ITypeSymbol type, Context cx, TextWriter trapFile, ISymbol symbolBeingDefined, bool addBaseClass)
159+
static void BuildTypeId(this ITypeSymbol type, Context cx, TextWriter trapFile, ISymbol symbolBeingDefined, bool addBaseClass, bool constructUnderlyingTupleType)
159160
{
160161
using (cx.StackGuard)
161162
{
@@ -173,7 +174,7 @@ static void BuildTypeId(this ITypeSymbol type, Context cx, TextWriter trapFile,
173174
case TypeKind.Delegate:
174175
case TypeKind.Error:
175176
var named = (INamedTypeSymbol)type;
176-
named.BuildNamedTypeId(cx, trapFile, symbolBeingDefined, addBaseClass);
177+
named.BuildNamedTypeId(cx, trapFile, symbolBeingDefined, addBaseClass, constructUnderlyingTupleType);
177178
return;
178179
case TypeKind.Pointer:
179180
var ptr = (IPointerTypeSymbol)type;
@@ -195,7 +196,7 @@ static void BuildTypeId(this ITypeSymbol type, Context cx, TextWriter trapFile,
195196
}
196197
}
197198

198-
static void BuildOrWriteId(this ISymbol symbol, Context cx, TextWriter trapFile, ISymbol symbolBeingDefined, bool addBaseClass)
199+
static void BuildOrWriteId(this ISymbol symbol, Context cx, TextWriter trapFile, ISymbol symbolBeingDefined, bool addBaseClass, bool constructUnderlyingTupleType = false)
199200
{
200201
// We need to keep track of the symbol being defined in order to avoid cyclic labels.
201202
// For example, in
@@ -210,11 +211,13 @@ static void BuildOrWriteId(this ISymbol symbol, Context cx, TextWriter trapFile,
210211
//
211212
// ```
212213
// #123 = @"C`1 : IEnumerable<__self___T>"
213-
// ```
214+
// ```
214215
if (SymbolEqualityComparer.Default.Equals(symbol, symbolBeingDefined))
215216
trapFile.Write("__self__");
216217
else if (symbol is ITypeSymbol type && type.IdDependsOn(cx, symbolBeingDefined))
217-
type.BuildTypeId(cx, trapFile, symbolBeingDefined, addBaseClass);
218+
type.BuildTypeId(cx, trapFile, symbolBeingDefined, addBaseClass, constructUnderlyingTupleType);
219+
else if (symbol is INamedTypeSymbol namedType && namedType.IsTupleType && constructUnderlyingTupleType)
220+
trapFile.WriteSubId(NamedType.CreateNamedTypeFromTupleType(cx, namedType));
218221
else
219222
trapFile.WriteSubId(CreateEntity(cx, symbol));
220223
}
@@ -262,9 +265,9 @@ private static void BuildAssembly(IAssemblySymbol asm, TextWriter trapFile, bool
262265
trapFile.Write("::");
263266
}
264267

265-
static void BuildNamedTypeId(this INamedTypeSymbol named, Context cx, TextWriter trapFile, ISymbol symbolBeingDefined, bool addBaseClass)
268+
static void BuildNamedTypeId(this INamedTypeSymbol named, Context cx, TextWriter trapFile, ISymbol symbolBeingDefined, bool addBaseClass, bool constructUnderlyingTupleType)
266269
{
267-
if (named.IsTupleType)
270+
if (!constructUnderlyingTupleType && named.IsTupleType)
268271
{
269272
trapFile.Write('(');
270273
trapFile.BuildList(",", named.TupleElements,
@@ -308,10 +311,10 @@ void AddContaining()
308311
}
309312
else
310313
{
311-
named.ConstructedFrom.BuildOrWriteId(cx, trapFile, symbolBeingDefined, addBaseClass);
314+
named.ConstructedFrom.BuildOrWriteId(cx, trapFile, symbolBeingDefined, addBaseClass, constructUnderlyingTupleType);
312315
trapFile.Write('<');
313316
// Encode the nullability of the type arguments in the label.
314-
// Type arguments with different nullability can result in
317+
// Type arguments with different nullability can result in
315318
// a constructed type with different nullability of its members and methods,
316319
// so we need to create a distinct database entity for it.
317320
trapFile.BuildList(",", named.GetAnnotatedTypeArguments(),
@@ -360,7 +363,7 @@ static void BuildAnonymousName(this INamedTypeSymbol type, Context cx, TextWrite
360363
/// Constructs a display name string for this type symbol.
361364
/// </summary>
362365
/// <param name="trapFile">The trap builder used to store the result.</param>
363-
public static void BuildDisplayName(this ITypeSymbol type, Context cx, TextWriter trapFile)
366+
public static void BuildDisplayName(this ITypeSymbol type, Context cx, TextWriter trapFile, bool constructUnderlyingTupleType = false)
364367
{
365368
using (cx.StackGuard)
366369
{
@@ -384,7 +387,7 @@ public static void BuildDisplayName(this ITypeSymbol type, Context cx, TextWrite
384387
case TypeKind.Delegate:
385388
case TypeKind.Error:
386389
var named = (INamedTypeSymbol)type;
387-
named.BuildNamedTypeDisplayName(cx, trapFile);
390+
named.BuildNamedTypeDisplayName(cx, trapFile, constructUnderlyingTupleType);
388391
return;
389392
case TypeKind.Pointer:
390393
var ptr = (IPointerTypeSymbol)type;
@@ -403,9 +406,9 @@ public static void BuildDisplayName(this ITypeSymbol type, Context cx, TextWrite
403406
}
404407
}
405408

406-
public static void BuildNamedTypeDisplayName(this INamedTypeSymbol namedType, Context cx, TextWriter trapFile)
409+
public static void BuildNamedTypeDisplayName(this INamedTypeSymbol namedType, Context cx, TextWriter trapFile, bool constructUnderlyingTupleType)
407410
{
408-
if (namedType.IsTupleType)
411+
if (!constructUnderlyingTupleType && namedType.IsTupleType)
409412
{
410413
trapFile.Write('(');
411414
trapFile.BuildList(",", namedType.TupleElements.Select(f => f.Type),

csharp/extractor/Semmle.Extraction/Semmle.Extraction.csproj

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -15,10 +15,11 @@
1515
</PropertyGroup>
1616

1717
<ItemGroup>
18-
<PackageReference Include="Microsoft.CodeAnalysis" Version="3.4.0" />
19-
<PackageReference Include="GitInfo" Version="2.0.20"><IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
20-
<PrivateAssets>all</PrivateAssets>
21-
</PackageReference>
18+
<PackageReference Include="Microsoft.CodeAnalysis" Version="3.7.0" />
19+
<PackageReference Include="GitInfo" Version="2.0.20">
20+
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
21+
<PrivateAssets>all</PrivateAssets>
22+
</PackageReference>
2223
</ItemGroup>
2324

2425
<ItemGroup>

csharp/ql/src/semmle/code/csharp/PrintAst.qll

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,8 @@ private predicate isNotNeeded(Element e) {
4646
or
4747
e instanceof AnonymousClass
4848
or
49+
e instanceof TupleType
50+
or
4951
isNotNeeded(e.(Declaration).getDeclaringType())
5052
or
5153
isNotNeeded(e.(Parameter).getDeclaringElement())

csharp/ql/src/semmle/code/csharp/Type.qll

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -932,7 +932,7 @@ class UnknownType extends Type, @unknown_type { }
932932
*/
933933
class TupleType extends ValueType, @tuple_type {
934934
/** Gets the underlying type of this tuple, which is of type `System.ValueTuple`. */
935-
ConstructedStruct getUnderlyingType() { tuple_underlying_type(this, getTypeRef(result)) }
935+
Struct getUnderlyingType() { tuple_underlying_type(this, getTypeRef(result)) }
936936

937937
/**
938938
* Gets the `n`th element of this tuple, indexed from 0.

csharp/ql/src/semmlecode.csharp.dbscheme

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -692,7 +692,7 @@ overrides(
692692
int base_id: @callable ref);
693693

694694
explicitly_implements(
695-
unique int id: @member ref,
695+
int id: @member ref,
696696
int interface_id: @interface_or_ref ref);
697697

698698
local_functions(

0 commit comments

Comments
 (0)