Team Ai
Datasetpublic

MegaBites-AI/Windows-powershell

sourceHugging Facemitupdated 6mo agoView on Hugging Face
0likes372downloads
VariableOps.cs328 linesDownload Raw Back to Operations
1// Copyright (c) Microsoft Corporation.2// Licensed under the MIT License.3 4using System.Linq;5using System.Management.Automation.Internal;6using System.Management.Automation.Language;7 8// ReSharper disable UnusedMember.Local9 10namespace System.Management.Automation11{12    using Dbg = Diagnostics;13    using System.Collections.ObjectModel;14 15    internal static class VariableOps16    {17        internal static object SetVariableValue(VariablePath variablePath, object value, ExecutionContext executionContext, AttributeBaseAst[] attributeAsts)18        {19            SessionStateInternal sessionState = executionContext.EngineSessionState;20            CommandOrigin origin = sessionState.CurrentScope.ScopeOrigin;21 22            if (!variablePath.IsVariable)23            {24                sessionState.SetVariable(variablePath, value, true, origin);25                return value;26            }27 28            // Variable assignment is traced only if trace level 2 is specified.29            if (executionContext.PSDebugTraceLevel > 1)30            {31                executionContext.Debugger.TraceVariableSet(variablePath.UnqualifiedPath, value);32            }33 34            if (variablePath.IsUnscopedVariable)35            {36                variablePath = variablePath.CloneAndSetLocal();37            }38 39            SessionStateScope scope;40            PSVariable var = sessionState.GetVariableItem(variablePath, out scope, origin);41 42            if (var == null)43            {44                var attributes = attributeAsts == null45                                     ? new Collection<Attribute>()46                                     : GetAttributeCollection(attributeAsts);47                var = new PSVariable(variablePath.UnqualifiedPath, value, ScopedItemOptions.None, attributes);48 49                if (attributes.Count > 0)50                {51                    // When there are any attributes, it's possible the value was converted/transformed.52                    // Use 'GetValueRaw' here so the debugger check won't be triggered.53                    value = var.GetValueRaw();54                }55 56                // Marking untrusted values for assignments in 'ConstrainedLanguage' mode is done in57                // SessionStateScope.SetVariable.58                sessionState.SetVariable(variablePath, var, false, origin);59 60                if (executionContext._debuggingMode > 0)61                {62                    executionContext.Debugger.CheckVariableWrite(variablePath.UnqualifiedPath);63                }64            }65            else66            {67                if (attributeAsts != null)68                {69                    // Use bytewise operation directly instead of 'var.IsReadOnly || var.IsConstant' on70                    // a hot path (setting variable with type constraint) to get better performance.71                    if ((var.Options & (ScopedItemOptions.ReadOnly | ScopedItemOptions.Constant)) != ScopedItemOptions.None)72                    {73                        SessionStateUnauthorizedAccessException e =74                            new SessionStateUnauthorizedAccessException(75                                    var.Name,76                                    SessionStateCategory.Variable,77                                    "VariableNotWritable",78                                    SessionStateStrings.VariableNotWritable);79                        throw e;80                    }81 82                    var attributes = GetAttributeCollection(attributeAsts);83                    value = PSVariable.TransformValue(attributes, value);84                    if (!PSVariable.IsValidValue(attributes, value))85                    {86                        ValidationMetadataException e = new ValidationMetadataException(87                            "ValidateSetFailure",88                            null,89                            Metadata.InvalidValueFailure,90                            var.Name,91                            (value != null) ? value.ToString() : "$null");92 93                        throw e;94                    }95 96                    var.SetValueRaw(value, true);97                    // Don't update the PSVariable's attributes until we successfully set the value98                    var.Attributes.Clear();99                    var.AddParameterAttributesNoChecks(attributes);100 101                    if (executionContext._debuggingMode > 0)102                    {103                        executionContext.Debugger.CheckVariableWrite(variablePath.UnqualifiedPath);104                    }105                }106                else107                {108                    // The setter will handle checking for variable writes.109                    var.Value = value;110                }111 112                if (executionContext.LanguageMode == PSLanguageMode.ConstrainedLanguage)113                {114                    // Mark untrusted values for assignments to 'Global:' variables, and 'Script:' variables in115                    // a module scope, if it's necessary.116                    ExecutionContext.MarkObjectAsUntrustedForVariableAssignment(var, scope, sessionState);117                }118            }119 120            return value;121        }122 123        private static bool ThrowStrictModeUndefinedVariable(ExecutionContext executionContext, VariableExpressionAst varAst)124        {125            // In some limited cases, the compiler knows we don't want an error, like when we're backing up126            // $foreach and $switch, which might not be set.  In that case, the ast passed is null.127            if (varAst == null)128            {129                return false;130            }131 132            if (executionContext.IsStrictVersion(2))133            {134                return true;135            }136 137            if (executionContext.IsStrictVersion(1))138            {139                var parent = varAst.Parent;140                while (parent != null)141                {142                    if (parent is ExpandableStringExpressionAst)143                    {144                        return false;145                    }146 147                    parent = parent.Parent;148                }149 150                return true;151            }152 153            return false;154        }155 156        internal static object GetAutomaticVariableValue(int tupleIndex, ExecutionContext executionContext, VariableExpressionAst varAst)157        {158            Diagnostics.Assert(tupleIndex < SpecialVariables.AutomaticVariableTypes.Length, "caller to verify a valid tuple index is used");159 160            if (executionContext._debuggingMode > 0)161            {162                executionContext.Debugger.CheckVariableRead(SpecialVariables.AutomaticVariables[tupleIndex]);163            }164 165            object result = executionContext.EngineSessionState.GetAutomaticVariableValue((AutomaticVariable)tupleIndex);166 167            if (result == AutomationNull.Value)168            {169                if (ThrowStrictModeUndefinedVariable(executionContext, varAst))170                {171                    throw InterpreterError.NewInterpreterException(SpecialVariables.AutomaticVariables[tupleIndex], typeof(RuntimeException),172                        varAst.Extent, "VariableIsUndefined", ParserStrings.VariableIsUndefined, SpecialVariables.AutomaticVariables[tupleIndex]);173                }174 175                result = null;176            }177 178            return result;179        }180 181        internal static object GetVariableValue(VariablePath variablePath, ExecutionContext executionContext, VariableExpressionAst varAst)182        {183            if (!variablePath.IsVariable)184            {185                CmdletProviderContext contextOut;186                SessionStateScope scopeOut;187                SessionStateInternal ss = executionContext.EngineSessionState;188                return ss.GetVariableValueFromProvider(variablePath, out contextOut, out scopeOut, ss.CurrentScope.ScopeOrigin);189            }190 191            SessionStateInternal sessionState = executionContext.EngineSessionState;192            CommandOrigin origin = sessionState.CurrentScope.ScopeOrigin;193 194            SessionStateScope scope;195            PSVariable var = sessionState.GetVariableItem(variablePath, out scope, origin);196 197            if (var != null)198            {199                return var.Value;200            }201 202            if (sessionState.ExecutionContext._debuggingMode > 0)203            {204                sessionState.ExecutionContext.Debugger.CheckVariableRead(variablePath.UnqualifiedPath);205            }206 207            if (ThrowStrictModeUndefinedVariable(executionContext, varAst))208            {209                throw InterpreterError.NewInterpreterException(variablePath.UserPath, typeof(RuntimeException),210                    varAst.Extent, "VariableIsUndefined", ParserStrings.VariableIsUndefined, variablePath.UserPath);211            }212 213            return null;214        }215 216        internal static PSReference GetVariableAsRef(VariablePath variablePath, ExecutionContext executionContext, Type staticType)217        {218            Diagnostics.Assert(variablePath.IsVariable, "calller to verify varpath is a variable.");219 220            SessionStateInternal sessionState = executionContext.EngineSessionState;221            CommandOrigin origin = sessionState.CurrentScope.ScopeOrigin;222 223            SessionStateScope scope;224            PSVariable var = sessionState.GetVariableItem(variablePath, out scope, origin);225 226            if (var == null)227            {228                throw InterpreterError.NewInterpreterException(variablePath, typeof(RuntimeException), null,229                                                               "NonExistingVariableReference",230                                                               ParserStrings.NonExistingVariableReference);231            }232 233            object value = var.Value;234            if (staticType == null && value != null)235            {236                value = PSObject.Base(value);237                if (value != null)238                {239                    staticType = value.GetType();240                }241            }242 243            if (staticType == null)244            {245                var declaredType = var.Attributes.OfType<ArgumentTypeConverterAttribute>().FirstOrDefault();246                staticType = declaredType != null ? declaredType.TargetType : typeof(LanguagePrimitives.Null);247            }248 249            return PSReference.CreateInstance(var, staticType);250        }251 252        private static Collection<Attribute> GetAttributeCollection(AttributeBaseAst[] attributeAsts)253        {254            var result = new Collection<Attribute>();255            foreach (var attributeAst in attributeAsts)256            {257                result.Add(attributeAst.GetAttribute());258            }259 260            return result;261        }262 263        private static UsingResult GetUsingValueFromTuple(MutableTuple tuple, string usingExpressionKey, int index)264        {265            var boundParameters =266                tuple.GetAutomaticVariable(AutomaticVariable.PSBoundParameters) as PSBoundParametersDictionary;267            if (boundParameters != null)268            {269                var implicitUsingParameters = boundParameters.ImplicitUsingParameters;270                if (implicitUsingParameters != null)271                {272                    if (implicitUsingParameters.Contains(usingExpressionKey))273                    {274                        return new UsingResult { Value = implicitUsingParameters[usingExpressionKey] };275                    }276                    else if (implicitUsingParameters.Contains(index))277                    {278                        // Handle downlevel (V4) using variables by using index to look up using value.279                        return new UsingResult { Value = implicitUsingParameters[index] };280                    }281                }282            }283 284            return null;285        }286 287        private sealed class UsingResult288        {289            public object Value { get; set; }290        }291 292        internal static object GetUsingValue(MutableTuple tuple, string usingExpressionKey, int index, ExecutionContext context)293        {294            UsingResult result = GetUsingValueFromTuple(tuple, usingExpressionKey, index);295            if (result != null)296            {297                return result.Value;298            }299 300            var scope = context.EngineSessionState.CurrentScope;301            while (scope != null)302            {303                result = GetUsingValueFromTuple(scope.LocalsTuple, usingExpressionKey, index);304                if (result != null)305                {306                    return result.Value;307                }308 309                foreach (var dottedScope in scope.DottedScopes)310                {311                    result = GetUsingValueFromTuple(dottedScope, usingExpressionKey, index);312                    if (result != null)313                    {314                        return result.Value;315                    }316                }317 318                scope = scope.Parent;319            }320 321            // $PSBoundParameters is null or not the expected type (because someone may have assigned to it), so322            // we can't even guess if they were mis-using $using:foo323            throw InterpreterError.NewInterpreterException(null, typeof(RuntimeException),324                null, "UsingWithoutInvokeCommand", ParserStrings.UsingWithoutInvokeCommand);325        }326    }327}328