public ExpandableStringExpressionAst(IScriptExtent extent, string value, System.Management.Automation.Language.StringConstantType type) : base(extent)
        {
            if (value == null)
            {
                throw PSTraceSource.NewArgumentNullException("value");
            }
            if (((type != System.Management.Automation.Language.StringConstantType.DoubleQuoted) && (type != System.Management.Automation.Language.StringConstantType.DoubleQuotedHereString)) && (type != System.Management.Automation.Language.StringConstantType.BareWord))
            {
                throw PSTraceSource.NewArgumentException("type");
            }
            ExpressionAst ast = Parser.ScanString(value);
            ExpandableStringExpressionAst ast2 = ast as ExpandableStringExpressionAst;

            if (ast2 != null)
            {
                this.FormatExpression  = ast2.FormatExpression;
                this.NestedExpressions = ast2.NestedExpressions;
            }
            else
            {
                this.FormatExpression  = "{0}";
                this.NestedExpressions = new ReadOnlyCollection <ExpressionAst>(new ExpressionAst[] { ast });
            }
            this.Value = value;
            this.StringConstantType = type;
        }
 public object VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst)
 {
     foreach (ExpressionAst ast in expandableStringExpressionAst.NestedExpressions)
     {
         ast.Accept(this);
     }
     return(null);
 }
 public object VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst)
 {
     bool isSafe = true;
     foreach (var nestedExpression in expandableStringExpressionAst.NestedExpressions)
     {
         _visitCount++;
         if (!(bool)nestedExpression.Accept(this))
         {
             isSafe = false;
             break;
         }
     }
     return isSafe;
 }
Exemple #4
0
 public override AstVisitAction VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst)
 {
     throw new NotImplementedException(); //VisitExpandableStringExpression(expandableStringExpressionAst);
 }
Exemple #5
0
        public override AstVisitAction VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst)
        {
            var evaluatedExpressions = from expressionAst in expandableStringExpressionAst.NestedExpressions
                                       select EvaluateAst(expressionAst);

            string expandedString = expandableStringExpressionAst.ExpandString(evaluatedExpressions);
            this._pipelineCommandRuntime.OutputStream.Write(expandedString);
            return AstVisitAction.SkipChildren;
        }
        /// <summary>
        /// Visit Expandable String Expression
        /// </summary>
        /// <param name="expandableStringExpressionAst"></param>
        /// <returns></returns>
        public object VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst)
        {
            if (expandableStringExpressionAst == null) return null;

            foreach (var expr in expandableStringExpressionAst.NestedExpressions)
            {
                expr.Visit(this.Decorator);
            }
            return null;
        }
        private List<CompletionResult> GetResultForIdentifier(CompletionContext completionContext, ref int replacementIndex, ref int replacementLength, bool isQuotedString)
        {
            var tokenAtCursor = completionContext.TokenAtCursor;
            var lastAst = completionContext.RelatedAsts.Last();

            List<CompletionResult> result = null;
            completionContext.WordToComplete = tokenAtCursor.Text;

            var strConst = lastAst as StringConstantExpressionAst;
            if (strConst != null)
            {
                if (strConst.Value.Equals("$", StringComparison.Ordinal))
                {
                    completionContext.WordToComplete = "";
                    return CompletionCompleters.CompleteVariable(completionContext);
                }
                else
                {
                    UsingStatementAst usingState = strConst.Parent as UsingStatementAst;
                    if (usingState != null)
                    {
                        completionContext.ReplacementIndex = strConst.Extent.StartOffset;
                        completionContext.ReplacementLength = strConst.Extent.EndOffset - replacementIndex;
                        completionContext.WordToComplete = strConst.Extent.Text;
                        switch (usingState.UsingStatementKind)
                        {
                            case UsingStatementKind.Assembly:
                                break;
                            case UsingStatementKind.Command:
                                break;
                            case UsingStatementKind.Module:
                                var moduleExtensions = new HashSet<string>(StringComparer.OrdinalIgnoreCase)
                                {
                                    StringLiterals.PowerShellModuleFileExtension,
                                    StringLiterals.PowerShellDataFileExtension,
                                    StringLiterals.PowerShellNgenAssemblyExtension,
                                    StringLiterals.DependentWorkflowAssemblyExtension,
                                    StringLiterals.PowerShellCmdletizationFileExtension,
                                    StringLiterals.WorkflowFileExtension
                                };
                                result = CompletionCompleters.CompleteFilename(completionContext, false, moduleExtensions).ToList();
                                if (completionContext.WordToComplete.IndexOfAny(Utils.Separators.DirectoryOrDrive) != -1)
                                {
                                    // The partial input is a path, then we don't iterate modules under $ENV:PSModulePath
                                    return result;
                                }

                                var moduleResults = CompletionCompleters.CompleteModuleName(completionContext, false);
                                if (moduleResults != null && moduleResults.Count > 0)
                                    result.AddRange(moduleResults);
                                return result;
                            case UsingStatementKind.Namespace:
                                result = CompletionCompleters.CompleteNamespace(completionContext);
                                return result;
                            case UsingStatementKind.Type:
                                break;
                            default:
                                throw new ArgumentOutOfRangeException("UsingStatementKind");
                        }
                    }
                }
            }
            result = GetResultForAttributeArgument(completionContext, ref replacementIndex, ref replacementLength);
            if (result != null) return result;

            if ((tokenAtCursor.TokenFlags & TokenFlags.CommandName) != 0)
            {
                // Handle completion for a path with variable, such as: $PSHOME\ty<tab>
                if (completionContext.RelatedAsts.Count > 0 && completionContext.RelatedAsts[0] is ScriptBlockAst)
                {
                    Ast cursorAst = null;
                    var cursorPosition = (InternalScriptPosition)_cursorPosition;
                    int offsetBeforeCmdName = cursorPosition.Offset - tokenAtCursor.Text.Length;
                    if (offsetBeforeCmdName >= 0)
                    {
                        var cursorBeforeCmdName = cursorPosition.CloneWithNewOffset(offsetBeforeCmdName);
                        var scriptBlockAst = (ScriptBlockAst)completionContext.RelatedAsts[0];
                        cursorAst = GetLastAstAtCursor(scriptBlockAst, cursorBeforeCmdName);
                    }

                    if (cursorAst != null &&
                        cursorAst.Extent.EndLineNumber == tokenAtCursor.Extent.StartLineNumber &&
                        cursorAst.Extent.EndColumnNumber == tokenAtCursor.Extent.StartColumnNumber)
                    {
                        if (tokenAtCursor.Text.IndexOfAny(Utils.Separators.Directory) == 0)
                        {
                            string wordToComplete =
                                CompletionCompleters.ConcatenateStringPathArguments(cursorAst as CommandElementAst, tokenAtCursor.Text, completionContext);
                            if (wordToComplete != null)
                            {
                                completionContext.WordToComplete = wordToComplete;
                                result = new List<CompletionResult>(CompletionCompleters.CompleteFilename(completionContext));
                                if (result.Count > 0)
                                {
                                    replacementIndex = cursorAst.Extent.StartScriptPosition.Offset;
                                    replacementLength += cursorAst.Extent.Text.Length;
                                }
                                return result;
                            }
                            else
                            {
                                var variableAst = cursorAst as VariableExpressionAst;
                                string fullPath = variableAst != null
                                    ? CompletionCompleters.CombineVariableWithPartialPath(
                                        variableAst: variableAst,
                                        extraText: tokenAtCursor.Text,
                                        executionContext: completionContext.ExecutionContext)
                                    : null;

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

                                // Continue trying the filename/commandname completion for scenarios like this: $aa\d<tab>
                                completionContext.WordToComplete = fullPath;
                                replacementIndex = cursorAst.Extent.StartScriptPosition.Offset;
                                replacementLength += cursorAst.Extent.Text.Length;

                                completionContext.ReplacementIndex = replacementIndex;
                                completionContext.ReplacementLength = replacementLength;
                            }
                        }
                        // Continue trying the filename/commandname completion for scenarios like this: $aa[get-<tab>
                        else if (!(cursorAst is ErrorExpressionAst && cursorAst.Parent is IndexExpressionAst))
                        {
                            return result;
                        }
                    }
                }

                // When it's the content of a quoted string, we only handle variable/member completion
                if (isQuotedString) { return result; }

                // Handle the StringExpandableToken;
                var strToken = tokenAtCursor as StringExpandableToken;
                if (strToken != null && strToken.NestedTokens != null && strConst != null)
                {
                    try
                    {
                        string expandedString = null;
                        var expandableStringAst = new ExpandableStringExpressionAst(strConst.Extent, strConst.Value, StringConstantType.BareWord);
                        if (CompletionCompleters.IsPathSafelyExpandable(expandableStringAst: expandableStringAst,
                                                                        extraText: String.Empty,
                                                                        executionContext: completionContext.ExecutionContext,
                                                                        expandedString: out expandedString))
                        {
                            completionContext.WordToComplete = expandedString;
                        }
                        else
                        {
                            return result;
                        }
                    }
                    catch (Exception e)
                    {
                        CommandProcessorBase.CheckForSevereException(e);
                        return result;
                    }
                }

                //
                // Handle completion of DSC resources within Configuration
                //
                DynamicKeywordStatementAst keywordAst;
                ConfigurationDefinitionAst configureAst = GetAncestorConfigurationAstAndKeywordAst(completionContext.CursorPosition, lastAst, out keywordAst);
                bool matched = false;
                List<CompletionResult> keywordResult = null;
                if (configureAst != null)
                {
                    // Current token is within ConfigurationDefinitionAst or DynamicKeywordStatementAst
                    keywordResult = GetResultForIdentifierInConfiguration(completionContext, configureAst, keywordAst, out matched);
                }

                // Handle the file completion before command name completion
                result = CompleteFileNameAsCommand(completionContext);
                // Handle the command name completion
                var commandNameResult = CompletionCompleters.CompleteCommand(completionContext);

                if (commandNameResult != null && commandNameResult.Count > 0)
                {
                    result.AddRange(commandNameResult);
                }

                if (matched && keywordResult != null)
                {
                    result.InsertRange(0, keywordResult);
                }
                else if (!matched && keywordResult != null && commandNameResult.Count == 0)
                {
                    result.AddRange(keywordResult);
                }
                return result;
            }

            if (tokenAtCursor.Text.Length == 1 && tokenAtCursor.Text[0].IsDash() && (lastAst.Parent is CommandAst || lastAst.Parent is DynamicKeywordStatementAst))
            {
                // When it's the content of a quoted string, we only handle variable/member completion
                if (isQuotedString) { return result; }
                return CompletionCompleters.CompleteCommandParameter(completionContext);
            }

            TokenKind memberOperator = TokenKind.Unknown;
            bool isMemberCompletion = (lastAst.Parent is MemberExpressionAst);
            bool isStatic = isMemberCompletion ? ((MemberExpressionAst)lastAst.Parent).Static : false;
            bool isWildcard = false;

            if (!isMemberCompletion)
            {
                // Still might be member completion, something like: echo $member.
                // We need to know if the previous element before the token is adjacent because
                // we don't have a MemberExpressionAst, we might have 2 command arguments.

                if (tokenAtCursor.Text.Equals(TokenKind.Dot.Text(), StringComparison.Ordinal))
                {
                    memberOperator = TokenKind.Dot;
                    isMemberCompletion = true;
                }
                else if (tokenAtCursor.Text.Equals(TokenKind.ColonColon.Text(), StringComparison.Ordinal))
                {
                    memberOperator = TokenKind.ColonColon;
                    isMemberCompletion = true;
                }
                else if (tokenAtCursor.Kind.Equals(TokenKind.Multiply) && lastAst is BinaryExpressionAst)
                {
                    // Handle member completion with wildcard(wildcard is at the end): $a.p*
                    var binaryExpressionAst = (BinaryExpressionAst)lastAst;
                    var memberExpressionAst = binaryExpressionAst.Left as MemberExpressionAst;
                    var errorPosition = binaryExpressionAst.ErrorPosition;

                    if (memberExpressionAst != null && binaryExpressionAst.Operator == TokenKind.Multiply &&
                        errorPosition.StartOffset == memberExpressionAst.Member.Extent.EndOffset)
                    {
                        isStatic = memberExpressionAst.Static;
                        memberOperator = isStatic ? TokenKind.ColonColon : TokenKind.Dot;
                        isMemberCompletion = true;
                        isWildcard = true;

                        // Member completion will add back the '*', so pretend it wasn't there, at least from the "related asts" point of view,
                        // but add the member expression that we are really completing.
                        completionContext.RelatedAsts.Remove(binaryExpressionAst);
                        completionContext.RelatedAsts.Add(memberExpressionAst);

                        var memberAst = memberExpressionAst.Member as StringConstantExpressionAst;
                        if (memberAst != null)
                        {
                            replacementIndex = memberAst.Extent.StartScriptPosition.Offset;
                            replacementLength += memberAst.Extent.Text.Length;
                        }
                    }
                }
            }

            if (isMemberCompletion)
            {
                result = CompletionCompleters.CompleteMember(completionContext, @static: (isStatic || memberOperator == TokenKind.ColonColon));

                // If the last token was just a '.', we tried to complete members.  That may
                // have failed because it wasn't really an attempt to complete a member, in
                // which case we should try to complete as an argument.
                if (result.Any())
                {
                    if (!isWildcard && memberOperator != TokenKind.Unknown)
                    {
                        replacementIndex += tokenAtCursor.Text.Length;
                        replacementLength = 0;
                    }
                    return result;
                }
            }

            if (lastAst.Parent is HashtableAst)
            {
                result = CompletionCompleters.CompleteHashtableKey(completionContext, (HashtableAst)lastAst.Parent);
                if (result != null && result.Any())
                {
                    return result;
                }
            }

            // When it's the content of a quoted string, we only handle variable/member completion
            if (isQuotedString) { return result; }

            bool needFileCompletion = false;
            if (lastAst.Parent is FileRedirectionAst || CompleteAgainstSwitchFile(lastAst, completionContext.TokenBeforeCursor))
            {
                string wordToComplete =
                    CompletionCompleters.ConcatenateStringPathArguments(lastAst as CommandElementAst, String.Empty, completionContext);
                if (wordToComplete != null)
                {
                    needFileCompletion = true;
                    completionContext.WordToComplete = wordToComplete;
                }
            }
            else if (tokenAtCursor.Text.IndexOfAny(Utils.Separators.Directory) == 0)
            {
                var command = lastAst.Parent as CommandBaseAst;
                if (command != null && command.Redirections.Any())
                {
                    var fileRedirection = command.Redirections[0] as FileRedirectionAst;
                    if (fileRedirection != null &&
                        fileRedirection.Extent.EndLineNumber == lastAst.Extent.StartLineNumber &&
                        fileRedirection.Extent.EndColumnNumber == lastAst.Extent.StartColumnNumber)
                    {
                        string wordToComplete =
                            CompletionCompleters.ConcatenateStringPathArguments(fileRedirection.Location, tokenAtCursor.Text, completionContext);

                        if (wordToComplete != null)
                        {
                            needFileCompletion = true;
                            completionContext.WordToComplete = wordToComplete;
                            replacementIndex = fileRedirection.Location.Extent.StartScriptPosition.Offset;
                            replacementLength += fileRedirection.Location.Extent.EndScriptPosition.Offset - replacementIndex;

                            completionContext.ReplacementIndex = replacementIndex;
                            completionContext.ReplacementLength = replacementLength;
                        }
                    }
                }
            }

            if (needFileCompletion)
            {
                return new List<CompletionResult>(CompletionCompleters.CompleteFilename(completionContext));
            }
            else
            {
                string wordToComplete =
                    CompletionCompleters.ConcatenateStringPathArguments(lastAst as CommandElementAst, String.Empty, completionContext);
                if (wordToComplete != null)
                {
                    completionContext.WordToComplete = wordToComplete;
                }
            }

            result = CompletionCompleters.CompleteCommandArgument(completionContext);
            replacementIndex = completionContext.ReplacementIndex;
            replacementLength = completionContext.ReplacementLength;
            return result;
        }
Exemple #8
0
 public override AstVisitAction VisitExpandableStringExpression(ExpandableStringExpressionAst ast) { return CheckParent(ast); }
Exemple #9
0
 /// <summary/>
 public virtual AstVisitAction VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst)
 {
     return(AstVisitAction.Continue);
 }
Exemple #10
0
        private ExpressionAst GetCommandArgument(CommandArgumentContext context, Token token)
        {
            ExpressionAst ast;
            List<ExpressionAst> source = null;
            Token token2 = null;
            bool flag = false;
        Label_0006:
            switch (token.Kind)
            {
                case TokenKind.Variable:
                case TokenKind.SplattedVariable:
                case TokenKind.Number:
                case TokenKind.StringLiteral:
                case TokenKind.StringExpandable:
                case TokenKind.HereStringLiteral:
                case TokenKind.HereStringExpandable:
                case TokenKind.LParen:
                case TokenKind.LCurly:
                case TokenKind.AtParen:
                case TokenKind.AtCurly:
                case TokenKind.DollarParen:
                    this.UngetToken(token);
                    ast = this.PrimaryExpressionRule(true);
                    break;

                case TokenKind.Generic:
                    {
                        if ((context & CommandArgumentContext.CommandName) != 0)
                        {
                            token.TokenFlags |= TokenFlags.CommandName;
                        }
                        StringToken token3 = (StringToken)token;
                        StringExpandableToken expandableStringToken = token3 as StringExpandableToken;
                        if ((expandableStringToken != null) && (context != CommandArgumentContext.CommandName))
                        {
                            List<ExpressionAst> nestedExpressions = this.ParseNestedExpressions(expandableStringToken);
                            ast = new ExpandableStringExpressionAst(expandableStringToken, expandableStringToken.Value, expandableStringToken.FormatString, nestedExpressions);
                        }
                        else
                        {
                            ast = new StringConstantExpressionAst(token3.Extent, token3.Value, StringConstantType.BareWord);
                            if (string.Equals(token3.Value, "--%", StringComparison.OrdinalIgnoreCase))
                            {
                                flag = true;
                            }
                        }
                        break;
                    }
                case TokenKind.NewLine:
                case TokenKind.EndOfInput:
                case TokenKind.RParen:
                case TokenKind.RCurly:
                case TokenKind.Semi:
                case TokenKind.AndAnd:
                case TokenKind.OrOr:
                case TokenKind.Ampersand:
                case TokenKind.Pipe:
                case TokenKind.Comma:
                case TokenKind.MinusMinus:
                case TokenKind.Redirection:
                case TokenKind.RedirectInStd:
                    this.UngetToken(token);
                    if (token2 != null)
                    {
                        this.ReportIncompleteInput(After(token2), ParserStrings.MissingExpression, new object[] { "," });
                        return new ErrorExpressionAst(ExtentOf(source.First<ExpressionAst>(), token2), (IEnumerable<Ast>)source);
                    }
                    return null;

                default:
                    ast = new StringConstantExpressionAst(token.Extent, token.Text, StringConstantType.BareWord);
                    switch (context)
                    {
                        case CommandArgumentContext.CommandName:
                        case CommandArgumentContext.CommandNameAfterInvocationOperator:
                            token.TokenFlags |= TokenFlags.CommandName;
                            break;

                        case CommandArgumentContext.FileName:
                        case CommandArgumentContext.CommandArgument:
                        case CommandArgumentContext.SwitchCondition:
                            token.SetIsCommandArgument();
                            break;
                    }
                    break;
            }
            if ((context == CommandArgumentContext.CommandArgument) && !flag)
            {
                token = this.PeekToken();
                if (token.Kind == TokenKind.Comma)
                {
                    token2 = token;
                    if (source == null)
                    {
                        source = new List<ExpressionAst>();
                    }
                    source.Add(ast);
                    this.SkipToken();
                    this.SkipNewlines();
                    token = this.NextToken();
                    goto Label_0006;
                }
            }
            if (source != null)
            {
                source.Add(ast);
                return new ArrayLiteralAst(ExtentOf(source.First<ExpressionAst>(), source.Last<ExpressionAst>()), source);
            }
            return ast;
        }
Exemple #11
0
 private ExpressionAst ExpandableStringRule(StringExpandableToken strToken)
 {
     ExpressionAst stringConstantExpressionAst;
     if (strToken.NestedTokens == null)
     {
         stringConstantExpressionAst = new StringConstantExpressionAst(strToken);
     }
     else
     {
         List<ExpressionAst> expressionAsts = this.ParseNestedExpressions(strToken);
         stringConstantExpressionAst = new ExpandableStringExpressionAst(strToken, strToken.Value, strToken.FormatString, expressionAsts);
     }
     return stringConstantExpressionAst;
 }
Exemple #12
0
        private ExpressionAst ExpandableStringRule(StringExpandableToken strToken)
        {
            //G  value:
            //G      literal

            ExpressionAst expr;
            // We need to scan the nested tokens even if there was some error. This is used by the tab completion: "pshome is $psh<tab>
            if (strToken.NestedTokens != null)
            {
                List<ExpressionAst> nestedExpressions = ParseNestedExpressions(strToken);
                expr = new ExpandableStringExpressionAst(strToken, strToken.Value, strToken.FormatString, nestedExpressions);
            }
            else
            {
                expr = new StringConstantExpressionAst(strToken);
            }
            return expr;
        }
Exemple #13
0
        private ExpressionAst GetCommandArgument(CommandArgumentContext context, Token token)
        {
            Diagnostics.Assert(token.Kind != TokenKind.Comma, "A unary comma is an error in command mode, and should have already been reported.");
            ExpressionAst exprAst;
            List<ExpressionAst> commandArgs = null;
            Token commaToken = null;
            bool foundVerbatimArgument = false;

            while (true)
            {
                switch (token.Kind)
                {
                    // The following tokens are never allowed as command arguments.
                    case TokenKind.Pipe:
                    case TokenKind.RCurly:
                    case TokenKind.RParen:
                    case TokenKind.EndOfInput:
                    case TokenKind.NewLine:
                    case TokenKind.Semi:
                    case TokenKind.Redirection:
                    case TokenKind.RedirectInStd:
                    case TokenKind.AndAnd:
                    case TokenKind.OrOr:
                    case TokenKind.Ampersand:
                    case TokenKind.MinusMinus:
                    case TokenKind.Comma:
                        UngetToken(token);

                        // If we haven't seen an argument, the caller must issue an error.  If we've seen at least one
                        // argument, then we will issue the error and return back the arguments seen so far.
                        if (commaToken == null)
                        {
                            return null;
                        }

                        // ErrorRecovery: stop looking for additional arguments, exclude the trailing comma

                        ReportIncompleteInput(After(commaToken), () => ParserStrings.MissingExpression, ",");
                        return new ErrorExpressionAst(ExtentOf(commandArgs.First(), commaToken), commandArgs);

                    case TokenKind.SplattedVariable:
                    case TokenKind.Variable:
                    case TokenKind.Number:
                    case TokenKind.HereStringExpandable:
                    case TokenKind.StringExpandable:
                    case TokenKind.HereStringLiteral:
                    case TokenKind.StringLiteral:
                    case TokenKind.LParen:
                    case TokenKind.DollarParen:
                    case TokenKind.AtParen:
                    case TokenKind.AtCurly:
                    case TokenKind.LCurly:
                        UngetToken(token);
                        exprAst = PrimaryExpressionRule(withMemberAccess: true);
                        Diagnostics.Assert(exprAst != null, "PrimaryExpressionRule should never return null");
                        break;

                    case TokenKind.Generic:
                        if ((context & CommandArgumentContext.CommandName) != 0)
                        {
                            token.TokenFlags |= TokenFlags.CommandName;
                        }

                        var genericToken = (StringToken)token;
                        var expandableToken = genericToken as StringExpandableToken;
                        // A command name w/o invocation operator is not expandable even if the token has expandable parts
                        // If we have seen an invocation operator, the command name is expandable.
                        if (expandableToken != null && context != CommandArgumentContext.CommandName)
                        {
                            var nestedExpressions = ParseNestedExpressions(expandableToken);
                            exprAst = new ExpandableStringExpressionAst(expandableToken, expandableToken.Value,
                                                                        expandableToken.FormatString, nestedExpressions);
                        }
                        else
                        {
                            exprAst = new StringConstantExpressionAst(genericToken.Extent, genericToken.Value, StringConstantType.BareWord);

                            // If this is a verbatim argument, then don't continue peeking
                            if (String.Equals(genericToken.Value, VERBATIM_ARGUMENT, StringComparison.OrdinalIgnoreCase))
                            {
                                foundVerbatimArgument = true;
                            }
                        }
                        break;

                    default:
                        exprAst = new StringConstantExpressionAst(token.Extent, token.Text, StringConstantType.BareWord);

                        // A command/argument that matches a keyword isn't really a keyword, so don't color it that way
                        token.TokenFlags &= ~TokenFlags.Keyword;

                        switch (context)
                        {
                            case CommandArgumentContext.CommandName:
                            case CommandArgumentContext.CommandNameAfterInvocationOperator:
                                token.TokenFlags |= TokenFlags.CommandName;
                                break;
                            case CommandArgumentContext.FileName:
                            case CommandArgumentContext.CommandArgument:
                            case CommandArgumentContext.SwitchCondition:
                                token.SetIsCommandArgument();
                                break;
                        }
                        break;
                }

                if (context != CommandArgumentContext.CommandArgument)
                {
                    break;
                }

                if (foundVerbatimArgument)
                {
                    break;
                }

                token = PeekToken();
                if (token.Kind != TokenKind.Comma)
                {
                    break;
                }
                commaToken = token;
                if (commandArgs == null)
                {
                    commandArgs = new List<ExpressionAst>();
                }
                commandArgs.Add(exprAst);

                SkipToken();
                SkipNewlines();

                token = NextToken();
            }

            Diagnostics.Assert(commandArgs != null || exprAst != null, "How did that happen?");

            if (commandArgs != null)
            {
                commandArgs.Add(exprAst);
                return new ArrayLiteralAst(ExtentOf(commandArgs[0], commandArgs[commandArgs.Count - 1]), commandArgs);
            }

            return exprAst;
        }
Exemple #14
0
 /// <summary/>
 public virtual object VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst) { return null; }
Exemple #15
0
 public override AstVisitAction VisitExpandableStringExpression(ExpandableStringExpressionAst ast)
 {
     return(Check(ast));
 }
 public object VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst)
 {
     return false;
 }
Exemple #17
0
 public object VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst)
 {
     ConstantExpression expression = Expression.Constant(expandableStringExpressionAst.FormatExpression);
     ReadOnlyCollection<ExpressionAst> nestedExpressions = expandableStringExpressionAst.NestedExpressions;
     PSToStringBinder toStringBinder = PSToStringBinder.Get();
     NewArrayExpression expression2 = Expression.NewArrayInit(typeof(string), (IEnumerable<Expression>) (from e in nestedExpressions select Expression.Dynamic(toStringBinder, typeof(string), this.Compile(e), _executionContextParameter)));
     return Expression.Call(CachedReflectionInfo.StringOps_FormatOperator, expression, expression2);
 }
 public object VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst)
 {
     return(AutomationNull.Value);
 }
Exemple #19
0
 /// <summary/>
 public virtual AstVisitAction VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst) => DefaultVisit(expandableStringExpressionAst);
 public override AstVisitAction VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst)
 {
     return AstVisitAction.Continue;
 }
Exemple #21
0
        public override AstVisitAction VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst)
        {
            // REVIEW: it should be OK to allow these, since the ast now would visit the nested expressions and catch the errors.
            // Not allowed since most variables are not allowed
            //ReportError(expandableStringExpressionAst, () => ParserStrings.ExpandableStringNotSupportedInDataSection);

            return AstVisitAction.Continue;
        }
Exemple #22
0
 public object VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst)
 {
     foreach (ExpressionAst ast in expandableStringExpressionAst.NestedExpressions)
     {
         ast.Accept(this);
     }
     return null;
 }
 public object VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst) { throw new UnexpectedElementException(); }
 /// <summary/>
 public virtual object VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst)
 {
     return _decorated.VisitExpandableStringExpression(expandableStringExpressionAst);
 }
 public override AstVisitAction VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst)
 {
     return(AstVisitAction.Continue);
 }
Exemple #26
0
    public System.Object VisitExpandableStringExpression(System.Management.Automation.Language.ExpandableStringExpressionAst expandableStringExpressionAst)
    {
        IScriptExtent mappedExtent = MapExtent(expandableStringExpressionAst.Extent);

        return(new ExpandableStringExpressionAst(mappedExtent, expandableStringExpressionAst.Value, expandableStringExpressionAst.StringConstantType));
    }
Exemple #27
0
 private List<CompletionResult> GetResultForIdentifier(CompletionContext completionContext, ref int replacementIndex, ref int replacementLength, bool isQuotedString)
 {
     Token tokenAtCursor = completionContext.TokenAtCursor;
     Ast lastAst = completionContext.RelatedAsts.Last<Ast>();
     List<CompletionResult> source = null;
     completionContext.WordToComplete = tokenAtCursor.Text;
     StringConstantExpressionAst ast2 = lastAst as StringConstantExpressionAst;
     if ((ast2 != null) && ast2.Value.Equals("$", StringComparison.Ordinal))
     {
         completionContext.WordToComplete = "";
         return CompletionCompleters.CompleteVariable(completionContext);
     }
     if ((tokenAtCursor.TokenFlags & TokenFlags.CommandName) != TokenFlags.None)
     {
         if ((completionContext.RelatedAsts.Count > 0) && (completionContext.RelatedAsts[0] is ScriptBlockAst))
         {
             Ast lastAstAtCursor = null;
             InternalScriptPosition position = (InternalScriptPosition) this._cursorPosition;
             int offset = position.Offset - tokenAtCursor.Text.Length;
             if (offset >= 0)
             {
                 InternalScriptPosition cursorPosition = position.CloneWithNewOffset(offset);
                 ScriptBlockAst scriptBlockAst = (ScriptBlockAst) completionContext.RelatedAsts[0];
                 lastAstAtCursor = GetLastAstAtCursor(scriptBlockAst, cursorPosition);
             }
             if (((lastAstAtCursor != null) && (lastAstAtCursor.Extent.EndLineNumber == tokenAtCursor.Extent.StartLineNumber)) && (lastAstAtCursor.Extent.EndColumnNumber == tokenAtCursor.Extent.StartColumnNumber))
             {
                 if (tokenAtCursor.Text.IndexOfAny(new char[] { '\\', '/' }) == 0)
                 {
                     string str = CompletionCompleters.ConcatenateStringPathArguments(lastAstAtCursor as CommandElementAst, tokenAtCursor.Text, completionContext);
                     if (str != null)
                     {
                         completionContext.WordToComplete = str;
                         source = new List<CompletionResult>(CompletionCompleters.CompleteFilename(completionContext));
                         if (source.Count > 0)
                         {
                             replacementIndex = lastAstAtCursor.Extent.StartScriptPosition.Offset;
                             replacementLength += lastAstAtCursor.Extent.Text.Length;
                         }
                         return source;
                     }
                     VariableExpressionAst variableAst = lastAstAtCursor as VariableExpressionAst;
                     string str2 = (variableAst != null) ? CompletionCompleters.CombineVariableWithPartialPath(variableAst, tokenAtCursor.Text, completionContext.ExecutionContext) : null;
                     if (str2 == null)
                     {
                         return source;
                     }
                     completionContext.WordToComplete = str2;
                     replacementIndex = lastAstAtCursor.Extent.StartScriptPosition.Offset;
                     replacementLength += lastAstAtCursor.Extent.Text.Length;
                     completionContext.ReplacementIndex = replacementIndex;
                     completionContext.ReplacementLength = replacementLength;
                 }
                 else if (!(lastAstAtCursor is ErrorExpressionAst) || !(lastAstAtCursor.Parent is IndexExpressionAst))
                 {
                     return source;
                 }
             }
         }
         if (!isQuotedString)
         {
             StringExpandableToken token2 = tokenAtCursor as StringExpandableToken;
             if (((token2 != null) && (token2.NestedTokens != null)) && (ast2 != null))
             {
                 try
                 {
                     string expandedString = null;
                     ExpandableStringExpressionAst expandableStringAst = new ExpandableStringExpressionAst(ast2.Extent, ast2.Value, StringConstantType.BareWord);
                     if (CompletionCompleters.IsPathSafelyExpandable(expandableStringAst, string.Empty, completionContext.ExecutionContext, out expandedString))
                     {
                         completionContext.WordToComplete = expandedString;
                     }
                     else
                     {
                         return source;
                     }
                 }
                 catch (Exception exception)
                 {
                     CommandProcessorBase.CheckForSevereException(exception);
                     return source;
                 }
             }
             source = CompleteFileNameAsCommand(completionContext);
             List<CompletionResult> collection = CompletionCompleters.CompleteCommand(completionContext);
             if ((collection != null) && (collection.Count > 0))
             {
                 source.AddRange(collection);
             }
         }
         return source;
     }
     if (((tokenAtCursor.Text.Length == 1) && tokenAtCursor.Text[0].IsDash()) && (lastAst.Parent is CommandAst))
     {
         if (isQuotedString)
         {
             return source;
         }
         return CompletionCompleters.CompleteCommandParameter(completionContext);
     }
     TokenKind unknown = TokenKind.Unknown;
     bool flag = lastAst.Parent is MemberExpressionAst;
     bool @static = flag ? ((MemberExpressionAst) lastAst.Parent).Static : false;
     bool flag3 = false;
     if (!flag)
     {
         if (tokenAtCursor.Text.Equals(TokenKind.Dot.Text(), StringComparison.Ordinal))
         {
             unknown = TokenKind.Dot;
             flag = true;
         }
         else if (tokenAtCursor.Text.Equals(TokenKind.ColonColon.Text(), StringComparison.Ordinal))
         {
             unknown = TokenKind.ColonColon;
             flag = true;
         }
         else if (tokenAtCursor.Kind.Equals(TokenKind.Multiply) && (lastAst is BinaryExpressionAst))
         {
             BinaryExpressionAst item = (BinaryExpressionAst) lastAst;
             MemberExpressionAst left = item.Left as MemberExpressionAst;
             IScriptExtent errorPosition = item.ErrorPosition;
             if (((left != null) && (item.Operator == TokenKind.Multiply)) && (errorPosition.StartOffset == left.Member.Extent.EndOffset))
             {
                 @static = left.Static;
                 unknown = @static ? TokenKind.ColonColon : TokenKind.Dot;
                 flag = true;
                 flag3 = true;
                 completionContext.RelatedAsts.Remove(item);
                 completionContext.RelatedAsts.Add(left);
                 StringConstantExpressionAst member = left.Member as StringConstantExpressionAst;
                 if (member != null)
                 {
                     replacementIndex = member.Extent.StartScriptPosition.Offset;
                     replacementLength += member.Extent.Text.Length;
                 }
             }
         }
     }
     if (flag)
     {
         source = CompletionCompleters.CompleteMember(completionContext, @static || (unknown == TokenKind.ColonColon));
         if (source.Any<CompletionResult>())
         {
             if (!flag3 && (unknown != TokenKind.Unknown))
             {
                 replacementIndex += tokenAtCursor.Text.Length;
                 replacementLength = 0;
             }
             return source;
         }
     }
     if (lastAst.Parent is HashtableAst)
     {
         source = CompletionCompleters.CompleteHashtableKey(completionContext, (HashtableAst) lastAst.Parent);
         if ((source != null) && source.Any<CompletionResult>())
         {
             return source;
         }
     }
     if (!isQuotedString)
     {
         bool flag4 = false;
         if ((lastAst.Parent is FileRedirectionAst) || CompleteAgainstSwitchFile(lastAst, completionContext.TokenBeforeCursor))
         {
             string str4 = CompletionCompleters.ConcatenateStringPathArguments(lastAst as CommandElementAst, string.Empty, completionContext);
             if (str4 != null)
             {
                 flag4 = true;
                 completionContext.WordToComplete = str4;
             }
         }
         else if (tokenAtCursor.Text.IndexOfAny(new char[] { '\\', '/' }) == 0)
         {
             CommandBaseAst parent = lastAst.Parent as CommandBaseAst;
             if ((parent != null) && parent.Redirections.Any<RedirectionAst>())
             {
                 FileRedirectionAst ast11 = parent.Redirections[0] as FileRedirectionAst;
                 if (((ast11 != null) && (ast11.Extent.EndLineNumber == lastAst.Extent.StartLineNumber)) && (ast11.Extent.EndColumnNumber == lastAst.Extent.StartColumnNumber))
                 {
                     string str5 = CompletionCompleters.ConcatenateStringPathArguments(ast11.Location, tokenAtCursor.Text, completionContext);
                     if (str5 != null)
                     {
                         flag4 = true;
                         completionContext.WordToComplete = str5;
                         replacementIndex = ast11.Location.Extent.StartScriptPosition.Offset;
                         replacementLength += ast11.Location.Extent.EndScriptPosition.Offset - replacementIndex;
                         completionContext.ReplacementIndex = replacementIndex;
                         completionContext.ReplacementLength = replacementLength;
                     }
                 }
             }
         }
         if (flag4)
         {
             return new List<CompletionResult>(CompletionCompleters.CompleteFilename(completionContext));
         }
         string str6 = CompletionCompleters.ConcatenateStringPathArguments(lastAst as CommandElementAst, string.Empty, completionContext);
         if (str6 != null)
         {
             completionContext.WordToComplete = str6;
         }
         source = CompletionCompleters.CompleteCommandArgument(completionContext);
         replacementIndex = completionContext.ReplacementIndex;
         replacementLength = completionContext.ReplacementLength;
     }
     return source;
 }
Exemple #28
0
 public virtual AstVisitAction VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst)
 {
     return AstVisitAction.Continue;
 }
Exemple #29
0
 public override AstVisitAction VisitExpandableStringExpression(ExpandableStringExpressionAst ast)
 {
     return this.Check(ast);
 }
Exemple #30
0
 /// <summary/>
 public virtual object VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst)
 {
     return(null);
 }
Exemple #31
0
 public object VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst) { return AutomationNull.Value; }
Exemple #32
0
        ExpressionAst BuildExpandableStringLiteralWithSubexpressionAst(ParseTreeNode parseTreeNode)
        {
            VerifyTerm(parseTreeNode, this._grammar.expandable_string_literal_with_subexpr);

            var toResolve = new List<ExpressionAst>();

            var stmtTreeNode = parseTreeNode.ChildNodes[1];
            var stmtAst = BuildStatementListAst(stmtTreeNode);
            // the child node only covers the stamentent list, but not $( and ), which are part of other child nodes
            // therefore we artifically expand the extent by -2 and 1 to cover the markup.
            // this is important so the replacements work correctly
            var subExpExtent = new ScriptExtent(stmtTreeNode.Span, -2, 1);
            toResolve.Add(new SubExpressionAst(subExpExtent, stmtAst));

            for (int i = 3; i < parseTreeNode.ChildNodes.Count - 1; i++)
            {
                var item = parseTreeNode.ChildNodes[i];

                if (item.Term == this._grammar.expandable_string_with_subexpr_characters)
                {
                    foreach (var item2 in item.ChildNodes)
                    {
                        //sub_expression
                        //expandable_string_part
                        if (item2.Term == this._grammar.expandable_string_with_subexpr_part)
                        {
                            foreach (var item3 in item2.ChildNodes)
                            {
                                if (item3.Term == this._grammar.expandable_string_characters)
                                {
                                    var matches = Regex.Match(item3.FindTokenAndGetText(), this._grammar.expandable_string_characters.Pattern, RegexOptions.IgnoreCase);
                                    string value = matches.Groups[this._grammar.expandable_string_characters.Name].Value;

                                    var ast = new ExpandableStringExpressionAst(new ScriptExtent(item3), value, StringConstantType.DoubleQuoted);
                                    if (ast.NestedExpressions.Any())
                                    {
                                        toResolve.Add(ast);
                                    }
                                }

                                if (item3.Term == this._grammar.sub_expression)
                                {
                                    toResolve.Add(BuildSubExpression(item3));
                                }
                            }
                        }
                    }
                }
            }

            var extent = (IScriptExtent) new ScriptExtent(parseTreeNode);
            // now strip the real text value. +1 and -2 are used to strip the quotes
            var textValue = _parseTree.SourceText.Substring(extent.StartOffset + 1, extent.EndOffset - extent.StartOffset - 2);
            return new ExpandableStringExpressionAst(
                extent, toResolve, textValue,
                StringConstantType.DoubleQuoted);
        }
Exemple #33
0
 public object VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst)
 {
     bool isSafe = true;
     foreach (var nestedExpression in expandableStringExpressionAst.NestedExpressions)
     {
         _visitCount++;
         if (!(bool)nestedExpression.Accept(this))
         {
             isSafe = false;
             break;
         }
     }
     return isSafe;
 }
        public object VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst)
        {
            object[] safeValues = new object[expandableStringExpressionAst.NestedExpressions.Count];
            // retrieve OFS, and if it doesn't exist set it to space
            string ofs = null;

            if (s_context != null)
            {
                ofs = s_context.SessionState.PSVariable.GetValue("OFS") as string;
            }

            if (ofs == null)
            {
                ofs = " ";
            }

            for (int offset = 0; offset < safeValues.Length; offset++)
            {
                var result = expandableStringExpressionAst.NestedExpressions[offset].Accept(this);
                // depending on the nested expression we may retrieve a variable, or even need to
                // execute a sub-expression. The result of which may be returned
                // as a scalar, array or nested array. If the unwrap of first array doesn't contain a nested
                // array we can then pass it to string.Join. If it *does* contain an array,
                // we need to unwrap the inner array and pass *that* to string.Join.
                //
                // This means we get the same answer with GetPowerShell() as in the command-line
                // { echo "abc $true $(1) $(2,3) def" }.Invoke() gives the same answer as
                // { echo "abc $true $(1) $(2,3) def" }.GetPowerShell().Invoke()
                // abc True 1 2 3 def
                // as does { echo "abc $true $(1) $(@(1,2),@(3,4)) def"
                // which is
                // abc True 1 System.Object[] System.Object[] def
                // fortunately, at this point, we're dealing with strings, so whatever the result
                // from the ToString method of the array (or scalar) elements, that's symmetrical with
                // a standard scriptblock invocation behavior
                var resultArray = result as object[];

                // In this environment, we can't use $OFS as we might expect. Retrieving OFS
                // might possibly leak server side info which we don't want, so we'll
                // assign ' ' as our OFS for purposes of GetPowerShell
                // Also, this will not call any script implementations of ToString (ala types.clixml)
                // This *will* result in a different result in those cases. However, to execute some
                // arbitrary script at this stage would be opening ourselves up to an attack
                if (resultArray != null)
                {
                    object[] subExpressionResult = new object[resultArray.Length];
                    for (int subExpressionOffset = 0;
                         subExpressionOffset < subExpressionResult.Length;
                         subExpressionOffset++)
                    {
                        // check to see if there is an array in our array,
                        object[] subResult = resultArray[subExpressionOffset] as object[];
                        if (subResult != null)
                        {
                            subExpressionResult[subExpressionOffset] = string.Join(ofs, subResult);
                        }
                        else // it is a scalar, so we can just add it to our collections
                        {
                            subExpressionResult[subExpressionOffset] = resultArray[subExpressionOffset];
                        }
                    }

                    safeValues[offset] = string.Join(ofs, subExpressionResult);
                }
                else
                {
                    safeValues[offset] = result;
                }
            }

            return(StringUtil.Format(expandableStringExpressionAst.FormatExpression, safeValues));
        }
Exemple #35
0
        public object VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst)
        {
            object[] safeValues = new object[expandableStringExpressionAst.NestedExpressions.Count];
            // retrieve OFS, and if it doesn't exist set it to space
            string ofs = null;
            if (s_context != null)
            {
                ofs = s_context.SessionState.PSVariable.GetValue("OFS") as string;
            }
            if (ofs == null)
            {
                ofs = " ";
            }
            for (int offset = 0; offset < safeValues.Length; offset++)
            {
                var result = expandableStringExpressionAst.NestedExpressions[offset].Accept(this);
                // depending on the nested expression we may retrieve a variable, or even need to 
                // execute a sub-expression. The result of which may be returned
                // as a scalar, array or nested array. If the unwrap of first array doesn't contain a nested
                // array we can then pass it to String.Join. If it *does* contain an array,
                // we need to unwrap the inner array and pass *that* to String.Join.
                // 
                // This means we get the same answer with GetPowerShell() as in the command-line
                // { echo "abc $true $(1) $(2,3) def" }.Invoke() gives the same answer as 
                // { echo "abc $true $(1) $(2,3) def" }.GetPowerShell().Invoke()
                // abc True 1 2 3 def
                // as does { echo "abc $true $(1) $(@(1,2),@(3,4)) def"
                // which is 
                // abc True 1 System.Object[] System.Object[] def
                // fortunately, at this point, we're dealing with strings, so whatever the result
                // from the ToString method of the array (or scalar) elements, that's symmetrical with
                // a standard scriptblock invocation behavior
                var resultArray = result as object[];

                // In this environment, we can't use $OFS as we might expect. Retrieving OFS
                // might possibly leak server side info which we don't want, so we'll
                // assign ' ' as our OFS for purposes of GetPowerShell
                // Also, this will not call any script implementations of ToString (ala types.clixml)
                // This *will* result in a different result in those cases. However, to execute some
                // arbitrary script at this stage would be opening ourselves up to an attack
                if (resultArray != null)
                {
                    object[] subExpressionResult = new object[resultArray.Length];
                    for (int subExpressionOffset = 0;
                        subExpressionOffset < subExpressionResult.Length;
                        subExpressionOffset++)
                    {
                        // check to see if there is an array in our array,
                        object[] subResult = resultArray[subExpressionOffset] as object[];
                        if (subResult != null)
                        {
                            subExpressionResult[subExpressionOffset] = String.Join(ofs, subResult);
                        }
                        else // it is a scalar, so we can just add it to our collections
                        {
                            subExpressionResult[subExpressionOffset] = resultArray[subExpressionOffset];
                        }
                    }
                    safeValues[offset] = string.Join(ofs, subExpressionResult);
                }
                else
                {
                    safeValues[offset] = result;
                }
            }

            return StringUtil.Format(expandableStringExpressionAst.FormatExpression, safeValues);
        }
 public object VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst)
 {
     return(false);
 }
Exemple #37
0
 public object VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst)
 {
     var left = Expression.Constant(expandableStringExpressionAst.FormatExpression);
     var nestedAsts = expandableStringExpressionAst.NestedExpressions;
     var toStringBinder = PSToStringBinder.Get();
     var right = Expression.NewArrayInit(typeof(string),
         nestedAsts.Select(
             e => DynamicExpression.Dynamic(toStringBinder, typeof(string), Compile(e), _executionContextParameter)));
     return Expression.Call(CachedReflectionInfo.StringOps_FormatOperator,
                            left, right);
 }
Exemple #38
0
        ExpressionAst BuildExpandableStringLiteralAst(ParseTreeNode parseTreeNode)
        {
            var matches = Regex.Match(parseTreeNode.FindTokenAndGetText(), this._grammar.expandable_string_literal.Pattern, RegexOptions.IgnoreCase);
            string value = matches.Groups[this._grammar.expandable_string_characters.Name].Value +
                matches.Groups[this._grammar.dollars.Name].Value
                ;

            var ast = new ExpandableStringExpressionAst(new ScriptExtent(parseTreeNode), value, StringConstantType.DoubleQuoted);
            if (ast.NestedExpressions.Any())
            {
                return ast;
            }
            return new StringConstantExpressionAst(new ScriptExtent(parseTreeNode), value, StringConstantType.DoubleQuoted);
        }
 public object VisitExpandableStringExpression(ExpandableStringExpressionAst expandableStringExpressionAst)
 {
     throw new NotImplementedException();
 }