예제 #1
0
        internal IMethodContract Map(IMethodContract methodContract)
        {
            var result   = new CodeAndContractDeepCopier(host).Copy(methodContract);
            var rewriter = new ActualMutator(host, targetUnit, sourceUnitIdentity);

            return(rewriter.Rewrite(result));
        }
예제 #2
0
        void WriteExceptions(XElement member, IMethodContract methodContract)
        {
            Contract.Requires(member != null);
            Contract.Requires(methodContract != null);
            Contract.Assume(methodContract.Preconditions != null, "lack of CCI2 contracts");

            foreach (IPrecondition pre in methodContract.Preconditions)
            {
                if (pre.ExceptionToThrow != null)
                {
                    Contract.Assume(pre.ExceptionToThrow.Type != null, "lack of CCI2 contracts");

                    string conditionText = "";
                    if (pre.OriginalSource != null)
                    {
                        conditionText = String.Format("If \"{0}\".", DocHelper.NegatePredicate(pre.OriginalSource));
                    }
                    WriteException(member, pre.ExceptionToThrow.Type, conditionText);
                }
            }

            foreach (IThrownException exc in methodContract.ThrownExceptions)
            {
                Contract.Assume(exc.ExceptionType != null, "lack of CCI2 contracts");

                string conditionText = "";
                if (exc.Postcondition.OriginalSource != null)
                {
                    conditionText = String.Format("\"{0}\" will be true.", exc.Postcondition.OriginalSource);
                }
                WriteException(member, exc.ExceptionType, conditionText);
            }
        }
        /// <summary>
        /// Updates this's visual based on new contract information.
        /// </summary>
        public void SetContracts(IMethodContract getterContract, IMethodContract setterContract, string toolTip)
        {
            #region Disable if contracts are null or dummy
            if ((getterContract == null && setterContract == null) || (getterContract == ContractDummy.MethodContract && setterContract == ContractDummy.MethodContract))
            {
                Visibility = Visibility.Collapsed;
                return;
            }
            #endregion
            #region Set tooltip
            if (!string.IsNullOrEmpty(toolTip))
            {
                ToolTipContent = toolTip;
            }
            #endregion
            ClearContracts();
            //IsPure = true; //Properties should always be pure.
            IsPure = (getterContract != null && getterContract.IsPure) || (setterContract != null && setterContract.IsPure);
            _hasNonPurityContracts = getterContract.Preconditions.Count() > 0 || getterContract.Postconditions.Count() > 0 || getterContract.ThrownExceptions.Count() > 0 ||
                                     setterContract.Preconditions.Count() > 0 || setterContract.Postconditions.Count() > 0 || setterContract.ThrownExceptions.Count() > 0;
            StartFormatContracts();
            FormatContracts(getterContract, setterContract);
            EndFormatContracts();
            if (ShouldBeVisible)
            {
                Visibility = Visibility.Visible;
            }
            else
            {
                Visibility = Visibility.Collapsed;
            }

            ShouldRefreshLineTransformer = true;
        }
예제 #4
0
        public bool TryGetPropertyContract(CSharpMember semanticMember, out IMethodContract getterContract, out IMethodContract setterContract)
        {
            Contract.Requires(semanticMember == null || semanticMember.IsProperty || semanticMember.IsIndexer);

            getterContract = null;
            setterContract = null;

            #region Check input
            if (semanticMember == null)
            {
                return(false);
            }
            #endregion
            IMethodReference getter, setter;
            if (!TryGetPropertyAccessorReferences(semanticMember, out getter, out setter))
            {
                return(false);
            }

            var success = false;
            if (getter != null)
            {
                success |= TryGetMethodContract(getter, out getterContract);
            }
            if (setter != null)
            {
                success |= TryGetMethodContract(setter, out setterContract);
            }
            return(success);
        }
        /// <summary>
        /// Updates this's visual based on new contract information.
        /// </summary>
        public void SetContracts(IMethodContract contracts, string toolTip)
        {
            #region Disable if contracts are null or dummy
            if (contracts == null || contracts == ContractDummy.MethodContract)
            {
                Visibility = Visibility.Collapsed;
                return;
            }
            #endregion
            #region Set tooltip
            if (!string.IsNullOrEmpty(toolTip))
            {
                ToolTipContent = toolTip;
            }
            #endregion
            ClearContracts();
            IsPure = contracts.IsPure;
            _hasNonPurityContracts = contracts.Preconditions.Count() > 0 || contracts.Postconditions.Count() > 0 || contracts.ThrownExceptions.Count() > 0;
            StartFormatContracts();
            FormatContracts(contracts);
            EndFormatContracts();
            if (ShouldBeVisible)
            {
                Visibility = Visibility.Visible;
            }
            else
            {
                Visibility = Visibility.Collapsed;
            }

            ShouldRefreshLineTransformer = true;
        }
예제 #6
0
 private void PrintMethodContract(IMethodContract /*?*/ methodContract)
 {
     if (methodContract == null)
     {
         this.Indent();
         Console.WriteLine("no contract");
         return;
     }
     this.Indent();
     Console.WriteLine(methodContract.IsPure ? "pure" : "not pure");
     if (IteratorHelper.EnumerableIsEmpty(methodContract.Preconditions) && IteratorHelper.EnumerableIsEmpty(methodContract.Postconditions) &&
         IteratorHelper.EnumerableIsEmpty(methodContract.ThrownExceptions))
     {
         return;
     }
     foreach (var p in methodContract.Preconditions)
     {
         this.Indent();
         Console.Write("requires ");
         if (!String.IsNullOrEmpty(p.OriginalSource))
         {
             Console.Write(p.OriginalSource);
         }
         else
         {
             Console.Write(PrintExpression(p.Condition));
         }
         Console.WriteLine();
     }
     foreach (var p in methodContract.Postconditions)
     {
         Indent();
         Console.Write("ensures ");
         if (!String.IsNullOrEmpty(p.OriginalSource))
         {
             Console.Write(p.OriginalSource);
         }
         else
         {
             Console.Write(PrintExpression(p.Condition));
         }
         Console.WriteLine();
     }
     foreach (var p in methodContract.ThrownExceptions)
     {
         Indent();
         Console.Write("throws ");
         Console.Write(TypeHelper.GetTypeName(p.ExceptionType, NameFormattingOptions.OmitContainingNamespace));
         Console.Write(" when ");
         if (!String.IsNullOrEmpty(p.Postcondition.OriginalSource))
         {
             Console.Write(p.Postcondition.OriginalSource);
         }
         else
         {
             Console.Write(PrintExpression(p.Postcondition.Condition));
         }
         Console.WriteLine();
     }
 }
예제 #7
0
        public CciAction(IMethodDefinition method, IMethodContract contract)
        {
            System.Diagnostics.Contracts.Contract.Requires(method != null);

            this.method   = method;
            this.contract = contract;
        }
예제 #8
0
 /// <summary>
 /// Accumulates all elements from <paramref name="sourceContract"/> into <paramref name="targetContract"/>
 /// </summary>
 /// <param name="targetContract">Contract which is target of accumulator</param>
 /// <param name="sourceContract">Contract which is source of accumulator</param>
 public static void AddMethodContract(MethodContract targetContract, IMethodContract sourceContract) {
   targetContract.Locations.AddRange(sourceContract.Locations);
   targetContract.Preconditions.AddRange(sourceContract.Preconditions);
   targetContract.Postconditions.AddRange(sourceContract.Postconditions);
   targetContract.ThrownExceptions.AddRange(sourceContract.ThrownExceptions);
   targetContract.IsPure |= sourceContract.IsPure; // need the disjunction
   return;
 }
예제 #9
0
 /// <summary>
 ///     Traverses the method contract.
 /// </summary>
 public void Traverse(IMethodContract methodContract)
 {
     Contract.Requires(methodContract != null);
     preorderVisitor.Visit(methodContract);
     if (StopTraversal)
     {
         return;
     }
     TraverseChildren(methodContract);
 }
예제 #10
0
        private static bool IsEmptyContract(IMethodContract methodContracts)
        {
            Contract.Ensures(Contract.Result <bool>() || methodContracts != null);

            return(methodContracts == null ||
                   (methodContracts == ContractDummy.MethodContract) ||
                   (!methodContracts.IsPure &&
                    methodContracts.Preconditions.Count() < 1 &&
                    methodContracts.Postconditions.Count() < 1 &&
                    methodContracts.ThrownExceptions.Count() < 1));
        }
    public IEnumerable<Bpl.Requires> getPreconditionTranslation(IMethodContract contract) {
      ICollection<Bpl.Requires> translatedPres = new List<Bpl.Requires>();
      foreach (IPrecondition pre in contract.Preconditions) {
        var stmtTraverser = this.Factory.MakeStatementTraverser(sink, null, true);
        ExpressionTraverser exptravers = this.Factory.MakeExpressionTraverser(sink, stmtTraverser, true);
        exptravers.Traverse(pre.Condition); // TODO
        // Todo: Deal with Descriptions
        var req = new Bpl.Requires(pre.Token(), false, exptravers.TranslatedExpressions.Pop(), "");
        translatedPres.Add(req);
      }

      return translatedPres;
    }
 /// <summary>
 /// Formats this's contracts grid based on the given contract information.
 /// </summary>
 protected virtual void FormatContracts(IMethodContract getterContract, IMethodContract setterContract)
 {
     if (getterContract != null && getterContract != ContractDummy.MethodContract)
     {
         //FormatContract("Getter Contracts:", " ");
         FormatContracts(getterContract, "get ");
     }
     if (setterContract != null && setterContract != ContractDummy.MethodContract)
     {
         //FormatContract("Setter Contracts:", " ");
         FormatContracts(setterContract, "set ");
     }
 }
    public IEnumerable<Bpl.Ensures> getPostconditionTranslation(IMethodContract contract) {
      ICollection<Bpl.Ensures> translatedPosts = new List<Bpl.Ensures>();
      foreach (IPostcondition post in contract.Postconditions) {
        var stmtTraverser = this.Factory.MakeStatementTraverser(sink, null, true);
        ExpressionTraverser exptravers = this.Factory.MakeExpressionTraverser(sink, stmtTraverser, true);
        exptravers.Traverse(post.Condition);
        // Todo: Deal with Descriptions
        var ens = new Bpl.Ensures(post.Token(), false, exptravers.TranslatedExpressions.Pop(), "");
        translatedPosts.Add(ens);
      }

      return translatedPosts;
    }
    public IEnumerable<Bpl.IdentifierExpr> getModifiedIdentifiers(IMethodContract contract) {
      ICollection<Bpl.IdentifierExpr> modifiedExpr = new List<Bpl.IdentifierExpr>();
      foreach (IAddressableExpression mod in contract.ModifiedVariables) {
        ExpressionTraverser exptravers = this.Factory.MakeExpressionTraverser(sink, null, true);
        exptravers.Traverse(mod);
        Bpl.IdentifierExpr idexp = exptravers.TranslatedExpressions.Pop() as Bpl.IdentifierExpr;
        if (idexp == null) {
          throw new TranslationException(String.Format("Cannot create IdentifierExpr for Modifyed Variable {0}", mod.ToString()));
        }
        modifiedExpr.Add(idexp);
      }

      return modifiedExpr;
    }
예제 #15
0
        public bool TryGetMethodContractSafe(CSharpMember semanticMehod, out IMethodContract methodContract)
        {
            Contract.Requires(semanticMehod == null || semanticMehod.IsMethod || semanticMehod.IsConstructor);
            Contract.Ensures(!Contract.Result <bool>() || (Contract.ValueAtReturn(out methodContract) != null));

            methodContract = null;

            #region Check input
            if (semanticMehod == null)
            {
                return(false);
            }
            #endregion
            #region Call TryGetMethodContract cautiously
            try {
                //Can we get contracts?
                if (!TryGetMethodContract(semanticMehod, out methodContract))
                {
                    return(false);
                }
            }
            #endregion
            #region Abort on exception
            //Give up on our contracts if we get an exception
            catch (IllFormedSemanticModelException) {
                return(false);
            } catch (InvalidOperationException e) {
                if (!e.Message.Contains(ContractsPackageAccessor.InvalidOperationExceptionMessage_TheSnapshotIsOutOfDate))
                {
                    throw e;
                }
                else
                {
                    return(false);
                }
            } catch (System.Runtime.InteropServices.COMException e) {
                if (!e.Message.Contains(ContractsPackageAccessor.COMExceptionMessage_BindingFailed))
                {
                    throw e;
                }
                else
                {
                    return(false);
                }
            }
            #endregion

            return(methodContract != null);
        }
예제 #16
0
 /// <summary>
 ///
 /// </summary>
 /// <param name="methodContract"></param>
 public MethodContract(IMethodContract methodContract)
 {
     this.allocates         = new List <IExpression>(methodContract.Allocates);
     this.frees             = new List <IExpression>(methodContract.Frees);
     this.locations         = new List <ILocation>(methodContract.Locations);
     this.modifiedVariables = new List <IAddressableExpression>(methodContract.ModifiedVariables);
     this.mustInline        = methodContract.MustInline;
     this.postconditions    = new List <IPostcondition>(methodContract.Postconditions);
     this.preconditions     = new List <IPrecondition>(methodContract.Preconditions);
     this.reads             = new List <IExpression>(methodContract.Reads);
     this.thrownExceptions  = new List <IThrownException>(methodContract.ThrownExceptions);
     this.variants          = new List <IExpression>(methodContract.Variants);
     this.writes            = new List <IExpression>(methodContract.Writes);
     this.isPure            = methodContract.IsPure;
 }
예제 #17
0
        public IEnumerable <Bpl.Requires> getPreconditionTranslation(IMethodContract contract)
        {
            ICollection <Bpl.Requires> translatedPres = new List <Bpl.Requires>();

            foreach (IPrecondition pre in contract.Preconditions)
            {
                var stmtTraverser = this.Factory.MakeStatementTraverser(sink, null, true);
                ExpressionTraverser exptravers = this.Factory.MakeExpressionTraverser(sink, stmtTraverser, true);
                exptravers.Traverse(pre.Condition); // TODO
                // Todo: Deal with Descriptions
                var req = new Bpl.Requires(pre.Token(), false, exptravers.TranslatedExpressions.Pop(), "");
                translatedPres.Add(req);
            }

            return(translatedPres);
        }
 /// <summary>
 /// Formats this's contracts grid based on the given contract information.
 /// </summary>
 protected virtual void FormatContracts(IMethodContract contracts, string headerPrefix = "")
 {
     Contract.Requires(contracts != null);
     foreach (var pre in contracts.Preconditions)
     {
         FormatContract(headerPrefix + "requires", pre.OriginalSource);
     }
     foreach (var post in contracts.Postconditions)
     {
         FormatContract(headerPrefix + "ensures", post.OriginalSource);
     }
     foreach (var thrown in contracts.ThrownExceptions)
     {
         FormatContract(headerPrefix + "ensures on throw", "of " + TypeHelper.GetTypeName(thrown.ExceptionType, NameFormattingOptions.OmitContainingType | NameFormattingOptions.OmitContainingNamespace) + " that " + thrown.Postcondition.OriginalSource);
     }
 }
예제 #19
0
        public IEnumerable <Bpl.Ensures> getPostconditionTranslation(IMethodContract contract)
        {
            ICollection <Bpl.Ensures> translatedPosts = new List <Bpl.Ensures>();

            foreach (IPostcondition post in contract.Postconditions)
            {
                var stmtTraverser = this.Factory.MakeStatementTraverser(sink, null, true);
                ExpressionTraverser exptravers = this.Factory.MakeExpressionTraverser(sink, stmtTraverser, true);
                exptravers.Traverse(post.Condition);
                // Todo: Deal with Descriptions
                var ens = new Bpl.Ensures(post.Token(), false, exptravers.TranslatedExpressions.Pop(), "");
                translatedPosts.Add(ens);
            }

            return(translatedPosts);
        }
            void PackageMethodContracts(IMethodContract methodContract, string methodId, string typeName)
            {
                Contract.Requires(methodContract != null);

                if (IteratorHelper.EnumerableIsNotEmpty <IPrecondition>(methodContract.Preconditions))
                {
                    PackagePreconditions(methodContract.Preconditions, methodId, typeName);
                }
                if (IteratorHelper.EnumerableIsNotEmpty <IPostcondition>(methodContract.Postconditions))
                {
                    PackagePostconditions(methodContract.Postconditions, methodId, typeName);
                }
                if (IteratorHelper.EnumerableIsNotEmpty <IThrownException>(methodContract.ThrownExceptions))
                {
                    PackageThrownExceptions(methodContract.ThrownExceptions, methodId, typeName);
                }
            }
예제 #21
0
        public IEnumerable <Bpl.IdentifierExpr> getModifiedIdentifiers(IMethodContract contract)
        {
            ICollection <Bpl.IdentifierExpr> modifiedExpr = new List <Bpl.IdentifierExpr>();

            foreach (IAddressableExpression mod in contract.ModifiedVariables)
            {
                ExpressionTraverser exptravers = this.Factory.MakeExpressionTraverser(sink, null, true);
                exptravers.Traverse(mod);
                Bpl.IdentifierExpr idexp = exptravers.TranslatedExpressions.Pop() as Bpl.IdentifierExpr;
                if (idexp == null)
                {
                    throw new TranslationException(String.Format("Cannot create IdentifierExpr for Modifyed Variable {0}", mod.ToString()));
                }
                modifiedExpr.Add(idexp);
            }

            return(modifiedExpr);
        }
예제 #22
0
        public static string FormatContracts(IMethodContract methodContracts)
        {
            //Did we get proper contracts?
            if (methodContracts == null)
            {
                //Return a message saying we failed to get contracts
                return("(Failed to properly get contracts)");
            }

            //Do we have any contracts?
            if (IsEmptyContract(methodContracts))
            {
                //Return a message saying we don't have any contracts
                return(null);
            }

            //Initialize our string builder
            var sb = new StringBuilder();

            //Append the 'Contracts' header
            sb.Append("Contracts: ");
            sb.Append('\n');

            //Append purity
            if (methodContracts.IsPure)
            {
                sb.Append("    ");
                sb.Append("[Pure]");
                sb.Append('\n');
            }

            FormatPrePostThrows(methodContracts, sb);

            //Can we get our result from the string builder?
            var result = sb.ToString();

            //Trim the new lines from the end
            result = result.TrimEnd('\n');

            result = SmartFormat(result);

            //Return our result
            return(result);
        }
예제 #23
0
        public bool TryGetMethodContract(IMethodReference method, out IMethodContract methodContract)
        {
            Contract.Ensures(!Contract.Result <bool>() || (Contract.ValueAtReturn(out methodContract) != null));

            methodContract = null;

            #region Check input
            if (method == null)
            {
                return(false);
            }
            #endregion
            try {
                // Resolving the method works *only* if the unit it is defined in has already been loaded.
                // That should have happened as part of creating the IMethodReference.
                var resolvedMethod = method.ResolvedMethod;
                if (resolvedMethod != Dummy.Method)
                {
                    methodContract = ContractHelper.GetMethodContractForIncludingInheritedContracts(Host, resolvedMethod);
                    if (methodContract == null)
                    {
                        methodContract = ContractDummy.MethodContract;
                        ContractsPackageAccessor.Current.Logger.WriteToLog(String.Format("Did not find any method contract(s) for '{0}'", method.Name));
                    }
                    else
                    {
                        ContractsPackageAccessor.Current.Logger.WriteToLog(
                            String.Format("Got method contract(s) for '{0}': {1} preconditions, {2} postconditions",
                                          method.Name,
                                          Microsoft.Cci.IteratorHelper.EnumerableCount(methodContract.Preconditions),
                                          Microsoft.Cci.IteratorHelper.EnumerableCount(methodContract.Postconditions)));
                    }
                }
                else
                {
                    ContractsPackageAccessor.Current.Logger.WriteToLog(String.Format("Method '{0}' resolved to dummy", method.Name));
                }
            } catch (NullReferenceException) {
                methodContract = null;
                ContractsPackageAccessor.Current.Logger.WriteToLog(String.Format("NullReferenceException thrown when getting contracts for '{0}'", method.Name));
            }
            return(methodContract != null);
        }
예제 #24
0
 /// <summary>
 ///     Traverses the children of the method contract.
 /// </summary>
 public virtual void TraverseChildren(IMethodContract methodContract)
 {
     Contract.Requires(methodContract != null);
     Traverse(methodContract.Allocates);
     if (StopTraversal)
     {
         return;
     }
     Traverse(methodContract.Frees);
     if (StopTraversal)
     {
         return;
     }
     Traverse(methodContract.ModifiedVariables);
     if (StopTraversal)
     {
         return;
     }
     Traverse(methodContract.Postconditions);
     if (StopTraversal)
     {
         return;
     }
     Traverse(methodContract.Preconditions);
     if (StopTraversal)
     {
         return;
     }
     Traverse(methodContract.Reads);
     if (StopTraversal)
     {
         return;
     }
     Traverse(methodContract.ThrownExceptions);
     if (StopTraversal)
     {
         return;
     }
     Traverse(methodContract.Writes);
 }
예제 #25
0
        public bool TryGetMethodContract(CSharpMember semanticMethod, out IMethodContract methodContract)
        {
            Contract.Requires(semanticMethod == null || semanticMethod.IsConstructor || semanticMethod.IsMethod);
            Contract.Ensures(!Contract.Result <bool>() || (Contract.ValueAtReturn(out methodContract) != null));

            methodContract = null;

            #region Check input
            if (semanticMethod == null)
            {
                return(false);
            }
            #endregion

            #region Try get the reference then check for contracts
            IMethodReference cciMethod;
            if (TryGetMethodReference(semanticMethod, out cciMethod))
            {
                if (TryGetMethodContract(cciMethod, out methodContract))
                {
                    return(true);
                }
                else
                {
                    //No need, detailed logs are written at all code paths in "TryGetMethodContract"
                    //ContractsPackageAccessor.Current.Logger.WriteToLog("Failed to get method contracts for: " + cciMethod.Name);
                }
            }
            else
            {
                methodContract = null;
                if (semanticMethod.Name != null)
                {
                    ContractsPackageAccessor.Current.Logger.WriteToLog("Failed to get CCI reference for: " + semanticMethod.Name.Text);
                }
            }
            return(false);

            #endregion
        }
예제 #26
0
        internal static string FormatPropertyContracts(IMethodContract getter, IMethodContract setter)
        {
            //Initialize our string builder
            var sb = new StringBuilder();

            //Append the 'Contracts' header
            //sb.Append("Contracts: ");
            //sb.Append('\n');

            if (!IsEmptyContract(getter))
            {
                sb.Append("get ");
                sb.Append('\n');
                FormatPrePostThrows(getter, sb);
            }
            if (!IsEmptyContract(setter))
            {
                sb.Append("set ");
                sb.Append('\n');
                FormatPrePostThrows(setter, sb);
            }
            //Can we get our result from the string builder?
            var result = sb.ToString();

            if (result == "")
            {
                return(null);
            }

            //Trim the new lines from the end
            result = result.TrimEnd('\n');

            result = SmartFormat(result);

            //Return our result
            return(result);
        }
예제 #27
0
 //^ ensures this.path.Count == old(this.path.Count);
 /// <summary>
 /// Traverses the given method contract.
 /// </summary>
 public virtual void Visit(IMethodContract methodContract)
 {
     if (this.stopTraversal) return;
       //^ int oldCount = this.path.Count;
       this.path.Push(methodContract);
       this.Visit(methodContract.Allocates);
       this.Visit(methodContract.Frees);
       this.Visit(methodContract.ModifiedVariables);
       this.Visit(methodContract.Postconditions);
       this.Visit(methodContract.Preconditions);
       this.Visit(methodContract.Reads);
       this.Visit(methodContract.ThrownExceptions);
       this.Visit(methodContract.Writes);
       //^ assume this.path.Count == oldCount+1; //True because all of the virtual methods of this class promise not decrease this.path.Count.
       this.path.Pop();
 }
예제 #28
0
        /// <summary>
        /// Returns the method contract, if any, that has been associated with the given object. Returns null if no association exits.
        /// </summary>
        /// <param name="method">An object that might have been associated with a method contract. This can be any kind of object.</param>
        /// <returns></returns>
        public IMethodContract /*?*/ GetMethodContractFor(object method)
        {
            IMethodContract contract = this.underlyingContractProvider.GetMethodContractFor(method);

            if (contract != null)
            {
                return(contract == ContractDummy.MethodContract ? null : contract);
            }

            IMethodReference methodReference = method as IMethodReference;

            if (methodReference == null)
            {
                this.underlyingContractProvider.AssociateMethodWithContract(method, ContractDummy.MethodContract);
                return(null);
            }

            IMethodDefinition methodDefinition = methodReference.ResolvedMethod;

            if (methodDefinition is Dummy)
            {
                this.underlyingContractProvider.AssociateMethodWithContract(method, ContractDummy.MethodContract);
                return(null);
            }

            if (methodDefinition.IsAbstract || methodDefinition.IsExternal) // precondition of Body getter
            // Need to see if the method is marked with any attributes that impact the contract
            {
                if (ContractHelper.IsPure(this.host, methodDefinition))
                {
                    var pureMC = new MethodContract()
                    {
                        IsPure = true,
                    };
                    this.underlyingContractProvider.AssociateMethodWithContract(method, pureMC);
                    return(pureMC);
                }
                else
                {
                    this.underlyingContractProvider.AssociateMethodWithContract(method, ContractDummy.MethodContract);
                    return(null);
                }
            }

            var unspecializedMethodDefintion = ContractHelper.UninstantiateAndUnspecializeMethodDefinition(methodDefinition);

            if (unspecializedMethodDefintion != methodDefinition)
            {
                contract = this.underlyingContractProvider.GetMethodContractFor(unspecializedMethodDefintion);
                if (contract != null)
                {
                    return(ContractHelper.InstantiateAndSpecializeContract(this.host, contract, methodDefinition, unspecializedMethodDefintion));
                }
            }

            IMethodBody methodBody = unspecializedMethodDefintion.Body;

            if (methodBody is Dummy)
            {
                this.underlyingContractProvider.AssociateMethodWithContract(method, ContractDummy.MethodContract);
                return(null);
            }

            ISourceMethodBody /*?*/ sourceMethodBody = methodBody as ISourceMethodBody;

            if (sourceMethodBody == null)
            {
                sourceMethodBody = Decompiler.GetCodeModelFromMetadataModel(this.host, methodBody, this.pdbReader, DecompilerOptions.AnonymousDelegates);
            }

            MethodContractAndMethodBody result = this.SplitMethodBodyIntoContractAndCode(sourceMethodBody);

            var methodContract = result.MethodContract;

            if (methodContract != null && unspecializedMethodDefintion != methodDefinition)
            {
                var instantiatedContract = ContractHelper.InstantiateAndSpecializeContract(this.host, result.MethodContract, methodDefinition, unspecializedMethodDefintion);
                methodContract = instantiatedContract;
            }

            #region Auto-properties get their contract from mining the invariant
            if (ContractHelper.IsAutoPropertyMember(host, unspecializedMethodDefintion))
            {
                var            tc = this.GetTypeContractFor(unspecializedMethodDefintion.ContainingTypeDefinition);
                MethodContract mc = ContractHelper.GetAutoPropertyContract(this.host, tc, unspecializedMethodDefintion);
                if (mc != null)
                {
                    if (unspecializedMethodDefintion != methodDefinition)
                    {
                        var mutableContract = ContractHelper.InstantiateAndSpecializeContract(this.host, mc, methodDefinition, unspecializedMethodDefintion);
                        mc = mutableContract;
                    }

                    if (methodContract == null)
                    {
                        methodContract = mc;
                    }
                    else
                    {
                        ContractHelper.AddMethodContract(mc, methodContract);
                    }
                }
            }
            #endregion

            if (methodContract == null)
            {
                this.underlyingContractProvider.AssociateMethodWithContract(method, ContractDummy.MethodContract); // so we don't try to extract more than once
            }
            else
            {
                this.underlyingContractProvider.AssociateMethodWithContract(method, methodContract);
            }

            // Notify all interested parties
            foreach (var c in this.callbacks)
            {
                c.ProvideResidualMethodBody(methodDefinition, result.BlockStatement);
            }

            return(methodContract);
        }
예제 #29
0
        /// <summary>
        /// Returns the method contract, if any, that has been associated with the given object. Returns null if no association exits.
        /// </summary>
        /// <param name="method">An object that might have been associated with a method contract. This can be any kind of object.</param>
        /// <returns></returns>
        public IMethodContract /*?*/ GetMethodContractFor(object method)
        {
            var cachedContract = this.contractProviderCache.GetMethodContractFor(method);

            if (cachedContract != null)
            {
                return(cachedContract == ContractDummy.MethodContract ? null : cachedContract);
            }

            IMethodReference methodReference = method as IMethodReference;

            if (methodReference == null)
            {
                this.contractProviderCache.AssociateMethodWithContract(method, ContractDummy.MethodContract);
                return(null);
            }
            IMethodDefinition methodDefinition = methodReference.ResolvedMethod;

            if (methodDefinition is Dummy)
            {
                this.contractProviderCache.AssociateMethodWithContract(method, ContractDummy.MethodContract);
                return(null);
            }
            var underlyingContract = this.underlyingContractProvider.GetMethodContractFor(method);

            if (!methodDefinition.IsAbstract)
            {
                if (underlyingContract != null)
                {
                    return(underlyingContract);
                }
                else
                {
                    this.contractProviderCache.AssociateMethodWithContract(method, ContractDummy.MethodContract);
                    return(null);
                }
            }

            // The method is definitely an abstract method, so either:
            //  (a) we've never looked for a contract for it before, or else
            //  (b) it is a specialized/instantiated method and the uninstantiated version has already
            //      had its contract extracted.

            var unspecializedMethodDefinition = ContractHelper.UninstantiateAndUnspecializeMethodDefinition(methodDefinition);

            cachedContract = this.contractProviderCache.GetMethodContractFor(unspecializedMethodDefinition);

            if (cachedContract == null) // (a)

            // Check to see if its containing type points to a class holding the contract
            {
                IMethodDefinition /*?*/ proxyMethod = ContractHelper.GetMethodFromContractClass(this.host, unspecializedMethodDefinition);
                if (proxyMethod == null)
                {
                    this.contractProviderCache.AssociateMethodWithContract(method, ContractDummy.MethodContract);
                    return(null);
                }
                MethodContract cumulativeContract = new MethodContract();
                if (underlyingContract != null)
                {
                    ContractHelper.AddMethodContract(cumulativeContract, underlyingContract);
                }

                IMethodContract proxyContract = this.underlyingContractProvider.GetMethodContractFor(proxyMethod);
                ITypeReference  contractClass = proxyMethod.ContainingTypeDefinition;
                var             gtir          = contractClass as IGenericTypeInstanceReference;
                if (gtir != null)
                {
                    contractClass = gtir.GenericType;
                }

                if (proxyContract == null)
                {
                    if (underlyingContract == null)
                    {
                        // then there was nothing on the abstract method (like purity markings)
                        this.contractProviderCache.AssociateMethodWithContract(method, ContractDummy.MethodContract);
                        return(null);
                    }
                    else
                    {
                        // nothing on proxy, but something on abstract method
                        this.contractProviderCache.AssociateMethodWithContract(method, cumulativeContract);
                        return(cumulativeContract);
                    }
                }
                var copier = new CodeAndContractDeepCopier(this.host);
                proxyContract = copier.Copy(proxyContract);

                var cccc = new ConvertContractClassContract(this.host, contractClass, unspecializedMethodDefinition.ContainingType);
                proxyContract = cccc.Rewrite(proxyContract);
                proxyContract = ContractHelper.CopyContractIntoNewContext(this.host, proxyContract, unspecializedMethodDefinition, proxyMethod);

                ContractHelper.AddMethodContract(cumulativeContract, proxyContract);

                // Cache the unspecialized contract: specialize and instantiate on demand
                this.contractProviderCache.AssociateMethodWithContract(unspecializedMethodDefinition, cumulativeContract);
                cachedContract = cumulativeContract;
            }

            if (unspecializedMethodDefinition == methodDefinition)
            {
                return(cachedContract == ContractDummy.MethodContract ? null : cachedContract);
            }
            else // (b)
            {
                var mc = ContractHelper.InstantiateAndSpecializeContract(this.host, cachedContract, methodDefinition, unspecializedMethodDefinition);
                mc = (MethodContract)ContractHelper.CopyContractIntoNewContext(this.host, mc, methodDefinition, unspecializedMethodDefinition);
                return(mc);
            }
        }
예제 #30
0
    /// <summary>
    /// Makes a shallow copy of the given method contract.
    /// </summary>
    public virtual MethodContract Copy(IMethodContract methodContract) {
      Contract.Requires(methodContract != null);
      Contract.Ensures(Contract.Result<MethodContract>() != null);

      return new MethodContract(methodContract);
    }
            public void PackageMethodContracts(IMethodDefinition method, bool isPure)
            {
                Contract.Requires(method != null);

                #region Package purity
                if (isPure)
                {
                    PackageContract(new XPure(this.host, isPure, docTracker));
                }
                //Don't package anything if it isn't pure. (That way it is easyer to deal with on the Sandcastle side)
                #endregion
                #region Package contracts from this implementation
                IMethodContract thisContract;
                if (CCDocContractHelper.TryGetMethodContract(host, method, out thisContract, docTracker))
                {
                    PackageMethodContracts(thisContract, null, null);
                }
                #endregion
                #region Package contracts from base overrides
                if (!method.IsNewSlot) // REVIEW: Is there a better test?
                {
                    IMethodDefinition overriddenMethod = MemberHelper.GetImplicitlyOverriddenBaseClassMethod(method) as IMethodDefinition;
                    while (overriddenMethod != null && overriddenMethod != Dummy.Method)
                    {
                        IMethodContract /*?*/ overriddenContract;
                        if (CCDocContractHelper.TryGetMethodContract(host, overriddenMethod, out overriddenContract, docTracker))
                        {
                            SubstituteParameters sps         = new SubstituteParameters(this.host, method, overriddenMethod);
                            IMethodContract      newContract = sps.Rewrite(overriddenContract) as MethodContract;
                            var unspecializedMethod          = MethodHelper.Unspecialize(overriddenMethod);
                            var methodId = MemberHelper.GetMemberSignature(unspecializedMethod, NameFormattingOptions.DocumentationId);
                            var typeName = TypeHelper.GetTypeName(unspecializedMethod.ContainingType, NameFormattingOptions.OmitContainingNamespace | NameFormattingOptions.OmitContainingType);
                            PackageMethodContracts(newContract, methodId, typeName);
                        }
                        overriddenMethod = MemberHelper.GetImplicitlyOverriddenBaseClassMethod(overriddenMethod) as IMethodDefinition;
                    }
                }
                #endregion
                #region Package contracts from implicit interface implementations
                foreach (IMethodDefinition ifaceMethod in MemberHelper.GetImplicitlyImplementedInterfaceMethods(method))
                {
                    IMethodContract /*?*/ ifaceContract;
                    if (!CCDocContractHelper.TryGetMethodContract(host, ifaceMethod, out ifaceContract, docTracker))
                    {
                        continue;
                    }
                    SubstituteParameters sps         = new SubstituteParameters(this.host, method, ifaceMethod);
                    IMethodContract      newContract = sps.Rewrite(ifaceContract) as MethodContract;
                    var unspecializedMethod          = MethodHelper.Unspecialize(ifaceMethod);
                    var methodId = MemberHelper.GetMemberSignature(unspecializedMethod, NameFormattingOptions.DocumentationId);
                    var typeName = TypeHelper.GetTypeName(unspecializedMethod.ContainingType, NameFormattingOptions.OmitContainingNamespace | NameFormattingOptions.OmitContainingType);
                    PackageMethodContracts(newContract, methodId, typeName);
                }
                #endregion
                #region Package contracts from explicit interface implementations
                // REVIEW: Why does GetExplicitlyOverriddenMethods return IMethodReference when GetImplicitlyImplementedInterfaceMethods
                // returns IMethodDefinition?
                foreach (IMethodReference ifaceMethodRef in MemberHelper.GetExplicitlyOverriddenMethods(method))
                {
                    IMethodDefinition /*?*/ ifaceMethod = ifaceMethodRef.ResolvedMethod;
                    if (ifaceMethod == null)
                    {
                        continue;
                    }
                    IMethodContract /*?*/ ifaceContract;
                    if (!CCDocContractHelper.TryGetMethodContract(host, ifaceMethod, out ifaceContract, docTracker))
                    {
                        continue;
                    }
                    SubstituteParameters sps         = new SubstituteParameters(this.host, method, ifaceMethod);
                    IMethodContract      newContract = sps.Rewrite(ifaceContract) as MethodContract;
                    var unspecializedMethod          = MethodHelper.Unspecialize(ifaceMethod);
                    var methodId = MemberHelper.GetMemberSignature(unspecializedMethod, NameFormattingOptions.DocumentationId);
                    var typeName = TypeHelper.GetTypeName(unspecializedMethod.ContainingType, NameFormattingOptions.OmitContainingNamespace | NameFormattingOptions.OmitContainingType);
                    PackageMethodContracts(newContract, methodId, typeName);;
                }
                #endregion
            }
예제 #32
0
 public void Visit(IMethodContract methodContract)
 {
     Contract.Assume(false);
 }
예제 #33
0
 public void Visit(IMethodContract methodContract)
 {
     Contract.Requires(methodContract != null);
       throw new NotImplementedException();
 }
예제 #34
0
파일: Copier.cs 프로젝트: riverar/devtools
 /// <summary>
 /// Returns a deep copy of the <param name="methodContract"/>.
 /// </summary>
 public virtual IMethodContract Substitute(IMethodContract methodContract)
 {
     this.coneAlreadyFixed = true;
       return this.DeepCopy(new MethodContract(methodContract));
 }
예제 #35
0
파일: Copier.cs 프로젝트: riverar/devtools
 /// <summary>
 /// Makes a deep copy of the given method contract.
 /// </summary>
 public MethodContract Copy(IMethodContract methodContract)
 {
     var mutableCopy = this.shallowCopier.Copy(methodContract);
       mutableCopy.Allocates = this.Copy(mutableCopy.Allocates);
       mutableCopy.Frees = this.Copy(mutableCopy.Frees);
       mutableCopy.ModifiedVariables = this.Copy(mutableCopy.ModifiedVariables);
       mutableCopy.Postconditions = this.Copy(mutableCopy.Postconditions);
       mutableCopy.Preconditions = this.Copy(mutableCopy.Preconditions);
       mutableCopy.Reads = this.Copy(mutableCopy.Reads);
       mutableCopy.ThrownExceptions = this.Copy(mutableCopy.ThrownExceptions);
       mutableCopy.Writes = this.Copy(mutableCopy.Writes);
       return mutableCopy;
 }
    internal static string FormatPropertyContracts(IMethodContract getter, IMethodContract setter)
    {
        //Initialize our string builder
        var sb = new StringBuilder();

        //Append the 'Contracts' header
        //sb.Append("Contracts: ");
        //sb.Append('\n');

        if (!IsEmptyContract(getter))
        {
            sb.Append("get ");
            sb.Append('\n');
            FormatPrePostThrows(getter, sb);
        }
        if (!IsEmptyContract(setter))
        {
            sb.Append("set ");
            sb.Append('\n');
            FormatPrePostThrows(setter, sb);
        }
        //Can we get our result from the string builder?
        var result = sb.ToString();

        if (result == "") return null;

        //Trim the new lines from the end
        result = result.TrimEnd('\n');

        result = SmartFormat(result);

        //Return our result
        return result;
    }
예제 #37
0
파일: Copier.cs 프로젝트: riverar/devtools
 /// <summary>
 /// Returns a deep mutable copy of the given method contract.
 /// </summary>
 /// <param name="host">An object representing the application that is hosting this mutator. It is used to obtain access to some global
 /// objects and services such as the shared name table and the table for interning references. For the purposes of this call, the
 /// table for interning is what is needed.</param>
 /// <param name="methodContract">The method contract to copy.</param>
 public static MethodContract DeepCopy(IMetadataHost host, IMethodContract methodContract)
 {
     return (MethodContract)new CodeAndContractCopier(host, null).Substitute(methodContract);
 }
예제 #38
0
    /// <summary>
    /// Makes a deep copy of the given method contract.
    /// </summary>
    public MethodContract Copy(IMethodContract methodContract) {
      Contract.Requires(methodContract != null);
      Contract.Ensures(Contract.Result<MethodContract>() != null);

      var mutableCopy = this.shallowCopier.Copy(methodContract);
      mutableCopy.Allocates = this.Copy(mutableCopy.Allocates);
      mutableCopy.Frees = this.Copy(mutableCopy.Frees);
      mutableCopy.ModifiedVariables = this.Copy(mutableCopy.ModifiedVariables);
      mutableCopy.Postconditions = this.Copy(mutableCopy.Postconditions);
      mutableCopy.Preconditions = this.Copy(mutableCopy.Preconditions);
      mutableCopy.Reads = this.Copy(mutableCopy.Reads);
      mutableCopy.ThrownExceptions = this.Copy(mutableCopy.ThrownExceptions);
      mutableCopy.Writes = this.Copy(mutableCopy.Writes);
      return mutableCopy;
    }
예제 #39
0
      void PackageMethodContracts(IMethodContract methodContract, string methodId, string typeName)
      {
        Contract.Requires(methodContract != null);

        if (IteratorHelper.EnumerableIsNotEmpty<IPrecondition>(methodContract.Preconditions))
          PackagePreconditions(methodContract.Preconditions, methodId, typeName);
        if (IteratorHelper.EnumerableIsNotEmpty<IPostcondition>(methodContract.Postconditions))
          PackagePostconditions(methodContract.Postconditions, methodId, typeName);
        if (IteratorHelper.EnumerableIsNotEmpty<IThrownException>(methodContract.ThrownExceptions))
          PackageThrownExceptions(methodContract.ThrownExceptions, methodId, typeName);
      }
예제 #40
0
 /// <summary>
 /// 
 /// </summary>
 /// <param name="methodContract"></param>
 public MethodContract(IMethodContract methodContract) {
   this.allocates = new List<IExpression>(methodContract.Allocates);
   this.frees = new List<IExpression>(methodContract.Frees);
   this.locations = new List<ILocation>(methodContract.Locations);
   this.modifiedVariables = new List<IAddressableExpression>(methodContract.ModifiedVariables);
   this.mustInline = methodContract.MustInline;
   this.postconditions = new List<IPostcondition>(methodContract.Postconditions);
   this.preconditions = new List<IPrecondition>(methodContract.Preconditions);
   this.reads = new List<IExpression>(methodContract.Reads);
   this.thrownExceptions = new List<IThrownException>(methodContract.ThrownExceptions);
   this.variants = new List<IExpression>(methodContract.Variants);
   this.writes = new List<IExpression>(methodContract.Writes);
   this.isPure = methodContract.IsPure;
 }
예제 #41
0
 /// <summary>
 /// Traverses the method contract.
 /// </summary>
 public void Traverse(IMethodContract methodContract)
 {
     Contract.Requires(methodContract != null);
       if (this.preorderVisitor != null) this.preorderVisitor.Visit(methodContract);
       if (this.StopTraversal) return;
       this.TraverseChildren(methodContract);
       if (this.postorderVisitor != null) this.postorderVisitor.Visit(methodContract);
       if (this.StopTraversal) return;
 }
예제 #42
0
파일: Copier.cs 프로젝트: riverar/devtools
 /// <summary>
 /// Makes a shallow copy of the given method contract.
 /// </summary>
 public virtual MethodContract Copy(IMethodContract methodContract)
 {
     return new MethodContract(methodContract);
 }
예제 #43
0
 /// <summary>
 /// Traverses the children of the method contract.
 /// </summary>
 public virtual void TraverseChildren(IMethodContract methodContract)
 {
     Contract.Requires(methodContract != null);
       this.Traverse(methodContract.Allocates);
       if (this.StopTraversal) return;
       this.Traverse(methodContract.Frees);
       if (this.StopTraversal) return;
       this.Traverse(methodContract.ModifiedVariables);
       if (this.StopTraversal) return;
       this.Traverse(methodContract.Postconditions);
       if (this.StopTraversal) return;
       this.Traverse(methodContract.Preconditions);
       if (this.StopTraversal) return;
       this.Traverse(methodContract.Reads);
       if (this.StopTraversal) return;
       this.Traverse(methodContract.ThrownExceptions);
       if (this.StopTraversal) return;
       this.Traverse(methodContract.Writes);
 }
예제 #44
0
 public void Visit(IMethodContract methodContract)
 {
     Contract.Assume(false);
 }
예제 #45
0
 /// <summary>
 /// Visits the given method contract.
 /// </summary>
 public virtual void Visit(IMethodContract methodContract)
 {
 }
    public bool TryGetPropertyContract(ISymbol semanticMember, out IMethodContract getterContract, out IMethodContract setterContract)
    {
        Contract.Requires(semanticMember == null || semanticMember.Kind == SymbolKind.Property);

        getterContract = null;
        setterContract = null;

        #region Check input
        if (semanticMember == null)
        {
            return false;
        }
        #endregion
        IMethodReference getter, setter;
        if (!TryGetPropertyAccessorReferences(semanticMember, out getter, out setter)) { return false; }

        var success = false;
        if (getter != null)
        {
            success |= TryGetMethodContract(getter, out getterContract);
        }
        if (setter != null)
        {
            success |= TryGetMethodContract(setter, out setterContract);
        }
        return success;
    }
예제 #47
0
        void DoWork()
        {
            string  assemblyName;
            Version assemblyVersion;
            string  assemblyLocation;
            string  typeName;
            int     genericParameterCount;

            GetNecessaryInfo(out assemblyName, out assemblyVersion, out assemblyLocation, out typeName, out genericParameterCount);


            #region Create host
            var host = this._projectTracker.Host;

            if (host == null)
            {
                VSServiceProvider.Current.Logger.WriteToLog("Couldn't create host.");
                return;
            }
            #endregion
            #region Find and load assembly
            IAssembly iAssembly = null;

            if (assemblyName.Equals(host.CoreAssemblySymbolicIdentity.Name.Value, StringComparison.OrdinalIgnoreCase) && assemblyVersion.Equals(host.CoreAssemblySymbolicIdentity.Version))
            {
                iAssembly = host.FindAssembly(host.CoreAssemblySymbolicIdentity);
            }
            else
            {
                var references = _projectTracker.References;
                VSLangProj.Reference reference   = null;
                var assemblyNameWithoutExtension = Path.GetFileNameWithoutExtension(assemblyName);
                for (int i = 1; i <= references.Count; i++)//TODO: Unify this code. This process of looking up a reference from a name is also done in ContractsProvider.TryGetAssemblyReference
                {
                    var    tempRef = references.Item(i);
                    string refName = tempRef.Name;
                    if (refName.Equals(assemblyNameWithoutExtension, StringComparison.OrdinalIgnoreCase))
                    {
                        reference = tempRef;
                        break;
                    }
                }
                if (reference != null)
                {
                    IName   iName    = host.NameTable.GetNameFor(Path.GetFileNameWithoutExtension(reference.Path));
                    string  culture  = reference.Culture;
                    Version version  = new Version(reference.MajorVersion, reference.MinorVersion, reference.BuildNumber, reference.RevisionNumber);
                    string  location = reference.Path;
                    var     tempRef2 = new Microsoft.Cci.Immutable.AssemblyReference(host, new AssemblyIdentity(iName, culture, version, Enumerable <byte> .Empty, location));
                    iAssembly = host.LoadAssembly(tempRef2.AssemblyIdentity);
                }
                else
                {
                    VSServiceProvider.Current.Logger.WriteToLog("Couldn't find reference for metadata file.");
                    return;
                }
            }
            if (iAssembly == null || iAssembly == Dummy.Assembly)
            {
                VSServiceProvider.Current.Logger.WriteToLog("Couldn't get assembly for metadata file.");
                return;
            }
            #endregion
            #region Get contracts provider
            var contractsProvider = host.GetContractExtractor(iAssembly.UnitIdentity);
            if (contractsProvider == null)
            {
                VSServiceProvider.Current.Logger.WriteToLog("Couldn't get contracts provider.");
                return;
            }
            #endregion
            #region Collect contracts
            var type = UnitHelper.FindType(host.NameTable, iAssembly, typeName, genericParameterCount);
            if (type == null || type is Dummy)
            {
                VSServiceProvider.Current.Logger.WriteToLog("Couldn't find metadata type '" + typeName + "' in assembly.");
                return;
            }

            //This dictionaries will map the method/property signature to the contracts for the method/property
            var methodsToContracts = new Dictionary <string, IMethodContract>(type.Methods.Count());
            var gettersToContracts = new Dictionary <string, IMethodContract>();
            var settersToContracts = new Dictionary <string, IMethodContract>();

            //Set the formatting options for property getters and setters
            var propertySignatureFormattingOptions = NameFormattingOptions.OmitContainingNamespace |
                                                     // NameFormattingOptions.ReturnType |
                                                     NameFormattingOptions.TypeParameters |
                                                     NameFormattingOptions.UseTypeKeywords |
                                                     NameFormattingOptions.OmitContainingType;
            //NameFormattingOptions.Visibility;
            //Set the formating options for methods
            var methodSignatureFormattingOptions = NameFormattingOptions.OmitContainingNamespace |
                                                   NameFormattingOptions.ReturnType |
                                                   NameFormattingOptions.ParameterName |
                                                   NameFormattingOptions.ParameterModifiers |
                                                   NameFormattingOptions.TypeParameters |
                                                   NameFormattingOptions.UseTypeKeywords |
                                                   NameFormattingOptions.OmitContainingType |
                                                   //NameFormattingOptions.Modifiers |
                                                   NameFormattingOptions.Signature
                                                   //NameFormattingOptions.Visibility
            ;

            //var sourceEmitterOutput = new SourceEmitterOutputString();//TODO: Use source emitter for all my printing? Instead of the whole NameFormattingOptions ordeal.
            //var csSourceEmitter = new SourceEmitter(sourceEmitterOutput);

            foreach (var method in type.Methods)
            {
                var methodContract = ContractHelper.GetMethodContractForIncludingInheritedContracts(host, method);
                if (methodContract != null && methodContract != ContractDummy.MethodContract)
                {
                    if (IsGetter(method))
                    {
                        if (method.ParameterCount > 0) //We have an indexer!
                        {
                            var indexerSignature = PrintIndexer(method, true);
                            gettersToContracts.Add(indexerSignature, methodContract);
                        }
                        else
                        {
                            var getterSignature = MemberHelper.GetMemberSignature(method, propertySignatureFormattingOptions);//Example: "XmlSchemaSet Schemas.get"
                            getterSignature = getterSignature.Substring(0, getterSignature.LastIndexOf('.'));
                            gettersToContracts.Add(getterSignature, methodContract);
                        }
                    }
                    else if (IsSetter(method))
                    {
                        if (method.ParameterCount > 1) //We have an indexer!
                        {
                            var indexerSignature = PrintIndexer(method, false);
                            settersToContracts.Add(indexerSignature, methodContract);
                        }
                        else
                        {
                            var setterSignature = MemberHelper.GetMemberSignature(method, propertySignatureFormattingOptions);
                            setterSignature = setterSignature.Substring(0, setterSignature.LastIndexOf('.'));
                            settersToContracts.Add(setterSignature, methodContract);
                        }
                    }
                    else
                    {
                        //#region Print method, stolen from CSharpSourceEmitter
                        //csSourceEmitter.PrintMethodDefinitionVisibility(method);
                        //csSourceEmitter.PrintMethodDefinitionModifiers(method);

                        //bool conversion = csSourceEmitter.IsConversionOperator(method);
                        //if (!conversion) {
                        //  csSourceEmitter.PrintMethodDefinitionReturnType(method);
                        //  if (!method.IsConstructor && !csSourceEmitter.IsDestructor(method))
                        //    csSourceEmitter.PrintToken(CSharpToken.Space);
                        //}
                        //csSourceEmitter.PrintMethodDefinitionName(method);
                        //if (conversion)
                        //  csSourceEmitter.PrintMethodDefinitionReturnType(method);

                        //if (method.IsGeneric) {
                        //  csSourceEmitter.Traverse(method.GenericParameters);
                        //}
                        //csSourceEmitter.Traverse(method.Parameters);
                        //#endregion
                        //var methodSignature = sourceEmitterOutput.Data;
                        //sourceEmitterOutput.ClearData();
                        var methodSignature = MemberHelper.GetMemberSignature(method, methodSignatureFormattingOptions);//Example: "XmlAttribute CreateAttribute(string name)"
                        methodsToContracts.Add(methodSignature, methodContract);
                    }
                }
            }
            #endregion

            var hasMethodContracts   = methodsToContracts.Count > 0;
            var hasPropertyContracts = gettersToContracts.Count > 0 || settersToContracts.Count > 0;

            if (!hasMethodContracts && !hasPropertyContracts)
            {
                VSServiceProvider.Current.Logger.WriteToLog("No contracts found.");
                return;
            }

            int propertyCounter = 0; //Counts the number of adornments added for property contracts
            int methodCounter   = 0; //Counts the number of adornments added for method contracts
            foreach (var line in _textView.TextSnapshot.Lines)
            {
                var lineText = line.GetText();

                //Skip lines with comments
                //This assumes that no method/property decelerations in metadata files will have comments in them
                if (lineText.Contains("//"))
                {
                    continue;
                }

                // bail out on nested types
                var typeNameMatch = Regex.Match(lineText, @"(class|struct|interface|enum) (\w+)");
                if (typeNameMatch.Success)
                {
                    if (typeNameMatch.Groups[2].Value == type.Name.Value)
                    {
                        continue;
                    }
                    break;
                }

                if (hasPropertyContracts &&
                    lineText.Contains('{') && (lineText.Contains(" get; ") || lineText.Contains(" set; ")) && lineText.Contains('}')) //Check if line is a property decleration
                {
                    #region Add property contracts
                    //Parse the property decleration to get a signature we can compare to our contract dictionaries
                    //Example of a property decleration: "     public int Build { get; }"
                    int  endOfSig              = lineText.IndexOf('{') - 1;
                    int  startOfSig            = endOfSig - 1;
                    bool hasHitSpace           = false;
                    bool isInPropertyParameter = false;
                    for (int i = startOfSig; i > 0; i--)
                    {
                        char c = lineText[i];
                        if (c == ']')
                        {
                            isInPropertyParameter = true;
                        }
                        else if (c == '[')
                        {
                            isInPropertyParameter = false;
                        }
                        else if (hasHitSpace && c == ' ')
                        {
                            startOfSig = i + 1;
                            break;
                        }
                        else if (!isInPropertyParameter && c == ' ')
                        {
                            startOfSig = i + 1;
                            break; // MAF: ignore return type of properties.
                            //hasHitSpace = true;
                        }
                    }
                    var propertySignature = lineText.Substring(startOfSig, endOfSig - startOfSig); //Example: "int Build"

                    IMethodContract getterContract = null;
                    IMethodContract setterContract = null;
                    if (gettersToContracts.TryGetValue(propertySignature, out getterContract) | // yes eager evaluation!!!
                        settersToContracts.TryGetValue(propertySignature, out setterContract))
                    {
                        var tag = propertySignature.GetHashCode();//We use this to uniquely identify the particular method/property decleration

                        //Find this first non-whitespace character. This is were we'll place the adornment.
                        int firstNonWhitespace = 0;
                        for (int i = 0; i < lineText.Length; i++)
                        {
                            char c = lineText[i];
                            if (c != ' ')
                            {
                                firstNonWhitespace = i;
                                break;
                            }
                        }
                        var span = _textView.TextSnapshot.CreateTrackingSpan(line.Start + firstNonWhitespace, propertySignature.Length, SpanTrackingMode.EdgeExclusive);
                        _vsTextProperties.LineHeight = _textView.LineHeight;
                        var ops       = AdornmentOptionsHelper.GetAdornmentOptions(VSServiceProvider.Current.VSOptionsPage);
                        var adornment = new MetadataContractAdornment(span, _vsTextProperties, VSServiceProvider.Current.Logger, _adornmentManager.QueueRefreshLineTransformer, ops);
                        adornment.SetContracts(getterContract, setterContract, null /* "Contracts from " + typeName + "." */);
                        _adornmentManager.AddAdornment(adornment, tag);
                        propertyCounter++;
                    }
                    #endregion
                    continue;
                }
                if (hasMethodContracts &&
                    lineText.Contains('(') && lineText.Contains(')') && lineText.Contains(';')) //Check if line is a method decleration
                {
                    #region Add method contracts
                    //Parse the method decleration to get a signature we can compare to our contract dictionaries
                    //Example of a method decleration: "      public static Version Parse(string input);"
                    int endOfSig = lineText.LastIndexOf(')') + 1;
                    //int startOfSig = !Char.IsWhiteSpace(lineText[0]) ? 0 : lineText.IndexOf(lineText.First(c => !Char.IsWhiteSpace(c)));
                    //int startOfSig = lineText.IndexOf('(');
                    //bool hitSpace = false;
                    //for (int i = startOfSig; i > 0; i--) {
                    //  char c = lineText[i];
                    //  if (c == ' ' && hitSpace) {
                    //    startOfSig = i + 1;
                    //    break;
                    //  } else if (c == ' ') {
                    //    hitSpace = true;
                    //  }
                    //}
                    var methodSignature = lineText.Substring(0, endOfSig); //Example: "Version Parse(string input)"

                    // remove modifiers
                    methodSignature = Regex.Replace(methodSignature, modifierFilter, "");
                    methodSignature = methodSignature.Trim();
                    if (methodSignature.StartsWith(type.Name.Value + "("))
                    {
                        methodSignature = "void .ctor" + methodSignature.Substring(type.Name.Value.Length);
                    }
                    IMethodContract methodContract;
                    if (methodsToContracts.TryGetValue(methodSignature, out methodContract))
                    {
                        var tag = methodSignature.GetHashCode();//We use this to uniquely identify the particular method/property decleration

                        //Find this first non-whitespace character. This is were we'll place the adornment.
                        int firstNonWhitespace = 0;
                        for (int i = 0; i < lineText.Length; i++)
                        {
                            char c = lineText[i];
                            if (c != ' ')
                            {
                                firstNonWhitespace = i;
                                break;
                            }
                        }
                        var span = _textView.TextSnapshot.CreateTrackingSpan(line.Start + firstNonWhitespace, methodSignature.Length, SpanTrackingMode.EdgeExclusive);
                        _vsTextProperties.LineHeight = _textView.LineHeight;
                        var ops       = AdornmentOptionsHelper.GetAdornmentOptions(VSServiceProvider.Current.VSOptionsPage);
                        var adornment = new MetadataContractAdornment(span, _vsTextProperties, VSServiceProvider.Current.Logger, _adornmentManager.QueueRefreshLineTransformer, ops);
                        adornment.SetContracts(methodContract, "Contracts from " + typeName + ".");
                        _adornmentManager.AddAdornment(adornment, tag);
                        //if (methodContract.IsPure) {
                        //  var purityAdornment = new PurityAdornment(_vsTextProperties, adornment);
                        //  //_adornmentManager.AddAdornment(purityAdornment, null);
                        //}
                        methodCounter++;
                    }
                    #endregion
                    continue;
                }
            }

            #region Add button to collapse all contracts
            if (propertyCounter > 0 || methodCounter > 0)
            {
                var button = new Button();
                button.Content = "Hide all contracts";
                button.Click  += OnCollapseAllClick;
                button.Cursor  = Cursors.Hand;
                var collapseAllAdornment = new StaticAdornment(false, 10d, true, 10d, button);
                _adornmentManager.AddStaticAdornment(collapseAllAdornment);
            }
            #endregion
        }
    public bool TryGetMethodContract(ISymbol semanticMethod, out IMethodContract methodContract)
    {
      Contract.Requires(semanticMethod == null || semanticMethod.Kind == SymbolKind.Method);
      Contract.Ensures(!Contract.Result<bool>() || (Contract.ValueAtReturn(out methodContract) != null));

      methodContract = null;

      #region Check input
      if (semanticMethod == null) {
        return false;
      }
      #endregion

      #region Try get the reference then check for contracts
      IMethodReference cciMethod;
      if (TryGetMethodReference(semanticMethod, out cciMethod)) {
        if (TryGetMethodContract(cciMethod, out methodContract)) {
          return true;
        } else {
          //No need, detailed logs are written at all code paths in "TryGetMethodContract"
          //ContractsPackageAccessor.Current.Logger.WriteToLog("Failed to get method contracts for: " + cciMethod.Name);
        }
      } else {
        methodContract = null;
        if (semanticMethod.Name != null)
        {
          ContractsPackageAccessor.Current.Logger.WriteToLog("Failed to get CCI reference for: " + semanticMethod.Name);
        }
      }
      return false;
      #endregion
    }
 public virtual IEnumerable<Bpl.IdentifierExpr> getModifiedIdentifiers(IMethodContract contract) { return new List<Bpl.IdentifierExpr>(); }
    public bool TryGetMethodContract(IMethodReference method, out IMethodContract methodContract) {
      Contract.Ensures(!Contract.Result<bool>() || (Contract.ValueAtReturn(out methodContract) != null));

      methodContract = null;

      #region Check input
      if (method == null) {
        return false;
      }
      #endregion
      try {
        // Resolving the method works *only* if the unit it is defined in has already been loaded.
        // That should have happened as part of creating the IMethodReference.
        var resolvedMethod = method.ResolvedMethod;
        if (resolvedMethod != Dummy.Method) {
          methodContract = ContractHelper.GetMethodContractForIncludingInheritedContracts(Host, resolvedMethod);
          if (methodContract == null) {
            methodContract = ContractDummy.MethodContract;
            ContractsPackageAccessor.Current.Logger.WriteToLog(String.Format("Did not find any method contract(s) for '{0}'", method.Name));
          } else {
            ContractsPackageAccessor.Current.Logger.WriteToLog(
              String.Format("Got method contract(s) for '{0}': {1} preconditions, {2} postconditions",
                method.Name,
                Microsoft.Cci.IteratorHelper.EnumerableCount(methodContract.Preconditions),
                Microsoft.Cci.IteratorHelper.EnumerableCount(methodContract.Postconditions)));
          }
        } else {
          ContractsPackageAccessor.Current.Logger.WriteToLog(String.Format("Method '{0}' resolved to dummy", method.Name));
        }
      } catch (NullReferenceException) {
        methodContract = null;
        ContractsPackageAccessor.Current.Logger.WriteToLog(String.Format("NullReferenceException thrown when getting contracts for '{0}'", method.Name));
      }
      return methodContract != null;
    }
 /// <summary>
 /// Wraps a call to GetMethodContractFor inside of a try-catch statement.
 /// </summary>
 public static bool TryGetMethodContract(CodeContractAwareHostEnvironment host, IMethodReference method, out IMethodContract methodContract, DocTracker docTracker)
 {
     Contract.Requires(host != null);
     Contract.Requires(method != null);
     Contract.Ensures(!Contract.Result <bool>() || Contract.ValueAtReturn(out methodContract) != null);
     try {
         methodContract = ContractHelper.GetMethodContractFor(host, method.ResolvedMethod);
     } catch (NullReferenceException) {
         docTracker.WriteLine("ERROR: NullReferenceException was thrown in CCI!");
         methodContract = null;
     }
     //} catch (Exception e) {
     //  docTracker.WriteLine("ERROR: Exception of type '{0}' was thrown in CCI!", e.GetType().Name);
     //  docTracker.WriteLine("\t'{0}'", e.Message);
     //  methodContract = null;
     //}
     return(methodContract != null);
 }
    public bool TryGetMethodContractSafe(ISymbol semanticMehod, out IMethodContract methodContract) {
      Contract.Requires(semanticMehod == null || semanticMehod.Kind == SymbolKind.Method);
      Contract.Ensures(!Contract.Result<bool>() || (Contract.ValueAtReturn(out methodContract) != null));

      methodContract = null;

      #region Check input
      if (semanticMehod == null) {
        return false;
      }
      #endregion
      #region Call TryGetMethodContract cautiously
      try {
        //Can we get contracts?
        if (!TryGetMethodContract(semanticMehod, out methodContract))
          return false;
      }
      #endregion
      #region Abort on exception
        //Give up on our contracts if we get an exception
      catch (IllFormedSemanticModelException) {
        return false;
      } catch (InvalidOperationException e) {
        if (!e.Message.Contains(ContractsPackageAccessor.InvalidOperationExceptionMessage_TheSnapshotIsOutOfDate))
          throw e;
        else
          return false;
      } catch (System.Runtime.InteropServices.COMException e) {
        if (!e.Message.Contains(ContractsPackageAccessor.COMExceptionMessage_BindingFailed))
          throw e;
        else
          return false;
      }
      #endregion

      return methodContract != null;
    }
예제 #53
0
        static void RecursivelyLookupContractsForMethods(InheritanceTracker @this)
        {
            Contract.Requires(@this != null);

            #region Dequeue
            if (@this._methodsNeedingContractLookup.Count < 1)
            {
                return;
            }
            var methodPair = @this._methodsNeedingContractLookup.Dequeue();
            var method     = methodPair.Value;
            var tag        = methodPair.Key;
            #endregion
            try {
                ContractsPackageAccessor.Current.Logger.WriteToLog(String.Format("Attempting to lookup contracts for '{0}'", tag.ToString()));
                var comp = @this._textViewTracker.LatestCompilation;
                if (comp == null)
                {
                    ContractsPackageAccessor.Current.Logger.WriteToLog("No LatestCompilation, waiting for a new semantic model.");
                    @this._textViewTracker.IsLatestCompilationStale = true;
                    Utilities.Delay(() => ContractsPackageAccessor.Current.AskForNewVSModel(), DelayOnVSModelFailedBeforeTryingAgain);
                    @this.semanticModelsFetchedCounter++;
                    goto RequeueAndAbort;
                }
                #region Get semantic method from syntactic method
                CSharpMember semanticMethod = null;
                semanticMethod = comp.GetMemberForMethodDeclaration(method);
                if (semanticMethod == null)
                {
                    if (@this.trackingNumberOfFetchedSemanticModels && @this.semanticModelsFetchedCounter <= 3)
                    {
                        ContractsPackageAccessor.Current.Logger.WriteToLog("Failed to get semantic method from syntactic method, waiting for a new semantic model.");
                        @this._textViewTracker.IsLatestCompilationStale = true;
                        Utilities.Delay(() => ContractsPackageAccessor.Current.AskForNewVSModel(), DelayOnVSModelFailedBeforeTryingAgain);
                        @this.semanticModelsFetchedCounter++;
                        goto RequeueAndAbort;
                    }
                    else
                    {
                        ContractsPackageAccessor.Current.Logger.WriteToLog("Failed to get semantic method from syntactic method. Too many semantic models have already been fetched, skipping this method...");
                        goto Continue;
                    }
                }
                #endregion
                #region Try get the method that this method is inherited from
                CSharpMember inheritedFromMethod;
                if (!TryGetIheritedFromMember(semanticMethod, method.Parent as TypeDeclarationNode, out inheritedFromMethod))
                {
                    goto Continue;
                }
                #endregion
                #region Uninstantiated method
                semanticMethod = semanticMethod.Uninstantiate();
                #endregion
                #region Get our tool tip
                var toolTip = "";
                if (!semanticMethod.IsAbstract && !semanticMethod.ContainingType.IsInterface)
                {
                    toolTip = String.Format("Contracts inherited from {0}.", inheritedFromMethod.ContainingType.Name.Text);
                }
                #endregion
                #region Try get method contracts and update adornment
                IMethodContract contracts = null;
                if (((ContractsProvider)@this._textViewTracker.ProjectTracker.ContractsProvider).TryGetMethodContract(inheritedFromMethod, out contracts))
                {
                    var possibleAdornment = @this._adornmentManager.GetAdornment(tag);
                    if (possibleAdornment != null)
                    {
                        var adornment = possibleAdornment as ContractAdornment;
                        if (adornment != null)
                        {
                            adornment.SetContracts(contracts, toolTip);
                        }
                        else
                        {
                            ContractsPackageAccessor.Current.Logger.WriteToLog("Placeholder adornment isn't a ContractAdornment (not good!), skipping method...");
                        }
                    }
                    else
                    {
                        ContractsPackageAccessor.Current.Logger.WriteToLog("Placeholder adornment not found, skipping method...");
                    }
                }
                #endregion
            }
            #region Exception handeling
            catch (IllFormedSemanticModelException e) {
                if (@this.trackingNumberOfFetchedSemanticModels && @this.semanticModelsFetchedCounter <= 2)
                {
                    ContractsPackageAccessor.Current.Logger.WriteToLog("Error: An 'IllFormedSemanticModelException' occured: '" + e.Message + "' Asking for a new semantic model...");
                    @this._textViewTracker.IsLatestCompilationStale = true;
                    ContractsPackageAccessor.Current.AskForNewVSModel();
                    @this.semanticModelsFetchedCounter++;
                    goto RequeueAndAbort;
                }
                else
                {
                    ContractsPackageAccessor.Current.Logger.WriteToLog("An 'IllFormedSemanticModelException' occured: '" + e.Message + "' Too many semantic models have been fetched, skipping this method...");
                    goto Continue;
                }
            } catch (InvalidOperationException e) {
                if (e.Message.Contains(ContractsPackageAccessor.InvalidOperationExceptionMessage_TheSnapshotIsOutOfDate))
                {
                    if (@this.trackingNumberOfFetchedSemanticModels && @this.semanticModelsFetchedCounter <= 5)
                    {
                        ContractsPackageAccessor.Current.Logger.WriteToLog("The Visual Studio Semantic/Syntactic model threw an exception (it's snapshot is out of date) while looking up contracts, getting new compilation...");
                        @this._textViewTracker.IsLatestCompilationStale = true;
                        ContractsPackageAccessor.Current.AskForNewVSModel();
                        @this.semanticModelsFetchedCounter++;
                        goto RequeueAndAbort;
                    }
                    else
                    {
                        ContractsPackageAccessor.Current.Logger.WriteToLog("The Visual Studio Semantic/Syntactic model threw an exception (it's snapshot is out of date) while looking up contracts. Too many compilations have already been fetched, skipping this method...");
                        goto Continue;
                    }
                }
                else
                {
                    throw e;
                }
            } catch (COMException e) {
                if (e.Message.Contains(ContractsPackageAccessor.COMExceptionMessage_BindingFailed))
                {
                    if (@this.trackingNumberOfFetchedSemanticModels && @this.semanticModelsFetchedCounter <= 5)
                    {
                        ContractsPackageAccessor.Current.Logger.WriteToLog("The Visual Studio Semantic/Syntactic model threw an exception (it's snapshot is out of date) while looking up contracts, getting new compilation...");
                        @this._textViewTracker.IsLatestCompilationStale = true;
                        ContractsPackageAccessor.Current.AskForNewVSModel();
                        @this.semanticModelsFetchedCounter++;
                        goto RequeueAndAbort;
                    }
                    else
                    {
                        ContractsPackageAccessor.Current.Logger.WriteToLog("The Visual Studio Semantic/Syntactic model threw an exception (it's snapshot is out of date) while looking up contracts. Too many compilations have already been fetched, skipping this method...");
                        goto Continue;
                    }
                }
                else
                {
                    throw e;
                }
            }
            #endregion
Continue:
            ContractsPackageAccessor.Current.QueueWorkItem(() => RecursivelyLookupContractsForMethods(@this));
            return;

RequeueAndAbort:
            @this._methodsNeedingContractLookup.Enqueue(methodPair);
            return;
        }
예제 #54
0
 /// <summary>
 /// Associates the given object with the given method contract.
 /// If the object is already associated with a method contract, that association will be lost as a result of this call.
 /// </summary>
 /// <param name="contract">The contract to associate with method.</param>
 /// <param name="method">An object to associate with the method contract. This can be any kind of object.</param>
 public void AssociateMethodWithContract(object method, IMethodContract contract) {
   lock (this.methodContractFor) {
     this.methodContractFor[method] = contract;
   }
 }
예제 #55
0
        /// <summary>
        /// Returns the method contract, if any, that has been associated with the given object. Returns null if no association exits.
        /// </summary>
        /// <param name="method">An object that might have been associated with a method contract. This can be any kind of object.</param>
        /// <returns></returns>
        public IMethodContract /*?*/ GetMethodContractFor(object method)
        {
            if (this.methodsBeingExtracted.Contains(method))
            {
                // hit a cycle while chasing validators/abbreviators
                // TODO: signal error
                return(null);
            }
            else
            {
                this.methodsBeingExtracted.Add(method);
            }

            try {
                IMethodContract contract = this.underlyingContractProvider.GetMethodContractFor(method);
                if (contract != null)
                {
                    return(contract == ContractDummy.MethodContract ? null : contract);
                }

                MethodContract  result          = new MethodContract();
                IMethodContract primaryContract = null;
                if (this.oobExtractors == null)
                {
                    primaryContract = this.primaryExtractor.GetMethodContractFor(method);
                }
                bool found = false;
                if (primaryContract != null)
                {
                    found = true;
                    Microsoft.Cci.MutableContracts.ContractHelper.AddMethodContract(result, primaryContract);
                }
                if (this.oobExtractors != null)
                {
                    foreach (var oobProvider in this.oobExtractors)
                    {
                        IMethodReference methodReference = method as IMethodReference;
                        if (methodReference == null)
                        {
                            continue;              // REVIEW: Is there anything else it could be and still find a contract for it?
                        }
                        MappingMutator primaryToOobMapper = this.mapperForPrimaryToOob[oobProvider];
                        var            oobMethod          = primaryToOobMapper.Map(methodReference);

                        if (oobMethod == null)
                        {
                            continue;
                        }

                        var oobContract = oobProvider.GetMethodContractFor(oobMethod);

                        if (oobContract == null)
                        {
                            continue;
                        }

                        MappingMutator oobToPrimaryMapper = this.mapperForOobToPrimary[oobProvider];
                        oobContract = oobToPrimaryMapper.Map(oobContract);

                        var sps = new Microsoft.Cci.MutableContracts.SubstituteParameters(this.host, oobMethod.ResolvedMethod, methodReference.ResolvedMethod);
                        oobContract = sps.Rewrite(oobContract);

                        Microsoft.Cci.MutableContracts.ContractHelper.AddMethodContract(result, oobContract);
                        found = true;
                    }
                }

                // always cache so we don't try to extract more than once
                if (found)
                {
                    this.underlyingContractProvider.AssociateMethodWithContract(method, result);
                }
                else
                {
                    this.underlyingContractProvider.AssociateMethodWithContract(method, ContractDummy.MethodContract);
                    result = null;
                }
                return(result);
            } finally {
                this.methodsBeingExtracted.RemoveAt(this.methodsBeingExtracted.Count - 1);
            }
        }
    public static string FormatContracts(IMethodContract methodContracts) {

      //Did we get proper contracts?
      if (methodContracts == null) {

        //Return a message saying we failed to get contracts
        return "(Failed to properly get contracts)";
      }

      //Do we have any contracts?
      if (IsEmptyContract(methodContracts))
      {
        //Return a message saying we don't have any contracts
        return null;
      }

      //Initialize our string builder
      var sb = new StringBuilder();

      //Append the 'Contracts' header
      sb.Append("Contracts: ");
      sb.Append('\n');

      //Append purity
      if (methodContracts.IsPure) {
        sb.Append("    ");
        sb.Append("[Pure]");
        sb.Append('\n');
      }

      FormatPrePostThrows(methodContracts, sb);

      //Can we get our result from the string builder?
      var result = sb.ToString();

      //Trim the new lines from the end
      result = result.TrimEnd('\n');

      result = SmartFormat(result);

      //Return our result
      return result;
    }
예제 #57
0
 /// <summary>
 /// Constructs a pair from the arguments.
 /// </summary>
 public MethodContractAndMethodBody(IMethodContract/*?*/ methodContract, IBlockStatement/*?*/ blockStatement) {
   this.methodContract = methodContract;
   this.blockStatement = blockStatement;
 }
    private static bool IsEmptyContract(IMethodContract methodContracts)
    {
      Contract.Ensures(Contract.Result<bool>() || methodContracts != null);

      return methodContracts == null
              || (methodContracts == ContractDummy.MethodContract)
              || (!methodContracts.IsPure
                  && methodContracts.Preconditions.Count() < 1
                  && methodContracts.Postconditions.Count() < 1
                  && methodContracts.ThrownExceptions.Count() < 1);
    }
예제 #59
0
 /// <summary>
 /// Wraps a call to GetMethodContractFor inside of a try-catch statement.
 /// </summary>
 public static bool TryGetMethodContract(CodeContractAwareHostEnvironment host, IMethodReference method, out IMethodContract methodContract, DocTracker docTracker) {
   Contract.Requires(host != null);
   Contract.Requires(method != null);
   Contract.Ensures(!Contract.Result<bool>() || Contract.ValueAtReturn(out methodContract) != null);
   try {
     methodContract = ContractHelper.GetMethodContractFor(host, method.ResolvedMethod);
   } catch (NullReferenceException) {
     docTracker.WriteLine("ERROR: NullReferenceException was thrown in CCI!");
     methodContract = null;
   }
   //} catch (Exception e) {
   //  docTracker.WriteLine("ERROR: Exception of type '{0}' was thrown in CCI!", e.GetType().Name);
   //  docTracker.WriteLine("\t'{0}'", e.Message);
   //  methodContract = null;
   //}
   return methodContract != null;
 }
    private static void FormatPrePostThrows(IMethodContract methodContracts, StringBuilder sb)
    {
      Contract.Requires(methodContracts != null);
      Contract.Requires(sb != null);

      if (methodContracts.Postconditions != null)
      {
          //Append our preconditions
          foreach (var pre in methodContracts.Preconditions)
          {
              if (pre == null) continue;
              if (pre.OriginalSource == null) continue;
              sb.Append("    ");
              sb.Append("requires ");
              sb.Append(pre.OriginalSource.Replace(Environment.NewLine, IndentString));
              sb.Append('\n');
          }
      }

      if (methodContracts.Postconditions != null)
      {
          //Append our postconditions
          foreach (var post in methodContracts.Postconditions)
          {
              if (post == null) continue;
              if (post.OriginalSource == null) continue;
              sb.Append("    ");
              sb.Append("ensures ");
              sb.Append(post.OriginalSource.Replace(Environment.NewLine, IndentString));
              sb.Append('\n');
          }
      }

      if (methodContracts.ThrownExceptions != null)
      {
          //Append our on throw conditions
          foreach (var onThrow in methodContracts.ThrownExceptions)
          {
              if (onThrow == null) continue;
              if (onThrow.ExceptionType == null) continue;
              if (onThrow.Postcondition == null) continue;
              if (onThrow.Postcondition.OriginalSource == null) continue;

              sb.Append("    ");
              sb.Append("ensures on throw of ");
              var onThrowType = TypeHelper.GetTypeName(onThrow.ExceptionType, NameFormattingOptions.OmitContainingType | NameFormattingOptions.OmitContainingNamespace);
              sb.Append(onThrowType);
              sb.Append(" that ");
              sb.Append(onThrow.Postcondition.OriginalSource.Replace(Environment.NewLine, IndentString));
              sb.Append('\n');
          }
      }
    }