Team Ai
Datasetpublic

MegaBites-AI/Windows-powershell

sourceHugging Facemitupdated 6mo agoView on Hugging Face
0likes308downloads
SessionStateNavigation.cs1751 linesDownload Raw Back to engine
1// Copyright (c) Microsoft Corporation.2// Licensed under the MIT License.3 4using System.Collections.ObjectModel;5using System.Management.Automation.Provider;6 7using Dbg = System.Management.Automation;8 9#pragma warning disable 1634, 1691 // Stops compiler from warning about unknown warnings10#pragma warning disable 5650011 12namespace System.Management.Automation13{14    /// <summary>15    /// Holds the state of a Monad Shell session.16    /// </summary>17    internal sealed partial class SessionStateInternal18    {19        #region NavigationCmdletProvider accessors20 21        #region GetParentPath22 23        /// <summary>24        /// Gets the path to the parent object for the given object.25        /// </summary>26        /// <param name="path">27        /// The path to the object to get the parent path from28        /// </param>29        /// <param name="root">30        /// The root of the drive.31        /// </param>32        /// <returns>33        /// The path to the parent object34        /// </returns>35        /// <exception cref="ArgumentNullException">36        /// If <paramref name="path"/> is null.37        /// </exception>38        /// <exception cref="NotSupportedException">39        /// If the <paramref name="providerInstance"/> does not support this operation.40        /// </exception>41        /// <exception cref="PipelineStoppedException">42        /// If the pipeline is being stopped while executing the command.43        /// </exception>44        /// <exception cref="ProviderInvocationException">45        /// If the provider threw an exception.46        /// </exception>47        internal string GetParentPath(string path, string root)48        {49            if (path == null)50            {51                throw PSTraceSource.NewArgumentNullException(nameof(path));52            }53 54            CmdletProviderContext context = new CmdletProviderContext(this.ExecutionContext);55 56            string result = GetParentPath(path, root, context);57 58            context.ThrowFirstErrorOrDoNothing();59 60            return result;61        }62 63        /// <summary>64        /// Gets the path to the parent object for the given object.65        /// </summary>66        /// <param name="path">67        /// The path to the object to get the parent path from68        /// </param>69        /// <param name="root">70        /// The root of the drive. Namespace providers should71        /// return the root if GetParentPath is called for the root.72        /// </param>73        /// <param name="context">74        /// The context which the core command is running.75        /// </param>76        /// <returns>77        /// The path to the parent object78        /// </returns>79        /// <exception cref="ArgumentNullException">80        /// If <paramref name="path"/> is null.81        /// </exception>82        /// <exception cref="NotSupportedException">83        /// If the <paramref name="providerInstance"/> does not support this operation.84        /// </exception>85        /// <exception cref="PipelineStoppedException">86        /// If the pipeline is being stopped while executing the command.87        /// </exception>88        /// <exception cref="ProviderInvocationException">89        /// If the provider threw an exception.90        /// </exception>91        internal string GetParentPath(92            string path,93            string root,94            CmdletProviderContext context)95        {96            return GetParentPath(path, root, context, false);97        }98 99        /// <summary>100        /// Gets the path to the parent object for the given object.101        /// Allow to use FileSystem as the default provider when the102        /// given path is drive-qualified and the drive cannot be found.103        /// </summary>104        /// <param name="path">105        /// The path to the object to get the parent path from106        /// </param>107        /// <param name="root">108        /// The root of the drive. Namespace providers should109        /// return the root if GetParentPath is called for the root.110        /// </param>111        /// <param name="context">112        /// The context which the core command is running.113        /// </param>114        /// <param name="useDefaultProvider">115        /// Specify whether to use default provider when needed.116        /// </param>117        /// <returns>118        /// The path to the parent object119        /// </returns>120        internal string GetParentPath(121            string path,122            string root,123            CmdletProviderContext context,124            bool useDefaultProvider)125        {126            if (path == null)127            {128                throw PSTraceSource.NewArgumentNullException(nameof(path));129            }130 131            CmdletProviderContext getProviderPathContext =132                new CmdletProviderContext(context);133 134            try135            {136                PSDriveInfo drive = null;137                ProviderInfo provider = null;138 139                try140                {141                    Globber.GetProviderPath(142                        path,143                        getProviderPathContext,144                        out provider,145                        out drive);146                }147                catch (DriveNotFoundException)148                {149                    // the path is sure to be drive_qualified and it is absolute path, otherwise the150                    // drive would be set to the current drive and the DriveNotFoundException will not happen151                    if (useDefaultProvider)152                    {153                        // the default provider is FileSystem154                        provider = PublicSessionState.Internal.GetSingleProvider(Microsoft.PowerShell.Commands.FileSystemProvider.ProviderName);155                    }156                    else157                    {158                        throw;159                    }160                }161 162                if (getProviderPathContext.HasErrors())163                {164                    getProviderPathContext.WriteErrorsToContext(context);165                    return null;166                }167 168                if (drive != null)169                {170                    context.Drive = drive;171                }172 173                bool isProviderQualified = false;174                bool isDriveQualified = false;175                string qualifier = null;176                string pathNoQualifier = RemoveQualifier(path, provider, out qualifier, out isProviderQualified, out isDriveQualified);177 178                string result = GetParentPath(provider, pathNoQualifier, root, context);179 180                if (!string.IsNullOrEmpty(qualifier) && !string.IsNullOrEmpty(result))181                {182                    result = AddQualifier(result, provider, qualifier, isProviderQualified, isDriveQualified);183                }184 185                return result;186            }187            finally188            {189                getProviderPathContext.RemoveStopReferral();190            }191        }192 193        private static string AddQualifier(string path, ProviderInfo provider, string qualifier, bool isProviderQualified, bool isDriveQualified)194        {195            string result = path;196 197            string formatString = "{1}";198            if (isProviderQualified)199            {200                formatString = "{0}::{1}";201            }202            else if (isDriveQualified)203            {204                // Porting note: on non-windows filesystem paths, there should be no colon in the path205                if (provider.VolumeSeparatedByColon)206                {207                    formatString = "{0}:{1}";208                }209                else210                {211                    formatString = "{0}{1}";212                }213            }214 215            result =216                string.Format(217                    System.Globalization.CultureInfo.InvariantCulture,218                    formatString,219                    qualifier,220                    path);221 222            return result;223        }224 225        /// <summary>226        /// Removes either the drive or provider qualifier or both from the path.227        /// </summary>228        /// <param name="path">229        /// The path to strip the provider qualifier from.230        /// </param>231        /// <param name="provider">232        /// The provider that should handle the RemoveQualifier call.233        /// </param>234        /// <param name="qualifier">235        /// Returns the qualifier of the path.236        /// </param>237        /// <param name="isProviderQualified">238        /// Returns true if the path is a provider-qualified path.239        /// </param>240        /// <param name="isDriveQualified">241        /// Returns true if the path is a drive-qualified path.242        /// </param>243        /// <returns>244        /// The path without the qualifier.245        /// </returns>246        private string RemoveQualifier(string path, ProviderInfo provider, out string qualifier, out bool isProviderQualified, out bool isDriveQualified)247        {248            Dbg.Diagnostics.Assert(249                path != null,250                "Path should be verified by the caller");251 252            string result = path;253            qualifier = null;254            isProviderQualified = false;255            isDriveQualified = false;256 257            if (LocationGlobber.IsProviderQualifiedPath(path, out qualifier))258            {259                isProviderQualified = true;260 261                int index = path.IndexOf("::", StringComparison.Ordinal);262 263                if (index != -1)264                {265                    // remove the qualifier266                    result = path.Substring(index + 2);267                }268            }269            else270            {271                if (Globber.IsAbsolutePath(path, out qualifier))272                {273                    isDriveQualified = true;274 275                    // Remove the drive name and colon, or just the drive name276 277                    // Porting note: on non-windows there is no colon for qualified paths278                    if (provider.VolumeSeparatedByColon)279                    {280                        result = path.Substring(qualifier.Length + 1);281                    }282                    else283                    {284                        result = path.Substring(qualifier.Length);285                    }286                }287            }288 289            return result;290        }291 292        /// <summary>293        /// Gets the path to the parent object for the given object.294        /// </summary>295        /// <param name="provider">296        /// The provider that should handle the GetParentPath call.297        /// </param>298        /// <param name="path">299        /// The path to the object to get the parent path from300        /// </param>301        /// <param name="root">302        /// The root of the drive. Namespace providers should303        /// return the root if GetParentPath is called for the root.304        /// </param>305        /// <param name="context">306        /// The context which the core command is running.307        /// </param>308        /// <returns>309        /// The path to the parent object310        /// </returns>311        /// <remarks>312        /// This is internal so that it can be called from the LocationGlobber.313        /// </remarks>314        /// <exception cref="NotSupportedException">315        /// If the <paramref name="providerInstance"/> does not support this operation.316        /// </exception>317        /// <exception cref="PipelineStoppedException">318        /// If the pipeline is being stopped while executing the command.319        /// </exception>320        /// <exception cref="ProviderInvocationException">321        /// If the provider threw an exception.322        /// </exception>323        internal string GetParentPath(324            ProviderInfo provider,325            string path,326            string root,327            CmdletProviderContext context)328        {329            // All parameters should have been validated by caller330            Dbg.Diagnostics.Assert(331                provider != null,332                "Caller should validate provider before calling this method");333 334            Dbg.Diagnostics.Assert(335                path != null,336                "Caller should validate path before calling this method");337 338            Dbg.Diagnostics.Assert(339                root != null,340                "Caller should validate root before calling this method");341 342            Dbg.Diagnostics.Assert(343                context != null,344                "Caller should validate context before calling this method");345 346            CmdletProvider providerInstance = GetProviderInstance(provider);347            return GetParentPath(providerInstance, path, root, context);348        }349 350        /// <summary>351        /// Gets the path to the parent object for the given object.352        /// </summary>353        /// <param name="providerInstance">354        /// The instance of the provider that should handle the GetParentPath call.355        /// </param>356        /// <param name="path">357        /// The path to the object to get the parent path from358        /// </param>359        /// <param name="root">360        /// The root of the drive. Namespace providers should361        /// return the root if GetParentPath is called for the root.362        /// </param>363        /// <param name="context">364        /// The context which the core command is running.365        /// </param>366        /// <returns>367        /// The path to the parent object368        /// </returns>369        /// <remarks>370        /// This is internal so that it can be called from the LocationGlobber.371        /// </remarks>372        /// <exception cref="NotSupportedException">373        /// If the <paramref name="providerInstance"/> does not support this operation.374        /// </exception>375        /// <exception cref="PipelineStoppedException">376        /// If the pipeline is being stopped while executing the command.377        /// </exception>378        /// <exception cref="ProviderInvocationException">379        /// If the provider threw an exception.380        /// </exception>381        internal string GetParentPath(382            CmdletProvider providerInstance,383            string path,384            string root,385            CmdletProviderContext context)386        {387            // All parameters should have been validated by caller388            Dbg.Diagnostics.Assert(389                providerInstance != null,390                "Caller should validate providerInstance before calling this method");391 392            Dbg.Diagnostics.Assert(393                path != null,394                "Caller should validate path before calling this method");395 396            Dbg.Diagnostics.Assert(397                root != null,398                "Caller should validate root before calling this method");399 400            Dbg.Diagnostics.Assert(401                context != null,402                "Caller should validate context before calling this method");403 404            NavigationCmdletProvider navigationCmdletProvider =405                GetNavigationProviderInstance(providerInstance, false);406 407            string result = null;408 409            try410            {411                result = navigationCmdletProvider.GetParentPath(path, root, context);412            }413            catch (LoopFlowException)414            {415                throw;416            }417            catch (PipelineStoppedException)418            {419                throw;420            }421            catch (ActionPreferenceStopException)422            {423                throw;424            }425            catch (Exception e) // Catch-all OK, 3rd party callout.426            {427                throw NewProviderInvocationException(428                    "GetParentPathProviderException",429                    SessionStateStrings.GetParentPathProviderException,430                    navigationCmdletProvider.ProviderInfo,431                    path,432                    e);433            }434 435            return result;436        }437 438        #endregion GetParentPath439 440        #region NormalizeRelativePath441 442        /// <summary>443        /// Normalizes the path that was passed in and returns the normalized path444        /// as a relative path to the basePath that was passed.445        /// </summary>446        /// <param name="path">447        /// An MSH path to an item. The item should exist448        /// or the provider should write out an error.449        /// </param>450        /// <param name="basePath">451        /// The path that the return value should be relative to.452        /// </param>453        /// <returns>454        /// A normalized path that is relative to the basePath that was passed.455        /// </returns>456        /// <exception cref="ArgumentNullException">457        /// If <paramref name="path"/> is null.458        /// </exception>459        /// <exception cref="NotSupportedException">460        /// If the <paramref name="providerInstance"/> does not support this operation.461        /// </exception>462        /// <exception cref="PipelineStoppedException">463        /// If the pipeline is being stopped while executing the command.464        /// </exception>465        /// <exception cref="ProviderInvocationException">466        /// If the provider threw an exception.467        /// </exception>468        internal string NormalizeRelativePath(string path, string basePath)469        {470            if (path == null)471            {472                throw PSTraceSource.NewArgumentNullException(nameof(path));473            }474 475            CmdletProviderContext context = new CmdletProviderContext(this.ExecutionContext);476 477            string result = NormalizeRelativePath(path, basePath, context);478 479            context.ThrowFirstErrorOrDoNothing();480 481            return result;482        }483 484        /// <summary>485        /// Normalizes the path that was passed in and returns the normalized path486        /// as a relative path to the basePath that was passed.487        /// </summary>488        /// <param name="path">489        /// An MSH path to an item. The item should exist490        /// or the provider should write out an error.491        /// </param>492        /// <param name="basePath">493        /// The path that the return value should be relative to.494        /// </param>495        /// <param name="context">496        /// The context under which the command is running.497        /// </param>498        /// <returns>499        /// A normalized path that is relative to the basePath that was passed.500        /// </returns>501        /// <exception cref="ArgumentNullException">502        /// If <paramref name="path"/> is null.503        /// </exception>504        /// <exception cref="NotSupportedException">505        /// If the <paramref name="providerInstance"/> does not support this operation.506        /// </exception>507        /// <exception cref="PipelineStoppedException">508        /// If the pipeline is being stopped while executing the command.509        /// </exception>510        /// <exception cref="ProviderInvocationException">511        /// If the provider threw an exception.512        /// </exception>513        internal string NormalizeRelativePath(514            string path,515            string basePath,516            CmdletProviderContext context)517        {518            if (path == null)519            {520                throw PSTraceSource.NewArgumentNullException(nameof(path));521            }522 523            CmdletProviderContext getProviderPathContext =524                new CmdletProviderContext(context);525 526            try527            {528                PSDriveInfo drive = null;529                ProviderInfo provider = null;530 531                string workingPath = Globber.GetProviderPath(532                     path,533                     getProviderPathContext,534                     out provider,535                     out drive);536 537                if (getProviderPathContext.HasErrors())538                {539                    getProviderPathContext.WriteErrorsToContext(context);540                    return null;541                }542 543                if (workingPath == null ||544                    provider == null)545                {546                    // Since the provider didn't write an error, and we didn't get any547                    // results ourselves, we need to write out our own error.548 549                    Exception e = PSTraceSource.NewArgumentException(nameof(path));550                    context.WriteError(new ErrorRecord(e, "NormalizePathNullResult", ErrorCategory.InvalidArgument, path));551                    return null;552                }553 554                if (basePath != null)555                {556                    PSDriveInfo baseDrive = null;557                    ProviderInfo baseProvider = null;558 559                    Globber.GetProviderPath(560                         basePath,561                         getProviderPathContext,562                         out baseProvider,563                         out baseDrive);564 565                    if (drive != null && baseDrive != null)566                    {567                        if (!drive.Name.Equals(baseDrive.Name, StringComparison.OrdinalIgnoreCase))568                        {569                            // Make sure they are from physically different drives570                            // Doing StartsWith from both directions covers the following cases571                            // C:\ and C:\Temp572                            // C:\Temp and C:\573                            if (!(drive.Root.StartsWith(baseDrive.Root, StringComparison.OrdinalIgnoreCase) ||574                                (baseDrive.Root.StartsWith(drive.Root, StringComparison.OrdinalIgnoreCase))))575                            {576                                // In this case, no normalization is necessary577                                return path;578                            }579                        }580                    }581                }582 583                if (drive != null)584                {585                    context.Drive = drive;586 587                    // Detect if the original path was already a588                    // provider path. This happens when a drive doesn't589                    // have a rooted root -- such as HKEY_LOCAL_MACHINE instead of590                    // \\HKEY_LOCAL_MACHINE591                    if (592                        (GetProviderInstance(provider) is NavigationCmdletProvider) &&593                        (!string.IsNullOrEmpty(drive.Root)) &&594                        (path.StartsWith(drive.Root, StringComparison.OrdinalIgnoreCase)))595                    {596                        //597                        // If the drive root doesn't end with a path separator then there is a chance the598                        // path starts with the drive root name but doesn't actually refer to it.  For example,599                        // (see Win8 bug 922001) consider drive with root HKEY_LOCAL_MACHINE named600                        // HKEY_LOCAL_MACHINE_foo.  The path would start with the drive root but is not a provider601                        // path.602                        //603                        // We will remediate this by only considering this a provider path if604                        // 1.  The drive root ends with a path separator.605                        // OR606                        // 2.  The path starts with the drive root followed by a path separator607                        // OR608                        // 3.  The path exactly matches the drive root.609                        //610 611                        // 1. Test for the drive root ending with a path separator.612                        bool driveRootEndsWithPathSeparator = IsPathSeparator(drive.Root[drive.Root.Length - 1]);613 614                        // 2. Test for the path starting with the drive root followed by a path separator615                        int indexAfterDriveRoot = drive.Root.Length;616                        bool pathStartsWithDriveRootAndPathSeparator = indexAfterDriveRoot < path.Length && IsPathSeparator(path[indexAfterDriveRoot]);617 618                        // 3. Test for the drive root exactly matching the path.619                        //    Since we know the path starts with the drive root then they are equal if the lengths are equal.620                        bool pathEqualsDriveRoot = drive.Root.Length == path.Length;621 622                        if (driveRootEndsWithPathSeparator || pathStartsWithDriveRootAndPathSeparator || pathEqualsDriveRoot)623                        {624                            workingPath = path;625                        }626                    }627                }628 629                return NormalizeRelativePath(provider, workingPath, basePath, context);630            }631            finally632            {633                getProviderPathContext.RemoveStopReferral();634            }635        }636 637        /// <summary>638        /// Tests the specified character for equality with one of the powershell path separators and639        /// returns true if it matches.640        /// </summary>641        /// <param name="c">The character to test.</param>642        /// <returns>True if the character is a path separator.</returns>643        private static bool IsPathSeparator(char c)644        {645            return c == StringLiterals.DefaultPathSeparator || c == StringLiterals.AlternatePathSeparator;646        }647 648        /// <summary>649        /// Normalizes the path that was passed in and returns the normalized path650        /// as a relative path to the basePath that was passed.651        /// </summary>652        /// <param name="provider">653        /// The provider to use to normalize the path.654        /// </param>655        /// <param name="path">656        /// An provider internal path to normalize.657        /// </param>658        /// <param name="basePath">659        /// The path that the return value should be relative to.660        /// </param>661        /// <param name="context">662        /// The context under which the command is running.663        /// </param>664        /// <returns>665        /// A normalized path that is relative to the basePath that was passed.666        /// </returns>667        /// <exception cref="NotSupportedException">668        /// If the <paramref name="providerInstance"/> does not support this operation.669        /// </exception>670        /// <exception cref="PipelineStoppedException">671        /// If the pipeline is being stopped while executing the command.672        /// </exception>673        /// <exception cref="ProviderInvocationException">674        /// If the provider threw an exception.675        /// </exception>676        internal string NormalizeRelativePath(677            ProviderInfo provider,678            string path,679            string basePath,680            CmdletProviderContext context)681        {682            // All parameters should have been validated by caller683            Dbg.Diagnostics.Assert(684                provider != null,685                "Caller should validate provider before calling this method");686 687            Dbg.Diagnostics.Assert(688                path != null,689                "Caller should validate path before calling this method");690 691            Dbg.Diagnostics.Assert(692                context != null,693                "Caller should validate context before calling this method");694 695            // Get an instance of the provider696 697            Provider.CmdletProvider providerInstance = GetProviderInstance(provider);698 699            NavigationCmdletProvider navigationCmdletProvider = providerInstance as NavigationCmdletProvider;700            if (navigationCmdletProvider != null)701            {702                try703                {704                    path = navigationCmdletProvider.NormalizeRelativePath(path, basePath, context);705                }706                catch (LoopFlowException)707                {708                    throw;709                }710                catch (PipelineStoppedException)711                {712                    throw;713                }714                catch (ActionPreferenceStopException)715                {716                    throw;717                }718                catch (Exception e) // Catch-all OK, 3rd party callout.719                {720                    throw NewProviderInvocationException(721                        "NormalizeRelativePathProviderException",722                    SessionStateStrings.NormalizeRelativePathProviderException,723                        navigationCmdletProvider.ProviderInfo,724                        path,725                        e);726                }727            }728            else if (providerInstance is ContainerCmdletProvider)729            {730                // Do nothing and return the path as-is731            }732            else733            {734                throw PSTraceSource.NewNotSupportedException();735            }736 737            return path;738        }739 740        #endregion NormalizeRelativePath741 742        #region MakePath743 744        /// <summary>745        /// Generates a path from the given parts.746        /// </summary>747        /// <param name="parent">748        /// The parent segment of the path to be joined with the child.749        /// </param>750        /// <param name="child">751        /// The child segment of the ath to be joined with the parent.752        /// </param>753        /// <returns>754        /// The generated path.755        /// </returns>756        /// <exception cref="ArgumentNullException">757        /// If <paramref name="context"/> is null.758        /// </exception>759        /// <exception cref="ArgumentException">760        /// If both <paramref name="parent"/> and <paramref name="child"/> is null.761        /// </exception>762        /// <exception cref="NotSupportedException">763        /// If the <paramref name="providerId"/> does not support this operation.764        /// </exception>765        /// <exception cref="PipelineStoppedException">766        /// If the pipeline is being stopped while executing the command.767        /// </exception>768        /// <exception cref="ProviderInvocationException">769        /// If the provider threw an exception.770        /// </exception>771        internal string MakePath(772            string parent,773            string child)774        {775            CmdletProviderContext context = new CmdletProviderContext(this.ExecutionContext);776 777            return MakePath(parent, child, context);778        }779 780        /// <summary>781        /// Generates a path from the given parts.782        /// </summary>783        /// <param name="parent">784        /// The parent segment of the path to be joined with the child.785        /// </param>786        /// <param name="child">787        /// The child segment of the ath to be joined with the parent.788        /// </param>789        /// <param name="context">790        /// The context which the core command is running.791        /// </param>792        /// <returns>793        /// The generated path.794        /// </returns>795        /// <exception cref="ArgumentNullException">796        /// If <paramref name="context"/> is null.797        /// </exception>798        /// <exception cref="ArgumentException">799        /// If both <paramref name="parent"/> and <paramref name="child"/> is null.800        /// </exception>801        /// <exception cref="NotSupportedException">802        /// If the <paramref name="providerId"/> does not support this operation.803        /// </exception>804        /// <exception cref="PipelineStoppedException">805        /// If the pipeline is being stopped while executing the command.806        /// </exception>807        /// <exception cref="ProviderInvocationException">808        /// If the provider threw an exception.809        /// </exception>810        internal string MakePath(811            string parent,812            string child,813            CmdletProviderContext context)814        {815            string result = null;816 817            if (context == null)818            {819                throw PSTraceSource.NewArgumentNullException(nameof(context));820            }821 822            if (parent == null &&823                child == null)824            {825                throw PSTraceSource.NewArgumentException(nameof(parent));826            }827 828            // Set the drive data for the context829 830            ProviderInfo provider = null;831            if (CurrentDrive != null)832            {833                provider = CurrentDrive.Provider;834            }835 836            if (context.Drive == null)837            {838                bool isProviderQualified = LocationGlobber.IsProviderQualifiedPath(parent);839                bool isAbsolute = LocationGlobber.IsAbsolutePath(parent);840                if (isProviderQualified || isAbsolute)841                {842                    PSDriveInfo drive = null;843 844                    // Ignore the result. Just using this to get the providerId and drive845                    Globber.GetProviderPath(parent, context, out provider, out drive);846 847                    if (drive == null && isProviderQualified)848                    {849                        drive = provider.HiddenDrive;850                    }851 852                    context.Drive = drive;853                }854                else855                {856                    context.Drive = CurrentDrive;857                }858 859                result = MakePath(provider, parent, child, context);860 861                if (isAbsolute)862                {863                    result = LocationGlobber.GetDriveQualifiedPath(result, context.Drive);864                }865                else if (isProviderQualified)866                {867                    result = LocationGlobber.GetProviderQualifiedPath(result, provider);868                }869            }870            else871            {872                provider = context.Drive.Provider;873                result = MakePath(provider, parent, child, context);874            }875 876            return result;877        }878 879        /// <summary>880        /// Uses the specified provider to put the two parts of a path together.881        /// </summary>882        /// <param name="provider">883        /// The provider to use.884        /// </param>885        /// <param name="parent">886        /// The parent part of the path to join with the child.887        /// </param>888        /// <param name="child">889        /// The child part of the path to join with the parent.890        /// </param>891        /// <param name="context">892        /// The context under which the command is running.893        /// </param>894        /// <returns>895        /// The combined path.896        /// </returns>897        /// <exception cref="NotSupportedException">898        /// If the <paramref name="providerId"/> does not support this operation.899        /// </exception>900        /// <exception cref="PipelineStoppedException">901        /// If the pipeline is being stopped while executing the command.902        /// </exception>903        /// <exception cref="ProviderInvocationException">904        /// If the provider threw an exception.905        /// </exception>906        internal string MakePath(907            ProviderInfo provider,908            string parent,909            string child,910            CmdletProviderContext context)911        {912            // All parameters should have been validated by caller913            Dbg.Diagnostics.Assert(914                provider != null,915                "Caller should validate provider before calling this method");916 917            Dbg.Diagnostics.Assert(918                context != null,919                "Caller should validate context before calling this method");920 921            // Get an instance of the provider922 923            Provider.CmdletProvider providerInstance = provider.CreateInstance();924 925            return MakePath(providerInstance, parent, child, context);926        }927 928        /// <summary>929        /// Uses the specified provider to put the two parts of a path together.930        /// </summary>931        /// <param name="providerInstance">932        /// The provider instance to use.933        /// </param>934        /// <param name="parent">935        /// The parent part of the path to join with the child.936        /// </param>937        /// <param name="child">938        /// The child part of the path to join with the parent.939        /// </param>940        /// <param name="context">941        /// The context under which the command is running.942        /// </param>943        /// <returns>944        /// The combined path.945        /// </returns>946        /// <exception cref="NotSupportedException">947        /// If the <paramref name="providerId"/> does not support this operation.948        /// </exception>949        /// <exception cref="PipelineStoppedException">950        /// If the pipeline is being stopped while executing the command.951        /// </exception>952        /// <exception cref="ProviderInvocationException">953        /// If the provider threw an exception.954        /// </exception>955        internal string MakePath(956            CmdletProvider providerInstance,957            string parent,958            string child,959            CmdletProviderContext context)960        {961            // All parameters should have been validated by caller962            Dbg.Diagnostics.Assert(963                providerInstance != null,964                "Caller should validate providerInstance before calling this method");965 966            Dbg.Diagnostics.Assert(967                context != null,968                "Caller should validate context before calling this method");969 970            // Get an instance of the provider971 972            string result = null;973 974            NavigationCmdletProvider navigationCmdletProvider = providerInstance as NavigationCmdletProvider;975 976            if (navigationCmdletProvider != null)977            {978                try979                {980                    result = navigationCmdletProvider.MakePath(parent, child, context);981                }982                catch (LoopFlowException)983                {984                    throw;985                }986                catch (PipelineStoppedException)987                {988                    throw;989                }990                catch (ActionPreferenceStopException)991                {992                    throw;993                }994                catch (Exception e) // Catch-all OK, 3rd party callout.995                {996                    throw NewProviderInvocationException(997                        "MakePathProviderException",998                        SessionStateStrings.MakePathProviderException,999                        navigationCmdletProvider.ProviderInfo,1000                        parent,1001                        e);1002                }1003            }1004            else if (providerInstance is ContainerCmdletProvider)1005            {1006                result = child;1007            }1008            else1009            {1010                throw PSTraceSource.NewNotSupportedException();1011            }1012 1013            return result;1014        }1015 1016        #endregion MakePath1017 1018        #region GetChildName1019 1020        /// <summary>1021        /// Gets the name of the leaf element in the specified path.1022        /// </summary>1023        /// <param name="path">1024        /// The fully qualified path to the item1025        /// </param>1026        /// <returns>1027        /// The leaf element in the path.1028        /// </returns>1029        /// <exception cref="ArgumentNullException">1030        /// If <paramref name="path"/> is null.1031        /// </exception>1032        /// <exception cref="ProviderNotFoundException">1033        /// If the <paramref name="path"/> refers to a provider that could not be found.1034        /// </exception>1035        /// <exception cref="DriveNotFoundException">1036        /// If the <paramref name="path"/> refers to a drive that could not be found.1037        /// </exception>1038        /// <exception cref="NotSupportedException">1039        /// If the provider that the <paramref name="path"/> refers to does1040        /// not support this operation.1041        /// </exception>1042        /// <exception cref="ProviderInvocationException">1043        /// If the provider threw an exception.1044        /// </exception>1045        internal string GetChildName(string path)1046        {1047            if (path == null)1048            {1049                throw PSTraceSource.NewArgumentNullException(nameof(path));1050            }1051 1052            CmdletProviderContext context = new CmdletProviderContext(this.ExecutionContext);1053 1054            string result = GetChildName(path, context);1055 1056            context.ThrowFirstErrorOrDoNothing();1057 1058            return result;1059        }1060 1061        /// <summary>1062        /// Gets the name of the leaf element in the specified path.1063        /// </summary>1064        /// <param name="path">1065        /// The fully qualified path to the item1066        /// </param>1067        /// <param name="context">1068        /// The context which the core command is running.1069        /// </param>1070        /// <returns>1071        /// The leaf element in the path.1072        /// </returns>1073        /// <exception cref="ArgumentNullException">1074        /// If <paramref name="path"/> is null.1075        /// </exception>1076        /// <exception cref="ProviderNotFoundException">1077        /// If the <paramref name="path"/> refers to a provider that could not be found.1078        /// </exception>1079        /// <exception cref="DriveNotFoundException">1080        /// If the <paramref name="path"/> refers to a drive that could not be found.1081        /// </exception>1082        /// <exception cref="NotSupportedException">1083        /// If the provider that the <paramref name="path"/> refers to does1084        /// not support this operation.1085        /// </exception>1086        /// <exception cref="ProviderInvocationException">1087        /// If the provider threw an exception.1088        /// </exception>1089        internal string GetChildName(1090            string path,1091            CmdletProviderContext context)1092        {1093            return GetChildName(path, context, false);1094        }1095 1096        /// <summary>1097        /// Gets the name of the leaf element in the specified path.1098        /// Allow to use FileSystem as the default provider when the1099        /// given path is drive-qualified and the drive cannot be found.1100        /// </summary>1101        /// <param name="path">1102        /// The fully qualified path to the item1103        /// </param>1104        /// <param name="context">1105        /// The context which the core command is running.1106        /// </param>1107        /// <param name="useDefaultProvider">1108        /// to use default provider when needed.1109        /// </param>1110        /// <returns>1111        /// The leaf element in the path.1112        /// </returns>1113        internal string GetChildName(1114            string path,1115            CmdletProviderContext context,1116            bool useDefaultProvider)1117        {1118            if (path == null)1119            {1120                throw PSTraceSource.NewArgumentNullException(nameof(path));1121            }1122 1123            PSDriveInfo drive = null;1124            ProviderInfo provider = null;1125            string workingPath = null;1126 1127            try1128            {1129                workingPath = Globber.GetProviderPath(path, context, out provider, out drive);1130            }1131            catch (DriveNotFoundException)1132            {1133                // the path is sure to be drive_qualified and it is an absolute path, otherwise the1134                // drive would be set to the current drive and the DriveNotFoundException will not happen.1135                if (useDefaultProvider)1136                {1137                    // the default provider is FileSystem1138                    provider = PublicSessionState.Internal.GetSingleProvider(Microsoft.PowerShell.Commands.FileSystemProvider.ProviderName);1139 1140                    workingPath = path.Replace(StringLiterals.AlternatePathSeparator, StringLiterals.DefaultPathSeparator);1141                    workingPath = workingPath.TrimEnd(StringLiterals.DefaultPathSeparator);1142                }1143                else1144                {1145                    throw;1146                }1147            }1148 1149            Dbg.Diagnostics.Assert(1150                workingPath != null,1151                "There should always be a way to generate a UniversalResourceName for a " +1152                "given path");1153 1154            Dbg.Diagnostics.Assert(1155                provider != null,1156            "There should always be a way to get the provider ID for a given path or else GetProviderPath should have thrown an exception");1157 1158            if (drive != null)1159            {1160                context.Drive = drive;1161            }1162 1163            return GetChildName(provider, workingPath, context);1164        }1165 1166        /// <summary>1167        /// Gets the leaf element of the specified path.1168        /// </summary>1169        /// <param name="provider">1170        /// The provider to use.1171        /// </param>1172        /// <param name="path">1173        /// The path to the item if it was specified on the command line.1174        /// </param>1175        /// <param name="context">1176        /// The context which the core command is running.1177        /// </param>1178        /// <exception cref="NotSupportedException">1179        /// If the <paramref name="providerInstance"/> does not support this operation.1180        /// </exception>1181        /// <exception cref="PipelineStoppedException">1182        /// If the pipeline is being stopped while executing the command.1183        /// </exception>1184        /// <exception cref="ProviderInvocationException">1185        /// If the provider threw an exception.1186        /// </exception>1187        private string GetChildName(1188            ProviderInfo provider,1189            string path,1190            CmdletProviderContext context)1191        {1192            // All parameters should have been validated by caller1193            Dbg.Diagnostics.Assert(1194                provider != null,1195                "Caller should validate provider before calling this method");1196 1197            Dbg.Diagnostics.Assert(1198                path != null,1199                "Caller should validate path before callin g this method");1200 

Showing the first 1,200 of 1751 lines. Download the file for the rest.