private IEnumerable<ITypeSymbol> InferTypeForReturnStatement(ReturnStatementSyntax returnStatement, SyntaxToken? previousToken = null)
            {
                // If we are position based, then we have to be after the return statement.
                if (previousToken.HasValue && previousToken.Value != returnStatement.ReturnKeyword)
                {
                    return SpecializedCollections.EmptyEnumerable<ITypeSymbol>();
                }

                var ancestorExpressions = returnStatement.GetAncestorsOrThis<ExpressionSyntax>();

                // If we're in a lambda, then use the return type of the lambda to figure out what to
                // infer.  i.e.   Func<int,string> f = i => { return Foo(); }
                var lambda = ancestorExpressions.FirstOrDefault(e => e.IsKind(SyntaxKind.ParenthesizedLambdaExpression, SyntaxKind.SimpleLambdaExpression));
                if (lambda != null)
                {
                    return InferTypeInLambdaExpression(lambda);
                }

                // If we are inside a delegate then use the return type of the Invoke Method of the delegate type
                var delegateExpression = ancestorExpressions.FirstOrDefault(e => e.IsKind(SyntaxKind.AnonymousMethodExpression));
                if (delegateExpression != null)
                {
                    var delegateType = InferTypesWorker(delegateExpression).FirstOrDefault();
                    if (delegateType != null && delegateType.IsDelegateType())
                    {
                        var delegateInvokeMethod = delegateType.GetDelegateType(this.Compilation).DelegateInvokeMethod;
                        if (delegateInvokeMethod != null)
                        {
                            return SpecializedCollections.SingletonEnumerable(delegateInvokeMethod.ReturnType);
                        }
                    }
                }

                var memberSymbol = GetDeclaredMemberSymbolFromOriginalSemanticModel(this.semanticModel, returnStatement.GetAncestorOrThis<MemberDeclarationSyntax>());

                if (memberSymbol.IsKind(SymbolKind.Method))
                {
                    var method = memberSymbol as IMethodSymbol;
                    if (method.IsAsync)
                    {
                        var typeArguments = method.ReturnType.GetTypeArguments();
                        var taskOfT = this.Compilation.TaskOfTType();

                        return taskOfT != null && method.ReturnType.OriginalDefinition == taskOfT && typeArguments.Any()
                            ? SpecializedCollections.SingletonEnumerable(typeArguments.First())
                            : SpecializedCollections.EmptyEnumerable<ITypeSymbol>();
                    }
                    else
                    {
                        return SpecializedCollections.SingletonEnumerable(method.ReturnType);
                    }
                }
                else if (memberSymbol.IsKind(SymbolKind.Property))
                {
                    return SpecializedCollections.SingletonEnumerable((memberSymbol as IPropertySymbol).Type);
                }
                else if (memberSymbol.IsKind(SymbolKind.Field))
                {
                    return SpecializedCollections.SingletonEnumerable((memberSymbol as IFieldSymbol).Type);
                }

                return SpecializedCollections.EmptyEnumerable<ITypeSymbol>();
            }
            private void InferTypeForReturnStatement(
                ReturnStatementSyntax returnStatement, SyntaxToken? previousToken, out bool isAsync, out IEnumerable<ITypeSymbol> types)
            {
                isAsync = false;
                types = SpecializedCollections.EmptyEnumerable<ITypeSymbol>();

                // If we are position based, then we have to be after the return statement.
                if (previousToken.HasValue && previousToken.Value != returnStatement.ReturnKeyword)
                {
                    return;
                }

                var ancestorExpressions = returnStatement.GetAncestorsOrThis<ExpressionSyntax>();

                // If we're in a lambda, then use the return type of the lambda to figure out what to
                // infer.  i.e.   Func<int,string> f = i => { return Foo(); }
                var lambda = ancestorExpressions.FirstOrDefault(e => e.IsKind(SyntaxKind.ParenthesizedLambdaExpression, SyntaxKind.SimpleLambdaExpression));
                if (lambda != null)
                {
                    types= InferTypeInLambdaExpression(lambda);
                    isAsync = lambda is ParenthesizedLambdaExpressionSyntax && ((ParenthesizedLambdaExpressionSyntax)lambda).AsyncKeyword.Kind() != SyntaxKind.None;
                    return;
                }

                // If we are inside a delegate then use the return type of the Invoke Method of the delegate type
                var delegateExpression = (AnonymousMethodExpressionSyntax)ancestorExpressions.FirstOrDefault(e => e.IsKind(SyntaxKind.AnonymousMethodExpression));
                if (delegateExpression != null)
                {
                    var delegateType = InferTypes(delegateExpression).FirstOrDefault();
                    if (delegateType != null && delegateType.IsDelegateType())
                    {
                        var delegateInvokeMethod = delegateType.GetDelegateType(this.Compilation).DelegateInvokeMethod;
                        if (delegateInvokeMethod != null)
                        {
                            types = SpecializedCollections.SingletonEnumerable(delegateInvokeMethod.ReturnType);
                            isAsync = delegateExpression.AsyncKeyword.Kind() != SyntaxKind.None;
                            return;
                        }
                    }
                }

                var memberSymbol = GetDeclaredMemberSymbolFromOriginalSemanticModel(SemanticModel, returnStatement.GetAncestorOrThis<MemberDeclarationSyntax>());

                if (memberSymbol.IsKind(SymbolKind.Method))
                {
                    var method = memberSymbol as IMethodSymbol;

                    isAsync = method.IsAsync;
                    types = SpecializedCollections.SingletonEnumerable(method.ReturnType);
                    return;
                }
                else if (memberSymbol.IsKind(SymbolKind.Property))
                {
                    types = SpecializedCollections.SingletonEnumerable((memberSymbol as IPropertySymbol).Type);
                    return;
                }
                else if (memberSymbol.IsKind(SymbolKind.Field))
                {
                    types = SpecializedCollections.SingletonEnumerable((memberSymbol as IFieldSymbol).Type);
                    return;
                }
            }