Skip to content

Commit 6eca97b

Browse files
authored
Merge pull request #4113 from tamasvajk/feature/nullability-extraction-cil
Enable nullability checks on Semmle.Extraction.CIL
2 parents 647ed03 + 7e2cf9a commit 6eca97b

22 files changed

+283
-181
lines changed

csharp/extractor/Semmle.Extraction.CIL/CachedFunction.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ namespace Semmle.Extraction.CIL
99
/// </summary>
1010
/// <typeparam name="SrcType">The type of the source.</typeparam>
1111
/// <typeparam name="TargetType">The type of the generated object.</typeparam>
12-
public class CachedFunction<SrcType, TargetType>
12+
public class CachedFunction<SrcType, TargetType> where SrcType : notnull
1313
{
1414
readonly Func<SrcType, TargetType> generator;
1515
readonly Dictionary<SrcType, TargetType> cache;

csharp/extractor/Semmle.Extraction.CIL/Context.cs

Lines changed: 15 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -14,13 +14,19 @@ namespace Semmle.Extraction.CIL
1414
/// </summary>
1515
partial class Context : IDisposable
1616
{
17-
public Extraction.Context cx;
1817
readonly FileStream stream;
19-
public readonly MetadataReader mdReader;
20-
public readonly PEReader peReader;
21-
public readonly string assemblyPath;
22-
public Entities.Assembly assembly;
23-
public PDB.IPdb pdb;
18+
Entities.Assembly? assemblyNull;
19+
20+
public Extraction.Context cx { get; }
21+
public MetadataReader mdReader { get; }
22+
public PEReader peReader { get; }
23+
public string assemblyPath { get; }
24+
public Entities.Assembly assembly
25+
{
26+
get { return assemblyNull!; }
27+
set { assemblyNull = value; }
28+
}
29+
public PDB.IPdb? pdb { get; }
2430

2531
public Context(Extraction.Context cx, string assemblyPath, bool extractPdbs)
2632
{
@@ -105,7 +111,7 @@ public Entities.Type ErrorType
105111
/// </summary>
106112
/// <param name="handle">The handle of the method.</param>
107113
/// <returns>The debugging information, or null if the information could not be located.</returns>
108-
public PDB.IMethod GetMethodDebugInformation(MethodDefinitionHandle handle)
114+
public PDB.IMethod? GetMethodDebugInformation(MethodDefinitionHandle handle)
109115
{
110116
return pdb == null ? null : pdb.GetMethod(handle.ToDebugInformationHandle());
111117
}
@@ -125,7 +131,8 @@ public GenericContext(Context cx)
125131
}
126132

127133
/// <summary>
128-
/// The list of generic type parameters.
134+
/// The list of generic type parameters, including type parameters of
135+
/// containing types.
129136
/// </summary>
130137
public abstract IEnumerable<Entities.Type> TypeParameters { get; }
131138

csharp/extractor/Semmle.Extraction.CIL/Entities/Assembly.cs

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -47,9 +47,9 @@ public override void WriteId(TextWriter trapFile)
4747
trapFile.Write(cx.assemblyPath.Replace("\\", "/"));
4848
}
4949

50-
public override bool Equals(object obj)
50+
public override bool Equals(object? obj)
5151
{
52-
return GetType() == obj.GetType() && Equals(file, ((Assembly)obj).file);
52+
return GetType() == obj?.GetType() && Equals(file, ((Assembly)obj).file);
5353
}
5454

5555
public override int GetHashCode() => 7 * file.GetHashCode();
@@ -63,7 +63,7 @@ public override IEnumerable<IExtractionProduct> Contents
6363
get
6464
{
6565
yield return file;
66-
yield return Tuples.assemblies(this, file, FullName, assemblyName.Name, assemblyName.Version.ToString());
66+
yield return Tuples.assemblies(this, file, FullName, assemblyName.Name ?? string.Empty, assemblyName.Version?.ToString() ?? string.Empty);
6767

6868
if (cx.pdb != null)
6969
{
@@ -75,7 +75,7 @@ public override IEnumerable<IExtractionProduct> Contents
7575

7676
foreach (var handle in cx.mdReader.TypeDefinitions)
7777
{
78-
IExtractionProduct product = null;
78+
IExtractionProduct? product = null;
7979
try
8080
{
8181
product = cx.Create(handle);
@@ -92,7 +92,7 @@ public override IEnumerable<IExtractionProduct> Contents
9292

9393
foreach (var handle in cx.mdReader.MethodDefinitions)
9494
{
95-
IExtractionProduct product = null;
95+
IExtractionProduct? product = null;
9696
try
9797
{
9898
product = cx.Create(handle);

csharp/extractor/Semmle.Extraction.CIL/Entities/Attribute.cs

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,7 @@ public Attribute(Context cx, IEntity @object, CustomAttributeHandle handle) : ba
2727
this.@object = @object;
2828
}
2929

30-
public override bool Equals(object obj)
30+
public override bool Equals(object? obj)
3131
{
3232
return obj is Attribute attribute && handle.Equals(attribute.handle);
3333
}
@@ -58,13 +58,15 @@ public override IEnumerable<IExtractionProduct> Contents
5858
for (int index = 0; index < decoded.FixedArguments.Length; ++index)
5959
{
6060
object value = decoded.FixedArguments[index].Value;
61-
yield return Tuples.cil_attribute_positional_argument(this, index, value == null ? "null" : value.ToString());
61+
var stringValue = value?.ToString();
62+
yield return Tuples.cil_attribute_positional_argument(this, index, stringValue ?? "null");
6263
}
6364

6465
foreach (var p in decoded.NamedArguments)
6566
{
6667
object value = p.Value;
67-
yield return Tuples.cil_attribute_named_argument(this, p.Name, value == null ? "null" : value.ToString());
68+
var stringValue = value?.ToString();
69+
yield return Tuples.cil_attribute_named_argument(this, p.Name, stringValue ?? "null");
6870
}
6971
}
7072
}

csharp/extractor/Semmle.Extraction.CIL/Entities/Event.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,7 @@ public override void WriteId(TextWriter trapFile)
3636

3737
public override string IdSuffix => ";cil-event";
3838

39-
public override bool Equals(object obj)
39+
public override bool Equals(object? obj)
4040
{
4141
return obj is Event e && handle.Equals(e.handle);
4242
}

csharp/extractor/Semmle.Extraction.CIL/Entities/ExceptionRegion.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,7 @@ public override IEnumerable<IExtractionProduct> Contents
3030
{
3131
get
3232
{
33-
IInstruction try_start, try_end, handler_start;
33+
IInstruction? try_start, try_end, handler_start;
3434

3535
if (!jump_table.TryGetValue(r.TryOffset, out try_start))
3636
throw new InternalError("Failed to retrieve handler");
@@ -44,7 +44,7 @@ public override IEnumerable<IExtractionProduct> Contents
4444

4545
if (r.FilterOffset != -1)
4646
{
47-
IInstruction filter_start;
47+
IInstruction? filter_start;
4848
if (!jump_table.TryGetValue(r.FilterOffset, out filter_start))
4949
throw new InternalError("ExceptionRegion filter clause");
5050

csharp/extractor/Semmle.Extraction.CIL/Entities/Field.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -91,7 +91,7 @@ public DefinitionField(GenericContext gc, FieldDefinitionHandle handle) : base(g
9191
fd = cx.mdReader.GetFieldDefinition(handle);
9292
}
9393

94-
public override bool Equals(object obj)
94+
public override bool Equals(object? obj)
9595
{
9696
return obj is DefinitionField field && handle.Equals(field.handle);
9797
}
@@ -153,7 +153,7 @@ public MemberReferenceField(GenericContext gc, MemberReferenceHandle handle) : b
153153
declType = (Type)cx.CreateGeneric(gc, mr.Parent);
154154
}
155155

156-
public override bool Equals(object obj)
156+
public override bool Equals(object? obj)
157157
{
158158
return obj is MemberReferenceField field && Handle.Equals(field.Handle);
159159
}

csharp/extractor/Semmle.Extraction.CIL/Entities/File.cs

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -25,9 +25,9 @@ public override void WriteId(TextWriter trapFile)
2525
trapFile.Write(Semmle.Extraction.Entities.File.PathAsDatabaseId(path));
2626
}
2727

28-
public override bool Equals(object obj)
28+
public override bool Equals(object? obj)
2929
{
30-
return GetType() == obj.GetType() && path == ((File)obj).path;
30+
return GetType() == obj?.GetType() && path == ((File)obj).path;
3131
}
3232

3333
public override int GetHashCode() => 11 * path.GetHashCode();
@@ -36,7 +36,11 @@ public override IEnumerable<IExtractionProduct> Contents
3636
{
3737
get
3838
{
39-
var parent = cx.CreateFolder(System.IO.Path.GetDirectoryName(path));
39+
var directoryName = System.IO.Path.GetDirectoryName(path);
40+
if (directoryName is null)
41+
throw new InternalError($"Directory name for path '{path}' is null.");
42+
43+
var parent = cx.CreateFolder(directoryName);
4044
yield return parent;
4145
yield return Tuples.containerparent(parent, this);
4246
yield return Tuples.files(this, path, System.IO.Path.GetFileNameWithoutExtension(path), System.IO.Path.GetExtension(path).Substring(1));

csharp/extractor/Semmle.Extraction.CIL/Entities/Folder.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,7 @@ public override IEnumerable<IExtractionProduct> Contents
4141
}
4242
}
4343

44-
public override bool Equals(object obj)
44+
public override bool Equals(object? obj)
4545
{
4646
return obj is Folder folder && path == folder.path;
4747
}

csharp/extractor/Semmle.Extraction.CIL/Entities/Instruction.cs

Lines changed: 14 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -365,6 +365,11 @@ public override IEnumerable<IExtractionProduct> Contents
365365
{
366366
int offset = Offset;
367367

368+
if (Method.Implementation is null)
369+
{
370+
yield break;
371+
}
372+
368373
yield return Tuples.cil_instruction(this, (int)OpCode, Index, Method.Implementation);
369374

370375
switch (PayloadType)
@@ -414,11 +419,17 @@ public override IEnumerable<IExtractionProduct> Contents
414419
break;
415420
case Payload.Arg8:
416421
case Payload.Arg16:
417-
yield return Tuples.cil_access(this, Method.Parameters[(int)UnsignedPayloadValue]);
422+
if (Method.Parameters is object)
423+
{
424+
yield return Tuples.cil_access(this, Method.Parameters[(int)UnsignedPayloadValue]);
425+
}
418426
break;
419427
case Payload.Local8:
420428
case Payload.Local16:
421-
yield return Tuples.cil_access(this, Method.LocalVariables[(int)UnsignedPayloadValue]);
429+
if (Method.LocalVariables is object)
430+
{
431+
yield return Tuples.cil_access(this, Method.LocalVariables[(int)UnsignedPayloadValue]);
432+
}
422433
break;
423434
case Payload.None:
424435
case Payload.Target8:
@@ -439,7 +450,7 @@ public override IEnumerable<IExtractionProduct> Contents
439450
public IEnumerable<IExtractionProduct> JumpContents(Dictionary<int, IInstruction> jump_table)
440451
{
441452
int target;
442-
IInstruction inst;
453+
IInstruction? inst;
443454

444455
switch (PayloadType)
445456
{

0 commit comments

Comments
 (0)