Example #1
0
        private IndexerInfo GetIndexerInfo(SyntaxNodeAnalysisContext syntaxNodeAnalysisContext, TIndexerExpressionSyntax indexerExpressionSyntax)
        {
            var info              = GetIndexerSymbol(syntaxNodeAnalysisContext, indexerExpressionSyntax);
            var symbol            = info as IMethodSymbol;
            var verifyIndexerCast = symbol == null || symbol.Name != MetadataNames.CallInfoArgTypesMethod;
            var verifyAssignment  = symbol == null;

            var indexerInfo = new IndexerInfo(verifyIndexerCast, verifyAssignment);

            return(indexerInfo);
        }
Example #2
0
        /// <summary>
        /// Resolves an indexer to a numeric value
        /// </summary>
        /// <param name="indexer">The indexer</param>
        /// <returns>The resolved value</returns>
        private int ResolverIndexerValue
        (
            IndexerInfo indexer
        )
        {
            switch (indexer.IndexerValueType)
            {
            case NettleValueType.Number:
            {
                return(indexer.ResolvedIndex);
            }

            case NettleValueType.Variable:
            {
                var value = ResolveVariableValue
                            (
                    indexer.IndexerSignature
                            );

                if (value == null)
                {
                    throw new NullReferenceException
                          (
                              "The indexer must resolve to a numeric value."
                          );
                }

                if (value.GetType().IsNumeric())
                {
                    return(Convert.ToInt32(value));
                }
                else
                {
                    throw new InvalidCastException
                          (
                              "{0} is not a valid indexer type.".With
                              (
                                  value.GetType().Name
                              )
                          );
                }
            }

            default:
            {
                return(-1);
            }
            }
        }
Example #3
0
        private bool AnalyzeAssignment(SyntaxNodeAnalysisContext syntaxNodeContext, IList <IParameterSymbol> substituteCallParameters, TIndexerExpressionSyntax indexer, IndexerInfo indexerInfo, int?position)
        {
            var assignmentExpressionSyntax = GetAssignmentExpression(indexer);

            if (indexerInfo.VerifyAssignment && assignmentExpressionSyntax != null && position.HasValue && position.Value < substituteCallParameters.Count)
            {
                var parameterSymbol = substituteCallParameters[position.Value];
                if (parameterSymbol.RefKind != RefKind.Out && parameterSymbol.RefKind != RefKind.Ref)
                {
                    var diagnostic = Diagnostic.Create(
                        DiagnosticDescriptorsProvider.CallInfoArgumentIsNotOutOrRef,
                        indexer.GetLocation(),
                        position.Value,
                        parameterSymbol.Type);
                    syntaxNodeContext.ReportDiagnostic(diagnostic);
                    return(true);
                }

                var typeInfo = syntaxNodeContext.SemanticModel.GetTypeInfo(assignmentExpressionSyntax);
                if (typeInfo.Type != null && IsAssignableTo(syntaxNodeContext.Compilation, typeInfo.Type, substituteCallParameters[position.Value].Type) == false)
                {
                    var diagnostic = Diagnostic.Create(
                        DiagnosticDescriptorsProvider.CallInfoArgumentSetWithIncompatibleValue,
                        indexer.GetLocation(),
                        typeInfo.Type,
                        position.Value,
                        substituteCallParameters[position.Value].Type);
                    syntaxNodeContext.ReportDiagnostic(diagnostic);
                    return(true);
                }
            }

            return(false);
        }
Example #4
0
        private bool AnalyzeCast(SyntaxNodeAnalysisContext syntaxNodeContext, IList <IParameterSymbol> substituteCallParameters, TIndexerExpressionSyntax indexer, IndexerInfo indexerInfo, int?position)
        {
            var castTypeExpression = GetCastTypeExpression(indexer);

            if (position.HasValue && indexerInfo.VerifyIndexerCast && castTypeExpression != null)
            {
                var typeInfo = syntaxNodeContext.SemanticModel.GetTypeInfo(castTypeExpression);
                if (typeInfo.Type != null && CanCast(syntaxNodeContext.Compilation, substituteCallParameters[position.Value].Type, typeInfo.Type) == false)
                {
                    var diagnostic = Diagnostic.Create(
                        DiagnosticDescriptorsProvider.CallInfoCouldNotConvertParameterAtPosition,
                        indexer.GetLocation(),
                        position.Value,
                        typeInfo.Type);
                    syntaxNodeContext.ReportDiagnostic(diagnostic);
                    return(true);
                }
            }

            return(false);
        }
Example #5
0
        /// <summary>
        /// Resolves an indexed binding value
        /// </summary>
        /// <param name="bindingPath">The binding path</param>
        /// <param name="collection">The collection</param>
        /// <param name="indexer">The indexer information</param>
        /// <returns>The value found at the specified index</returns>
        private object ResolveIndexedBinding
        (
            string bindingPath,
            object collection,
            IndexerInfo indexer
        )
        {
            if (collection == null)
            {
                throw new InvalidOperationException
                      (
                          "The value for '{0}' is null.".With
                          (
                              bindingPath
                          )
                      );
            }

            if (false == collection.GetType().IsEnumerable())
            {
                throw new InvalidOperationException
                      (
                          "'{0}' is not a valid collection.".With
                          (
                              bindingPath
                          )
                      );
            }

            var index = ResolverIndexerValue(indexer);

            if (index < 0)
            {
                throw new ArgumentOutOfRangeException
                      (
                          "The index for '{0}' must be zero or greater.".With
                          (
                              bindingPath
                          )
                      );
            }

            var counter = default(int);

            foreach (var item in collection as IEnumerable)
            {
                if (counter == index)
                {
                    if (indexer.NextIndexer != null)
                    {
                        return(ResolveIndexedBinding
                               (
                                   indexer.FullPath,
                                   item,
                                   indexer.NextIndexer
                               ));
                    }
                    else
                    {
                        return(item);
                    }
                }

                counter++;
            }

            throw new IndexOutOfRangeException
                  (
                      "The index {0} for '{1}' is out of range.".With
                      (
                          index,
                          bindingPath
                      )
                  );
        }