Skip to content

Commit

Permalink
Merge remote-tracking branch 'upstream/master' into 295_beta1
Browse files Browse the repository at this point in the history
  • Loading branch information
mavasani committed Sep 11, 2019
2 parents d7a6b37 + 924f9f5 commit 267729b
Show file tree
Hide file tree
Showing 10 changed files with 57 additions and 18 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -350,7 +350,7 @@ Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.ValueContentAnalysis.ValueContainsN
Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.ValueContentAnalysis.ValueContainsNonLiteralState.Undefined = 1 -> Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.ValueContentAnalysis.ValueContainsNonLiteralState
Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.ValueContentAnalysis.ValueContentAbstractValue
Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.ValueContentAnalysis.ValueContentAbstractValue.IsLiteralState.get -> bool
Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.ValueContentAnalysis.ValueContentAbstractValue.TryGetSingleLiteral<T>(out T literalValue) -> bool
Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.ValueContentAnalysis.ValueContentAbstractValue.TryGetSingleNonNullLiteral<T>(out T literalValue) -> bool
Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.ValueContentAnalysis.ValueContentAbstractValue.LiteralValues.get -> System.Collections.Immutable.ImmutableHashSet<object>
Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.ValueContentAnalysis.ValueContentAbstractValue.NonLiteralState.get -> Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.ValueContentAnalysis.ValueContainsNonLiteralState
Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.ValueContentAnalysis.ValueContentAnalysis
Expand Down Expand Up @@ -631,6 +631,7 @@ static readonly Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.DisposeAnalysis.Dis
static readonly Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.DisposeAnalysis.DisposeAbstractValue.Unknown -> Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.DisposeAnalysis.DisposeAbstractValue
static Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.ValueContentAnalysis.ValueContentAbstractValue.ContainsEmptyStringLiteralState.get -> Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.ValueContentAnalysis.ValueContentAbstractValue
static Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.ValueContentAnalysis.ValueContentAbstractValue.ContainsOneIntergralLiteralState.get -> Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.ValueContentAnalysis.ValueContentAbstractValue
static Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.ValueContentAnalysis.ValueContentAbstractValue.ContainsNullLiteralState.get -> Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.ValueContentAnalysis.ValueContentAbstractValue
static Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.ValueContentAnalysis.ValueContentAbstractValue.ContainsZeroIntergralLiteralState.get -> Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.ValueContentAnalysis.ValueContentAbstractValue
static Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.ValueContentAnalysis.ValueContentAbstractValue.DoesNotContainLiteralOrNonLiteralState.get -> Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.ValueContentAnalysis.ValueContentAbstractValue
static Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.ValueContentAnalysis.ValueContentAbstractValue.InvalidState.get -> Microsoft.CodeAnalysis.FlowAnalysis.DataFlow.ValueContentAnalysis.ValueContentAbstractValue
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2640,5 +2640,37 @@ End If
End Sub
End Module");
}

[Trait(Traits.DataflowAnalysis, Traits.Dataflow.ValueContentAnalysis)]
[Fact]
public void ValueContentAnalysis_MergeForUnreachableCode()
{
var editorconfig = "dotnet_code_quality.interprocedural_analysis_kind = ContextSensitive";

VerifyCSharp(@"
using System;
public class C
{
public void Load(C c1, C c2)
{
var x = c1 ?? c2;
this.Load(null);
}
public void Load(Uri productFileUrl, Uri originalLocation = null)
{
if (productFileUrl == null)
{
throw new ArgumentNullException();
}
Uri feedLocationUri = originalLocation ?? productFileUrl;
_ = feedLocationUri.LocalPath;
}
}
", GetEditorConfigAdditionalFile(editorconfig));
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -98,13 +98,13 @@ public override void Initialize(AnalysisContext context)
{
if (constructorMethod.Parameters[0].Type.Equals(storeNameTypeSymbol))
{
kind = PropertySetCallbacks.EvaluateLiteralValues(argumentValueContentAbstractValues[0], o => o.Equals(6));
kind = PropertySetCallbacks.EvaluateLiteralValues(argumentValueContentAbstractValues[0], o => o != null && o.Equals(6));
}
else if (constructorMethod.Parameters[0].Type.SpecialType == SpecialType.System_String)
{
kind = PropertySetCallbacks.EvaluateLiteralValues(
argumentValueContentAbstractValues[0],
s => string.Equals(s.ToString(), "root", StringComparison.OrdinalIgnoreCase));
s => s != null && string.Equals(s.ToString(), "root", StringComparison.OrdinalIgnoreCase));
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -138,8 +138,8 @@ public override void Initialize(AnalysisContext context)
invocationOperation.Arguments[1].Syntax];
// Just check for simple cases with one possible literal value.
if (switchNameValueContent.TryGetSingleLiteral<string>(out var switchName) &&
switchValueValueContent.TryGetSingleLiteral<bool>(out var switchValue) &&
if (switchNameValueContent.TryGetSingleNonNullLiteral<string>(out var switchName) &&
switchValueValueContent.TryGetSingleNonNullLiteral<bool>(out var switchValue) &&
BadSwitches.TryGetValue(switchName, out var pair) &&
pair.BadValue.Equals(switchValue) &&
!IsConfiguredToSkipAnalysis(pair.Rule, operationAnalysisContext))
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,7 @@ public sealed class UseSecureCookiesASPNetCore : DiagnosticAnalyzer
"Secure",
(ValueContentAbstractValue valueContentAbstractValue) =>
{
return PropertySetCallbacks.EvaluateLiteralValues(valueContentAbstractValue, o => o.Equals(false));
return PropertySetCallbacks.EvaluateLiteralValues(valueContentAbstractValue, o => o != null && o.Equals(false));
}));

private static HazardousUsageEvaluationResult HazardousUsageCallback(IMethodSymbol methodSymbol, PropertySetAbstractValue propertySetAbstractValue)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@

namespace Microsoft.NetCore.Analyzers.Security.UnitTests
{
[Trait(Traits.DataflowAnalysis, Traits.Dataflow.PropertySetAnalysis)]
public class DoNotInstallRootCertTests : DiagnosticAnalyzerTestBase
{
[Fact]
Expand Down
2 changes: 1 addition & 1 deletion src/Utilities/Compiler/HashUtilities.cs
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,7 @@ internal static int Combine<T>(ImmutableStack<T> stack, int currentKey)

internal static int Combine<T>(ImmutableHashSet<T> set) => Combine(set, 0);
internal static int Combine<T>(ImmutableHashSet<T> set, int currentKey)
=> Combine(set.Select(element => element.GetHashCode()).Order(),
=> Combine(set.Select(element => element?.GetHashCode() ?? 0).Order(),
set.Count,
currentKey);

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -41,8 +41,6 @@ public static PropertySetAbstractValueKind FlagIfNull(PointsToAbstractValue poin
/// <param name="badLiteralValuePredicate">Predicate function to determine if a literal value is bad.</param>
/// <returns>Mapped kind.</returns>
/// <remarks>
/// Null is not handled by this. Look at the <see cref="PointsToAbstractValue"/> if you need to treat null as bad.
///
/// All literal values are bad => Flagged
/// Some but not all literal are bad => MaybeFlagged
/// All literal values are known and none are bad => Unflagged
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ public partial class ValueContentAbstractValue : CacheBasedEquatable<ValueConten
public static ValueContentAbstractValue InvalidState { get; } = new ValueContentAbstractValue(ImmutableHashSet<object>.Empty, ValueContainsNonLiteralState.Invalid);
public static ValueContentAbstractValue MayBeContainsNonLiteralState { get; } = new ValueContentAbstractValue(ImmutableHashSet<object>.Empty, ValueContainsNonLiteralState.Maybe);
public static ValueContentAbstractValue DoesNotContainLiteralOrNonLiteralState { get; } = new ValueContentAbstractValue(ImmutableHashSet<object>.Empty, ValueContainsNonLiteralState.No);
public static ValueContentAbstractValue ContainsNullLiteralState { get; } = new ValueContentAbstractValue(ImmutableHashSet.Create((object)null), ValueContainsNonLiteralState.No);
public static ValueContentAbstractValue ContainsEmptyStringLiteralState { get; } = new ValueContentAbstractValue(ImmutableHashSet.Create<object>(string.Empty), ValueContainsNonLiteralState.No);
public static ValueContentAbstractValue ContainsZeroIntergralLiteralState { get; } = new ValueContentAbstractValue(ImmutableHashSet.Create<object>(0), ValueContainsNonLiteralState.No);
public static ValueContentAbstractValue ContainsOneIntergralLiteralState { get; } = new ValueContentAbstractValue(ImmutableHashSet.Create<object>(1), ValueContainsNonLiteralState.No);
Expand All @@ -38,6 +39,8 @@ private ValueContentAbstractValue(ImmutableHashSet<object> literalValues, ValueC

internal static ValueContentAbstractValue Create(object literal, ITypeSymbol type)
{
Debug.Assert(literal != null);

switch (type.SpecialType)
{
case SpecialType.System_Byte:
Expand Down Expand Up @@ -199,13 +202,13 @@ private static ValueContainsNonLiteralState Merge(ValueContainsNonLiteralState v
public bool IsLiteralState => !LiteralValues.IsEmpty && NonLiteralState == ValueContainsNonLiteralState.No;

/// <summary>
/// For super simple cases: If this abstract value is a single literal, then get that literal value.
/// For super simple cases: If this abstract value is a single non-null literal, then get that literal value.
/// </summary>
/// <typeparam name="T">Type of the expected literal value.</typeparam>
/// <param name="literalValue">Literal value, or its default if not a single literal value.</param>
/// <returns>True if a literal value was found, false otherwise.</returns>
/// <param name="literalValue">Literal value, or its default if not a single non-null literal value.</param>
/// <returns>True if a non-null literal value was found, false otherwise.</returns>
/// <remarks>If you're looking for null, you should be looking at <see cref="PointsToAnalysis"/>.</remarks>
public bool TryGetSingleLiteral<T>(out T literalValue)
public bool TryGetSingleNonNullLiteral<T>(out T literalValue)
{
if (!IsLiteralState || LiteralValues.Count != 1)
{
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,9 @@ protected override ValueContentAbstractValue GetAbstractValue(AnalysisEntity ana
=> CurrentAnalysisData.TryGetValue(analysisEntity, out var value) ? value : ValueDomain.UnknownOrMayBeValue;

protected override ValueContentAbstractValue GetAbstractDefaultValue(ITypeSymbol type)
=> ValueContentAbstractValue.DoesNotContainLiteralOrNonLiteralState;
=> type != null ?
ValueContentAbstractValue.DoesNotContainLiteralOrNonLiteralState :
ValueContentAbstractValue.ContainsNullLiteralState;

protected override bool HasAnyAbstractValue(ValueContentAnalysisData data)
=> data.HasAnyAbstractValue;
Expand Down Expand Up @@ -158,22 +160,24 @@ public override ValueContentAbstractValue DefaultVisit(IOperation operation, obj
_ = base.DefaultVisit(operation, argument);
if (operation.Type == null)
{
return ValueContentAbstractValue.DoesNotContainLiteralOrNonLiteralState;
return ValueContentAbstractValue.ContainsNullLiteralState;
}

if (ValueContentAbstractValue.IsSupportedType(operation.Type, out ITypeSymbol valueTypeSymbol))
{
if (operation.ConstantValue.HasValue && operation.ConstantValue.Value != null)
if (operation.ConstantValue.HasValue)
{
return ValueContentAbstractValue.Create(operation.ConstantValue.Value, valueTypeSymbol);
return operation.ConstantValue.Value != null ?
ValueContentAbstractValue.Create(operation.ConstantValue.Value, valueTypeSymbol) :
ValueContentAbstractValue.ContainsNullLiteralState;
}
else
{
return (GetNullAbstractValue(operation)) switch
{
PointsToAnalysis.NullAbstractValue.Invalid => ValueContentAbstractValue.InvalidState,

PointsToAnalysis.NullAbstractValue.Null => ValueContentAbstractValue.DoesNotContainLiteralOrNonLiteralState,
PointsToAnalysis.NullAbstractValue.Null => ValueContentAbstractValue.ContainsNullLiteralState,

_ => ValueContentAbstractValue.MayBeContainsNonLiteralState,
};
Expand Down

0 comments on commit 267729b

Please sign in to comment.