diff --git a/src/Microsoft.PackageManagement.CoreProviders/Bootstrap/BootstrapRequest.cs b/src/Microsoft.PackageManagement.CoreProviders/Bootstrap/BootstrapRequest.cs index 09cf02ca3..537129985 100644 --- a/src/Microsoft.PackageManagement.CoreProviders/Bootstrap/BootstrapRequest.cs +++ b/src/Microsoft.PackageManagement.CoreProviders/Bootstrap/BootstrapRequest.cs @@ -79,8 +79,6 @@ namespace Microsoft.PackageManagement.Providers.Internal.Bootstrap { return Enumerable.Empty(); } -#if !PORTABLE - // we don't do bootstrap on core powershell if (!System.Net.NetworkInformation.NetworkInterface.GetIsNetworkAvailable()) { Warning(Constants.Messages.NetworkNotAvailable); Warning(string.Format(CultureInfo.CurrentCulture, Resources.Messages.ProviderBootstrapFailed)); @@ -96,7 +94,6 @@ namespace Microsoft.PackageManagement.Providers.Internal.Bootstrap { Warning(Constants.Messages.ProviderSwidtagUnavailable); return Enumerable.Empty(); } -#endif } return _feeds; } @@ -507,10 +504,6 @@ namespace Microsoft.PackageManagement.Providers.Internal.Bootstrap { /// internal Package GetProviderFromFile(string filePath, bool copyFileToTemp = false, bool suppressErrorsAndWarnings = false) { -#if PORTABLE - // not supported on core powershell - return null; -#else if (string.IsNullOrWhiteSpace(filePath) && !System.IO.File.Exists(filePath)) { Warning(Constants.Messages.FileNotFound, filePath); return null; @@ -571,7 +564,6 @@ namespace Microsoft.PackageManagement.Providers.Internal.Bootstrap { } return null; -#endif } /// @@ -700,4 +692,4 @@ namespace Microsoft.PackageManagement.Providers.Internal.Bootstrap { } } } -} +} \ No newline at end of file diff --git a/src/Microsoft.PackageManagement.MetaProvider.PowerShell/PowerShellMetaProvider.cs b/src/Microsoft.PackageManagement.MetaProvider.PowerShell/PowerShellMetaProvider.cs index 99b692ce1..56b2d98b0 100644 --- a/src/Microsoft.PackageManagement.MetaProvider.PowerShell/PowerShellMetaProvider.cs +++ b/src/Microsoft.PackageManagement.MetaProvider.PowerShell/PowerShellMetaProvider.cs @@ -134,8 +134,6 @@ namespace Microsoft.PackageManagement.MetaProvider.PowerShell.Internal { if (_baseFolder == null || !Directory.Exists(_baseFolder)) { throw new Exception(Resources.Messages.CantFindBasePowerShellModuleFolder); } - - _baseFolder = Path.Combine(_baseFolder, "Modules", "PackageManagement"); } return _baseFolder; } @@ -829,4 +827,4 @@ namespace Microsoft.PackageManagement.MetaProvider.PowerShell.Internal { } } } -} +} \ No newline at end of file diff --git a/src/Microsoft.PackageManagement.NuGetProvider/NugetLightClient.cs b/src/Microsoft.PackageManagement.NuGetProvider/NugetLightClient.cs index 4d4750b27..70c3fcdc9 100644 --- a/src/Microsoft.PackageManagement.NuGetProvider/NugetLightClient.cs +++ b/src/Microsoft.PackageManagement.NuGetProvider/NugetLightClient.cs @@ -480,7 +480,7 @@ HashSet temporarilyMarked = new HashSet(new PackageItemComparer()); // checks that there are no dependency loop - hasDependencyLoop = !DepthFirstVisit(packageItem, temporarilyMarked, permanentlyMarked, dependencyToBeInstalled, new HashSet(), request); + hasDependencyLoop = !DepthFirstVisit(packageItem, temporarilyMarked, permanentlyMarked, dependencyToBeInstalled, request); if (!hasDependencyLoop) { @@ -502,10 +502,9 @@ /// /// /// - /// /// /// - internal static bool DepthFirstVisit(PackageItem packageItem, HashSet temporarilyMarked, HashSet permanentlyMarked, List dependencyToBeInstalled, HashSet processedDependencies, NuGetRequest request) + internal static bool DepthFirstVisit(PackageItem packageItem, HashSet temporarilyMarked, HashSet permanentlyMarked, List dependencyToBeInstalled, NuGetRequest request) { // dependency loop detected because the element is temporarily marked if (temporarilyMarked.Contains(packageItem)) @@ -524,9 +523,9 @@ temporarilyMarked.Add(packageItem); // Visit the dependency - foreach (var dependency in GetPackageDependenciesHelper(packageItem, processedDependencies, request)) + foreach (var dependency in GetPackageDependenciesHelper(packageItem, request)) { - if (!DepthFirstVisit(dependency, temporarilyMarked, permanentlyMarked, dependencyToBeInstalled, processedDependencies, request)) + if (!DepthFirstVisit(dependency, temporarilyMarked, permanentlyMarked, dependencyToBeInstalled, request)) { // if dfs returns false then we have encountered a loop return false; @@ -550,9 +549,8 @@ /// Returns the package dependencies of packageItem. We only return the dependencies that are not installed in the destination folder of request /// /// - /// /// - private static IEnumerable GetPackageDependenciesHelper(PackageItem packageItem, HashSet processedDependencies, NuGetRequest request) + private static IEnumerable GetPackageDependenciesHelper(PackageItem packageItem, NuGetRequest request) { if (packageItem.Package.DependencySetList == null) { @@ -569,13 +567,6 @@ foreach (var dep in depSet.Dependencies) { - var depKey = string.Format(CultureInfo.InvariantCulture, "{0}!#!{1}", dep.Id, dep.DependencyVersion.ToStringSafe()); - - if (processedDependencies.Contains(depKey)) - { - continue; - } - // Get the min dependencies version string minVersion = dep.DependencyVersion.MinVersion.ToStringSafe(); @@ -626,8 +617,6 @@ if (installed) { - // already processed this so don't need to do this next time - processedDependencies.Add(dep.Id); request.Verbose(String.Format(CultureInfo.CurrentCulture, Messages.AlreadyInstalled, dep.Id)); // already have a dependency so move on continue; @@ -645,9 +634,7 @@ } // Get the package that is the latest version - yield return dependentPackageItem.OrderByDescending(each => each.Version).FirstOrDefault(); - - processedDependencies.Add(depKey); + yield return dependentPackageItem.OrderByDescending(each => each.Version).FirstOrDefault(); } } } diff --git a/src/Microsoft.PackageManagement.NuGetProvider/NugetLightRequest.cs b/src/Microsoft.PackageManagement.NuGetProvider/NugetLightRequest.cs index 5bc0aa951..4cc643090 100644 --- a/src/Microsoft.PackageManagement.NuGetProvider/NugetLightRequest.cs +++ b/src/Microsoft.PackageManagement.NuGetProvider/NugetLightRequest.cs @@ -20,8 +20,6 @@ using System.Net; using Microsoft.PackageManagement.Provider.Utility; - using SemanticVersion = Microsoft.PackageManagement.Provider.Utility.SemanticVersion; - /// /// This class drives the Request class that is an interface exposed from the PackageManagement Platform to the provider to use. /// @@ -173,10 +171,6 @@ // or $env:programfiles\NuGet\Packages\ if you are an admin. try { -#if UNIX - // there is only 1 installation location by default for linux ("HOME/.local/share/powershell/PackageManagement/NuGet/Packages") - string basePath = CurrentUserDefaultInstallLocation; -#else var scope = (Scope == null) ? null : Scope.Value; scope = string.IsNullOrWhiteSpace(scope) ? Constants.AllUsers : scope; string basePath; @@ -198,7 +192,6 @@ Constants.Messages.InstallRequiresCurrentUserScopeParameterForNonAdminUser, AllUserDefaultInstallLocation, CurrentUserDefaultInstallLocation); return string.Empty; } -#endif if (!Directory.Exists(basePath)) { @@ -222,11 +215,7 @@ get { #if CORECLR -#if UNIX - return Path.Combine(Path.GetDirectoryName(Platform.SelectProductNameForDirectory(Platform.XDG_Type.DATA)), "PackageManagement", "NuGet", "Packages"); -#else return Path.Combine(Environment.GetEnvironmentVariable("LocalAppData"), "PackageManagement", "NuGet", "Packages"); -#endif #else return Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData), "PackageManagement", "NuGet", "Packages"); #endif @@ -239,11 +228,7 @@ get { #if CORECLR -#if UNIX - return Path.Combine(Path.GetDirectoryName(Platform.SelectProductNameForDirectory(Platform.XDG_Type.DATA)), "PackageManagement", "NuGet", "Packages"); -#else return Path.Combine(Environment.GetEnvironmentVariable("ProgramFiles"), "NuGet", "Packages"); -#endif #else return Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ProgramFiles), "NuGet", "Packages"); #endif @@ -1304,11 +1289,7 @@ } } else { -#if UNIX - var appdataFolder = Path.GetDirectoryName(Platform.SelectProductNameForDirectory(Platform.XDG_Type.CONFIG)); -#else var appdataFolder = Environment.GetEnvironmentVariable("appdata"); -#endif _configurationFileLocation = Path.Combine(appdataFolder, "NuGet", NuGetConstant.SettingsFileName); //create directory if does not exist diff --git a/src/Microsoft.PackageManagement.NuGetProvider/Repository/PackageRepositoryFactory.cs b/src/Microsoft.PackageManagement.NuGetProvider/Repository/PackageRepositoryFactory.cs index 4ff0fe9cb..771651e32 100644 --- a/src/Microsoft.PackageManagement.NuGetProvider/Repository/PackageRepositoryFactory.cs +++ b/src/Microsoft.PackageManagement.NuGetProvider/Repository/PackageRepositoryFactory.cs @@ -19,12 +19,6 @@ throw new ArgumentNullException("packageSource"); } - // we cannot call new uri on file path on linux because it will error out - if (System.IO.Directory.Exists(packageSource)) - { - return new LocalPackageRepository(packageSource, request); - } - Uri uri = new Uri(packageSource); if (uri.IsFile) diff --git a/src/Microsoft.PackageManagement.NuGetProvider/nugetlightprovider.cs b/src/Microsoft.PackageManagement.NuGetProvider/nugetlightprovider.cs index 5bc32760e..b21a211ca 100644 --- a/src/Microsoft.PackageManagement.NuGetProvider/nugetlightprovider.cs +++ b/src/Microsoft.PackageManagement.NuGetProvider/nugetlightprovider.cs @@ -11,8 +11,6 @@ namespace Microsoft.PackageManagement.NuGetProvider using System.Reflection; using System.Management.Automation; - using SemanticVersion = Microsoft.PackageManagement.Provider.Utility.SemanticVersion; - /// /// A Package provider to the PackageManagement Platform. /// diff --git a/src/Microsoft.PackageManagement.PackageSourceListProvider/Extensions/PackageListExtensions.cs b/src/Microsoft.PackageManagement.PackageSourceListProvider/Extensions/PackageListExtensions.cs index bb7a4db32..f57e4ab32 100644 --- a/src/Microsoft.PackageManagement.PackageSourceListProvider/Extensions/PackageListExtensions.cs +++ b/src/Microsoft.PackageManagement.PackageSourceListProvider/Extensions/PackageListExtensions.cs @@ -1,6 +1,4 @@ -#if !UNIX - -// Copyright (c) .NET Foundation. All rights reserved. +// Copyright (c) .NET Foundation. All rights reserved. // Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. using System; @@ -92,5 +90,3 @@ namespace Microsoft.PackageManagement.PackageSourceListProvider } } } - -#endif diff --git a/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/ExePackageInstaller.cs b/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/ExePackageInstaller.cs index 18e6ca1d7..4874e915d 100644 --- a/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/ExePackageInstaller.cs +++ b/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/ExePackageInstaller.cs @@ -1,6 +1,4 @@ -#if !UNIX - -// +// // Copyright (c) Microsoft Corporation. All rights reserved. // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. @@ -29,7 +27,6 @@ namespace Microsoft.PackageManagement.PackageSourceListProvider using Microsoft.PackageManagement.Provider.Utility; using Microsoft.Win32; using ErrorCategory = PackageManagement.Internal.ErrorCategory; - using SemanticVersion = Microsoft.PackageManagement.Provider.Utility.SemanticVersion; internal static class ExePackageInstaller { @@ -592,6 +589,4 @@ namespace Microsoft.PackageManagement.PackageSourceListProvider // TODO do we need to support save-package for executable packages? } } -} - -#endif \ No newline at end of file +} \ No newline at end of file diff --git a/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/NupkgInstaller.cs b/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/NupkgInstaller.cs index 30e538785..3e8bedeb6 100644 --- a/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/NupkgInstaller.cs +++ b/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/NupkgInstaller.cs @@ -1,6 +1,4 @@ -#if !UNIX - -// +// // Copyright (c) Microsoft Corporation. All rights reserved. // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. @@ -27,7 +25,6 @@ namespace Microsoft.PackageManagement.PackageSourceListProvider using Microsoft.PackageManagement.Provider.Utility; using ErrorCategory = PackageManagement.Internal.ErrorCategory; using System.Globalization; - using SemanticVersion = Microsoft.PackageManagement.Provider.Utility.SemanticVersion; internal static class NupkgInstaller { @@ -235,6 +232,4 @@ namespace Microsoft.PackageManagement.PackageSourceListProvider } } } -} - -#endif \ No newline at end of file +} \ No newline at end of file diff --git a/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PackageListParser.cs b/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PackageListParser.cs index a20856c2d..c5ca6e69b 100644 --- a/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PackageListParser.cs +++ b/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PackageListParser.cs @@ -1,6 +1,4 @@ -#if !UNIX - -using System; +using System; using System.Collections.Generic; using System.Linq; using System.IO; @@ -9,8 +7,6 @@ using Microsoft.PackageManagement.Provider.Utility; using System.Reflection; using System.Globalization; -using SemanticVersion = Microsoft.PackageManagement.Provider.Utility.SemanticVersion; - namespace Microsoft.PackageManagement.PackageSourceListProvider { internal static class JsonParser @@ -140,7 +136,7 @@ namespace Microsoft.PackageManagement.PackageSourceListProvider } else { - throw new ArgumentException(string.Format("'{0}' is not referencd but not defined in the file '{1}'", dep.Name, package.FilePath)); + throw new FileFormatException(string.Format("'{0}' is not referencd but not defined in the file '{1}'", dep.Name, package.FilePath)); } } @@ -347,9 +343,9 @@ namespace Microsoft.PackageManagement.PackageSourceListProvider if (!uri.IsFile) { - if (uri.Scheme != "https") + if (uri.Scheme != Uri.UriSchemeHttps) { - throw new ArgumentException(string.Format(CultureInfo.CurrentCulture, Resources.Messages.UriSchemeNotSupported, uri.Scheme, "https")); + throw new ArgumentException(string.Format(CultureInfo.CurrentCulture, Resources.Messages.UriSchemeNotSupported, uri.Scheme, Uri.UriSchemeHttps)); } } @@ -494,5 +490,3 @@ namespace Microsoft.PackageManagement.PackageSourceListProvider } } } - -#endif \ No newline at end of file diff --git a/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PackageListProvider.cs b/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PackageListProvider.cs index 8e4fe99d7..21fe11146 100644 --- a/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PackageListProvider.cs +++ b/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PackageListProvider.cs @@ -1,6 +1,4 @@ -#if !UNIX - -// +// // Copyright (c) Microsoft Corporation. All rights reserved. // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. @@ -940,6 +938,4 @@ namespace Microsoft.PackageManagement.PackageSourceListProvider } } -} - -#endif \ No newline at end of file +} \ No newline at end of file diff --git a/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PackageListRequest.cs b/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PackageListRequest.cs index 4c8282017..c3aa9d3ed 100644 --- a/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PackageListRequest.cs +++ b/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PackageListRequest.cs @@ -1,5 +1,3 @@ -#if !UNIX - // // Copyright (c) Microsoft Corporation. All rights reserved. // Licensed under the Apache License, Version 2.0 (the "License"); @@ -34,7 +32,6 @@ namespace Microsoft.PackageManagement.PackageSourceListProvider using Microsoft.PackageManagement.Implementation; using Microsoft.PackageManagement.Internal.Api; using Microsoft.PackageManagement.Provider.Utility; - using SemanticVersion = Microsoft.PackageManagement.Provider.Utility.SemanticVersion; public abstract class PackageSourceListRequest : Request { @@ -1076,6 +1073,4 @@ namespace Microsoft.PackageManagement.PackageSourceListProvider } } } -} - -#endif \ No newline at end of file +} \ No newline at end of file diff --git a/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PackageQuery.cs b/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PackageQuery.cs index 81947104d..8f425211f 100644 --- a/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PackageQuery.cs +++ b/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PackageQuery.cs @@ -1,6 +1,4 @@ -#if !UNIX - -// +// // Copyright (c) Microsoft Corporation. All rights reserved. // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. @@ -172,5 +170,3 @@ namespace Microsoft.PackageManagement.PackageSourceListProvider } } } - -#endif \ No newline at end of file diff --git a/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PackageSource.cs b/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PackageSource.cs index 51921a434..7e84a7278 100644 --- a/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PackageSource.cs +++ b/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PackageSource.cs @@ -1,6 +1,4 @@ -#if !UNIX - -// +// // Copyright (c) Microsoft Corporation. All rights reserved. // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. @@ -43,5 +41,3 @@ namespace Microsoft.PackageManagement.PackageSourceListProvider } } } - -#endif \ No newline at end of file diff --git a/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PowerShellArtifactInstaller.cs b/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PowerShellArtifactInstaller.cs index d7026a148..547d14c00 100644 --- a/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PowerShellArtifactInstaller.cs +++ b/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/PowerShellArtifactInstaller.cs @@ -1,6 +1,4 @@ -#if !UNIX - -// +// // Copyright (c) Microsoft Corporation. All rights reserved. // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. @@ -199,6 +197,4 @@ namespace Microsoft.PackageManagement.PackageSourceListProvider } } -} - -#endif \ No newline at end of file +} \ No newline at end of file diff --git a/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/ProgressTracker.cs b/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/ProgressTracker.cs index 8421ba006..711ae473e 100644 --- a/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/ProgressTracker.cs +++ b/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/ProgressTracker.cs @@ -1,6 +1,4 @@ -#if !UNIX - -// +// // Copyright (c) Microsoft Corporation. All rights reserved. // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. @@ -53,5 +51,3 @@ namespace Microsoft.PackageManagement.PackageSourceListProvider } } } - -#endif \ No newline at end of file diff --git a/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/WebDownloader.cs b/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/WebDownloader.cs index fab3e4bcb..6ea213412 100644 --- a/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/WebDownloader.cs +++ b/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/WebDownloader.cs @@ -1,6 +1,4 @@ -#if !UNIX - -// +// // Copyright (c) Microsoft Corporation. All rights reserved. // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. @@ -301,5 +299,3 @@ namespace Microsoft.PackageManagement.PackageSourceListProvider } } } - -#endif diff --git a/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/ZipPackageInstaller.cs b/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/ZipPackageInstaller.cs index 00791fee3..6c2346f9d 100644 --- a/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/ZipPackageInstaller.cs +++ b/src/Microsoft.PackageManagement.PackageSourceListProvider/PackageList/ZipPackageInstaller.cs @@ -1,6 +1,4 @@ -#if !UNIX - -// +// // Copyright (c) Microsoft Corporation. All rights reserved. // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. @@ -212,6 +210,4 @@ namespace Microsoft.PackageManagement.PackageSourceListProvider } } -} - -#endif \ No newline at end of file +} \ No newline at end of file diff --git a/src/Microsoft.PackageManagement.PackageSourceListProvider/Sdk/Constants.cs b/src/Microsoft.PackageManagement.PackageSourceListProvider/Sdk/Constants.cs index ee97a4fc4..b55586362 100644 --- a/src/Microsoft.PackageManagement.PackageSourceListProvider/Sdk/Constants.cs +++ b/src/Microsoft.PackageManagement.PackageSourceListProvider/Sdk/Constants.cs @@ -1,4 +1,3 @@ -#if !UNIX namespace Microsoft.PackageManagement.PackageSourceListProvider { @@ -160,5 +159,3 @@ namespace Microsoft.PackageManagement.PackageSourceListProvider #endregion } } - -#endif \ No newline at end of file diff --git a/src/Microsoft.PackageManagement/Implementation/PackageManagementService.cs b/src/Microsoft.PackageManagement/Implementation/PackageManagementService.cs index a081161dc..e4fc27bf8 100644 --- a/src/Microsoft.PackageManagement/Implementation/PackageManagementService.cs +++ b/src/Microsoft.PackageManagement/Implementation/PackageManagementService.cs @@ -857,11 +857,6 @@ namespace Microsoft.PackageManagement.Internal.Implementation { Version maximumVersion, ProviderOption providerOption = ProviderOption.LatestVersion) { -#if PORTABLE - return Enumerable.Empty(); -#else - //We don't need to scan provider assemblies on corepowershell. - //if provider is installed in providername\version format var providerFolder = ProviderAssembliesLocation.Distinct(new PathEqualityComparer(PathCompareOption.Full)).SelectMany(Directory.EnumerateDirectories); @@ -967,20 +962,16 @@ namespace Microsoft.PackageManagement.Internal.Implementation { } } } -#endif } //Return all providers under the providerAssemblies folder internal IEnumerable AllProvidersFromProviderAssembliesLocation(IHostApi request) { -#if !PORTABLE - // don't need this for core powershell try { return ScanAllProvidersFromProviderAssembliesLocation(request, null, null, null, null, ProviderOption.AllProvider).WhereNotNull().ToArray(); } catch (Exception ex) { request.Debug(ex.Message); } -#endif return Enumerable.Empty(); } @@ -988,8 +979,6 @@ namespace Microsoft.PackageManagement.Internal.Implementation { //return the providers with latest version under the providerAssemblies folder //This method only gets called during the initialization, i.e. LoadProviders(). private IEnumerable ProvidersWithLatestVersionFromProviderAssembliesLocation(IHostApi request) { -#if !PORTABLE - // don't need this for core powershell try { var providerPaths = ScanAllProvidersFromProviderAssembliesLocation(request, null, null, null, null, ProviderOption.LatestVersion).WhereNotNull().ToArray(); @@ -1022,8 +1011,6 @@ namespace Microsoft.PackageManagement.Internal.Implementation { { request.Debug(ex.Message); } -#endif - return Enumerable.Empty(); } @@ -1042,14 +1029,28 @@ namespace Microsoft.PackageManagement.Internal.Implementation { .Concat(GetProvidersFromRegistry(Registry.LocalMachine, "SOFTWARE\\MICROSOFT\\PACKAGEMANAGEMENT")) .Concat(GetProvidersFromRegistry(Registry.CurrentUser, "SOFTWARE\\MICROSOFT\\PACKAGEMANAGEMENT")); + providerAssemblies = providerAssemblies.Concat(ProvidersWithLatestVersionFromProviderAssembliesLocation(request)); + +#if DEEP_DEBUG + providerAssemblies = providerAssemblies.ToArray(); + + foreach (var each in providerAssemblies) { + request.Debug("possible assembly: {0}".format(each)); + } +#endif + + // find modules that have manifests + // todo: expand this out to validate the assembly is ok for this instance of PackageManagement. + providerAssemblies = providerAssemblies.Where(each => Manifest.LoadFrom(each).Any(manifest => Swidtag.IsSwidtag(manifest) && new Swidtag(manifest).IsApplicable(new Hashtable()))); + + // add inbox assemblies (don't require manifests, because they are versioned with the core) + #if !COMMUNITY_BUILD // todo: these should just be strong-named references. for now, just load them from the same directory. providerAssemblies = providerAssemblies.Concat(new[] { Path.Combine(BaseDir, "Microsoft.PackageManagement.MetaProvider.PowerShell.dll"), Path.Combine(BaseDir, "Microsoft.PackageManagement.ArchiverProviders.dll"), - Path.Combine(BaseDir, "Microsoft.PackageManagement.CoreProviders.dll"), - Path.Combine(BaseDir, "Microsoft.PackageManagement.NuGetProvider.dll"), - Path.Combine(BaseDir, "Microsoft.PackageManagement.PackageSourceListProvider.dll"), + Path.Combine(BaseDir, "Microsoft.PackageManagement.CoreProviders.dll"), #if !CORECLR Path.Combine(BaseDir, "Microsoft.PackageManagement.MsuProvider.dll"), Path.Combine(BaseDir, "Microsoft.PackageManagement.MsiProvider.dll") @@ -1057,6 +1058,14 @@ namespace Microsoft.PackageManagement.Internal.Implementation { }); #endif +#if DEEP_DEBUG + providerAssemblies = providerAssemblies.ToArray(); + + foreach (var each in providerAssemblies) { + request.Debug("possible assembly with manifest: {0}".format(each)); + } +#endif + providerAssemblies = providerAssemblies.OrderByDescending(each => { try { // try to get a version from the file first @@ -1602,4 +1611,4 @@ namespace Microsoft.PackageManagement.Internal.Implementation { return found; } } -} +} \ No newline at end of file diff --git a/src/Microsoft.PackageManagement/Implementation/ProviderBase.cs b/src/Microsoft.PackageManagement/Implementation/ProviderBase.cs index 8228efd11..188b743ea 100644 --- a/src/Microsoft.PackageManagement/Implementation/ProviderBase.cs +++ b/src/Microsoft.PackageManagement/Implementation/ProviderBase.cs @@ -81,7 +81,6 @@ namespace Microsoft.PackageManagement.Internal.Implementation { /// public void SetSwidTag(string providerPath) { -#if !UNIX if (!string.IsNullOrWhiteSpace(providerPath)) { // check whether there is swidtag attached to the provider path @@ -93,7 +92,6 @@ namespace Microsoft.PackageManagement.Internal.Implementation { SetSwidTag(new XDocument(new XDeclaration("1.0", "UTF-8", "yes"), swid)); } } -#endif } public IEnumerable SupportedFileExtensions { @@ -209,4 +207,4 @@ namespace Microsoft.PackageManagement.Internal.Implementation { return new DynamicOptionRequestObject(this, requestObject, request => Provider.GetDynamicOptions(category.ToString(), request), category); } } -} +} \ No newline at end of file diff --git a/src/Microsoft.PackageManagement/Implementation/ProviderServicesImpl.cs b/src/Microsoft.PackageManagement/Implementation/ProviderServicesImpl.cs index 8065f479b..ae3b2e482 100644 --- a/src/Microsoft.PackageManagement/Implementation/ProviderServicesImpl.cs +++ b/src/Microsoft.PackageManagement/Implementation/ProviderServicesImpl.cs @@ -176,13 +176,9 @@ namespace Microsoft.PackageManagement.Internal.Implementation { Debug(request, "Calling 'ProviderService::IsSignedAndTrusted, '{0}'", filename); - // we are not using this function anywhere -#if !UNIX var wtd = new WinTrustData(filename); - var result = NativeMethods.WinVerifyTrust(new IntPtr(-1), new Guid("{00AAC56B-CD44-11d0-8CC2-00C04FC295EE}"), wtd); return result == WinVerifyTrustResult.Success; -#endif } return false; } @@ -190,14 +186,9 @@ namespace Microsoft.PackageManagement.Internal.Implementation { public int StartProcess(string filename, string arguments, bool requiresElevation, out string standardOutput, IRequest requestObject) { Process p = new Process(); -#if !CORECLR - if (requiresElevation) - { + if (requiresElevation) { p.StartInfo.UseShellExecute = true; - } - else -#endif - { + } else { p.StartInfo.UseShellExecute = false; p.StartInfo.RedirectStandardOutput = true; } @@ -242,4 +233,4 @@ namespace Microsoft.PackageManagement.Internal.Implementation { return request.Debug(request.FormatMessageString(messageText, args)); } } -} +} \ No newline at end of file diff --git a/src/Microsoft.PackageManagement/Utility/Extensions/ExceptionExtensions.cs b/src/Microsoft.PackageManagement/Utility/Extensions/ExceptionExtensions.cs index ef5b600b3..dc2c842af 100644 --- a/src/Microsoft.PackageManagement/Utility/Extensions/ExceptionExtensions.cs +++ b/src/Microsoft.PackageManagement/Utility/Extensions/ExceptionExtensions.cs @@ -19,11 +19,9 @@ namespace Microsoft.PackageManagement.Internal.Utility.Extensions { internal static class ExceptionExtensions { public static void Dump(this Exception e) { -#if !UNIX var text = string.Format(CultureInfo.CurrentCulture, "{0}/{1}\r\n{2}", e.GetType().Name, e.Message, e.StackTrace); // for now, this is the only way we'll see exceptions in the wild. NativeMethods.OutputDebugString(text); -#endif } #if DETAILED_DEBUG @@ -37,4 +35,4 @@ namespace Microsoft.PackageManagement.Internal.Utility.Extensions { } #endif } -} +} \ No newline at end of file diff --git a/src/Microsoft.PackageManagement/Utility/Extensions/FilesystemExtensions.cs b/src/Microsoft.PackageManagement/Utility/Extensions/FilesystemExtensions.cs index 74888c932..2c97c5048 100644 --- a/src/Microsoft.PackageManagement/Utility/Extensions/FilesystemExtensions.cs +++ b/src/Microsoft.PackageManagement/Utility/Extensions/FilesystemExtensions.cs @@ -74,14 +74,14 @@ namespace Microsoft.PackageManagement.Internal.Utility.Extensions { // move the file to the tmp file // and tell the OS to remove it next reboot. var tmpFilename = GenerateTemporaryFileOrDirectoryNameInTempDirectory() + ".delete_me"; // generates a unique filename but not a file! - File.Move(location, tmpFilename); + MoveFileOverwrite(location, tmpFilename); if (File.Exists(location) || Directory.Exists(location)) { // of course, if the tmpFile isn't on the same volume as the location, this doesn't work. // then, last ditch effort, let's rename it in the current directory // and then we can hide it and mark it for cleanup . tmpFilename = Path.Combine(Path.GetDirectoryName(location), "tmp." + CounterHex + "." + Path.GetFileName(location) + ".delete_me"); - File.Move(location, tmpFilename); + MoveFileOverwrite(location, tmpFilename); if (File.Exists(tmpFilename) || Directory.Exists(location)) { // hide the file for convenience. File.SetAttributes(tmpFilename, File.GetAttributes(tmpFilename) | FileAttributes.Hidden); @@ -89,7 +89,7 @@ namespace Microsoft.PackageManagement.Internal.Utility.Extensions { } // Now we mark the locked file to be deleted upon next reboot (or until another coapp app gets there) - File.Move(File.Exists(tmpFilename) ? tmpFilename : location, null); + MoveFileOverwrite(File.Exists(tmpFilename) ? tmpFilename : location, null); } catch { // really. Hmmm. } @@ -101,6 +101,19 @@ namespace Microsoft.PackageManagement.Internal.Utility.Extensions { return; } + /// + /// File move abstraction that can be implemented to handle non-windows platforms + /// + /// + /// + public static void MoveFileOverwrite(string sourceFile, string destinationFile) { + NativeMethods.MoveFileEx(sourceFile, destinationFile, MoveFileFlags.ReplaceExisting); + } + + public static void MoveFileAtNextBoot(string sourceFile, string destinationFile) { + NativeMethods.MoveFileEx(sourceFile, destinationFile, MoveFileFlags.DelayUntilReboot); + } + /// /// Create a temporary file name in the temp directory so we can move file that we cannot delete over /// @@ -186,7 +199,6 @@ namespace Microsoft.PackageManagement.Internal.Utility.Extensions { // is this a unc path? if (string.IsNullOrWhiteSpace(pathUri.Host)) { -#if !UNIX // no, this is a drive:\path path // use API to resolve out the drive letter to see if it is a remote var drive = pathUri.Segments[1].Replace('/', '\\'); // the zero segment is always just '/' @@ -200,7 +212,6 @@ namespace Microsoft.PackageManagement.Internal.Utility.Extensions { return pathUri.Segments.Skip(2).Aggregate(sb.ToString().Trim(), (current, item) => current + item); } } -#endif } // not a remote (or resovably-remote) path or // it is already a path that is in it's correct form (via localpath) @@ -254,4 +265,4 @@ namespace Microsoft.PackageManagement.Internal.Utility.Extensions { return new Regex(@"-+").Replace(new Regex(@"[^\d\w\[\]_\-\.\ ]").Replace(input, "-"), "-").Replace(" ", ""); } } -} +} \ No newline at end of file diff --git a/src/Microsoft.PackageManagement/Utility/Platform/AdminPrivilege.cs b/src/Microsoft.PackageManagement/Utility/Platform/AdminPrivilege.cs index b9974203d..c65ae1af7 100644 --- a/src/Microsoft.PackageManagement/Utility/Platform/AdminPrivilege.cs +++ b/src/Microsoft.PackageManagement/Utility/Platform/AdminPrivilege.cs @@ -27,14 +27,10 @@ namespace Microsoft.PackageManagement.Internal.Utility.Platform { /// public static bool IsElevated { get { -#if UNIX - return string.Equals(System.Environment.GetEnvironmentVariable("SUDO_UID"), "1000"); -#else var id = WindowsIdentity.GetCurrent(); var principal = new WindowsPrincipal(id); return principal.IsInRole(WindowsBuiltInRole.Administrator); -#endif } } } -} +} \ No newline at end of file diff --git a/src/Microsoft.PackageManagement/Utility/Platform/Manifest.cs b/src/Microsoft.PackageManagement/Utility/Platform/Manifest.cs index 8935298fb..3edf59e9e 100644 --- a/src/Microsoft.PackageManagement/Utility/Platform/Manifest.cs +++ b/src/Microsoft.PackageManagement/Utility/Platform/Manifest.cs @@ -22,7 +22,6 @@ namespace Microsoft.PackageManagement.Internal.Utility.Platform { internal static class Manifest { private static readonly byte[] _utf = {0xef, 0xbb, 0xbf}; -#if !UNIX public static IEnumerable LoadFrom(string filename) { var manifests = new List(); @@ -69,7 +68,5 @@ namespace Microsoft.PackageManagement.Internal.Utility.Platform { } return manifests; } -#endif - } -} +} \ No newline at end of file diff --git a/src/Microsoft.PackageManagement/Utility/Platform/NativeMethods.cs b/src/Microsoft.PackageManagement/Utility/Platform/NativeMethods.cs index 99fc2f20a..f1223a519 100644 --- a/src/Microsoft.PackageManagement/Utility/Platform/NativeMethods.cs +++ b/src/Microsoft.PackageManagement/Utility/Platform/NativeMethods.cs @@ -12,7 +12,6 @@ // limitations under the License. // -#if !UNIX namespace Microsoft.PackageManagement.Internal.Utility.Platform { using System; using System.Diagnostics.CodeAnalysis; @@ -335,6 +334,4 @@ namespace Microsoft.PackageManagement.Internal.Utility.Platform { public static extern void OutputDebugString(string debugMessageText); #endif } -} -#endif - +} \ No newline at end of file diff --git a/src/Microsoft.PackageManagement/providers/inbox/Common/Utility/PathUtility.cs b/src/Microsoft.PackageManagement/providers/inbox/Common/Utility/PathUtility.cs index ad4ed28d5..6f4d357ca 100644 --- a/src/Microsoft.PackageManagement/providers/inbox/Common/Utility/PathUtility.cs +++ b/src/Microsoft.PackageManagement/providers/inbox/Common/Utility/PathUtility.cs @@ -192,7 +192,7 @@ namespace Microsoft.PackageManagement.Provider.Utility #if !CORECLR Marshal.ZeroFreeGlobalAllocUnicode(value); #else - Marshal.ZeroFreeCoTaskMemUnicode(value); + SecureStringMarshal.ZeroFreeCoTaskMemUnicode(value); #endif } } @@ -250,4 +250,4 @@ namespace Microsoft.PackageManagement.Provider.Utility } } -} +} \ No newline at end of file diff --git a/src/Microsoft.PowerShell.Activities/Xamls/InlineScriptDesigner.xaml b/src/Microsoft.PowerShell.Activities/Xamls/InlineScriptDesigner.xaml index a01b00c04..6d5deb2de 100644 --- a/src/Microsoft.PowerShell.Activities/Xamls/InlineScriptDesigner.xaml +++ b/src/Microsoft.PowerShell.Activities/Xamls/InlineScriptDesigner.xaml @@ -6,7 +6,7 @@ xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:s="clr-namespace:System;assembly=mscorlib" xmlns:conv="clr-namespace:System.Activities.Presentation.Converters;assembly=System.Activities.Presentation" - xmlns:sap="clr-namespace:System.Activities.Presentation" + xmlns:sap="clr-namespace:System.Activities.Presentation;assembly=System.Activities.Presentation" xmlns:sapv="clr-namespace:System.Activities.Presentation.View;assembly=System.Activities.Presentation" mc:Ignorable="d" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" diff --git a/src/Microsoft.PowerShell.Activities/Xamls/PipelineDesigner.xaml b/src/Microsoft.PowerShell.Activities/Xamls/PipelineDesigner.xaml index 16f9b3543..983cfeee7 100644 --- a/src/Microsoft.PowerShell.Activities/Xamls/PipelineDesigner.xaml +++ b/src/Microsoft.PowerShell.Activities/Xamls/PipelineDesigner.xaml @@ -1,7 +1,7 @@  + xmlns:swd="clr-namespace:System.Activities.Presentation;assembly=System.Activities.Presentation"> diff --git a/src/Microsoft.PowerShell.Commands.Diagnostics/CommonUtils.cs b/src/Microsoft.PowerShell.Commands.Diagnostics/CommonUtils.cs index 97fdbc978..cd2050f3d 100644 --- a/src/Microsoft.PowerShell.Commands.Diagnostics/CommonUtils.cs +++ b/src/Microsoft.PowerShell.Commands.Diagnostics/CommonUtils.cs @@ -3,15 +3,19 @@ using System.Collections; using System.Diagnostics; using System.Runtime.InteropServices; using System.Text; -using System.Resources; -using System.Reflection; + namespace Microsoft.PowerShell.Commands.Diagnostics.Common { - internal static class CommonUtilities + internal class CommonUtilities { -#if !CORECLR + // + // No-op private ctor to prevent the default ctor from getting generated. + // This class is intended to only have static members. + // + private CommonUtilities() { } + // // StringArrayToString helper converts a string array into a comma-separated string. // Note this has only limited use, individual strings cannot have commas. @@ -112,13 +116,7 @@ namespace Microsoft.PowerShell.Commands.Diagnostics.Common } return formatError; } -#endif - public static ResourceManager GetResourceManager() - { - // this naming pattern is dictated by the dotnet cli - return new ResourceManager("Microsoft.PowerShell.Commands.Diagnostics.resources.GetEventResources", typeof(CommonUtilities).GetTypeInfo().Assembly); - } } } diff --git a/src/Microsoft.PowerShell.Commands.Diagnostics/CounterSample.cs b/src/Microsoft.PowerShell.Commands.Diagnostics/CounterSample.cs index a7cdd86d1..29bdd7845 100644 --- a/src/Microsoft.PowerShell.Commands.Diagnostics/CounterSample.cs +++ b/src/Microsoft.PowerShell.Commands.Diagnostics/CounterSample.cs @@ -145,7 +145,7 @@ namespace Microsoft.PowerShell.Commands.GetCounter { internal PerformanceCounterSampleSet() { - _resourceMgr = Microsoft.PowerShell.Commands.Diagnostics.Common.CommonUtilities.GetResourceManager(); + _resourceMgr = new ResourceManager("GetEventResources", Assembly.GetExecutingAssembly()); } internal PerformanceCounterSampleSet (DateTime timeStamp, diff --git a/src/Microsoft.PowerShell.Commands.Diagnostics/ExportCounterCommand.cs b/src/Microsoft.PowerShell.Commands.Diagnostics/ExportCounterCommand.cs index 49246e66f..9104fc838 100644 --- a/src/Microsoft.PowerShell.Commands.Diagnostics/ExportCounterCommand.cs +++ b/src/Microsoft.PowerShell.Commands.Diagnostics/ExportCounterCommand.cs @@ -152,7 +152,7 @@ namespace Microsoft.PowerShell.Commands protected override void BeginProcessing() { - _resourceMgr = Microsoft.PowerShell.Commands.Diagnostics.Common.CommonUtilities.GetResourceManager(); + _resourceMgr = new ResourceManager("GetEventResources", Assembly.GetExecutingAssembly()); // // Determine the OS version: this cmdlet requires Windows 7 diff --git a/src/Microsoft.PowerShell.Commands.Diagnostics/GetCounterCommand.cs b/src/Microsoft.PowerShell.Commands.Diagnostics/GetCounterCommand.cs index 815f10705..b0eac6410 100644 --- a/src/Microsoft.PowerShell.Commands.Diagnostics/GetCounterCommand.cs +++ b/src/Microsoft.PowerShell.Commands.Diagnostics/GetCounterCommand.cs @@ -203,7 +203,7 @@ namespace Microsoft.PowerShell.Commands // protected override void BeginProcessing() { - _resourceMgr = Microsoft.PowerShell.Commands.Diagnostics.Common.CommonUtilities.GetResourceManager(); + _resourceMgr = new ResourceManager("GetEventResources", Assembly.GetExecutingAssembly()); _pdhHelper = new PdhHelper(System.Environment.OSVersion.Version.Major < 6); uint res = _pdhHelper.ConnectToDataSource(); diff --git a/src/Microsoft.PowerShell.Commands.Diagnostics/GetEventCommand.cs b/src/Microsoft.PowerShell.Commands.Diagnostics/GetEventCommand.cs index e6e2ad81d..019c0b014 100644 --- a/src/Microsoft.PowerShell.Commands.Diagnostics/GetEventCommand.cs +++ b/src/Microsoft.PowerShell.Commands.Diagnostics/GetEventCommand.cs @@ -27,9 +27,9 @@ namespace Microsoft.PowerShell.Commands [Cmdlet(VerbsCommon.Get, "WinEvent" , DefaultParameterSetName = "GetLogSet", HelpUri = "http://go.microsoft.com/fwlink/?LinkID=138336")] public sealed class GetWinEventCommand : PSCmdlet { - /// - /// ListLog parameter - /// + // + // ListLog parameter + // [Parameter( Position = 0, Mandatory = true, @@ -51,9 +51,9 @@ namespace Microsoft.PowerShell.Commands } private string[] _listLog = {"*"}; - /// - /// GetLog parameter - /// + // + // GetLog parameter + // [Parameter( Position = 0, ParameterSetName="GetLogSet", @@ -73,9 +73,9 @@ namespace Microsoft.PowerShell.Commands private string[] _logName = {"*"}; - /// - /// ListProvider parameter - /// + // + // ListProvider parameter + // [Parameter( Position = 0, Mandatory = true, @@ -99,9 +99,9 @@ namespace Microsoft.PowerShell.Commands private string[] _listProvider = {"*"}; - /// - /// ProviderName parameter - /// + // + // ProviderName parameter + // [Parameter( Position = 0, Mandatory = true, @@ -123,9 +123,9 @@ namespace Microsoft.PowerShell.Commands private string[] _providerName; - /// - /// Path parameter - /// + // + // Path parameter + // [Parameter( Position = 0, Mandatory = true, @@ -147,9 +147,9 @@ namespace Microsoft.PowerShell.Commands private string[] _path; - /// - /// MaxEvents parameter - /// + // + // MaxEvents parameter + // [Parameter( ParameterSetName="FileSet", ValueFromPipeline = false, @@ -188,9 +188,9 @@ namespace Microsoft.PowerShell.Commands } private Int64 _maxEvents = -1; - /// - /// ComputerName parameter - /// + // + // ComputerName parameter + // [Parameter( ParameterSetName="ListProviderSet", HelpMessageBaseName = "GetEventResources", @@ -225,9 +225,9 @@ namespace Microsoft.PowerShell.Commands } private string _computerName = string.Empty; - /// - /// Credential parameter - /// + // + // Credential parameter + // [Parameter(ParameterSetName="ListProviderSet")] [Parameter(ParameterSetName="GetProviderSet")] [Parameter(ParameterSetName="ListLogSet")] @@ -244,9 +244,9 @@ namespace Microsoft.PowerShell.Commands private PSCredential _credential = PSCredential.Empty; - /// - /// FilterXPath parameter - /// + // + // FilterXPath parameter + // [Parameter( ParameterSetName="FileSet", ValueFromPipeline = false, @@ -270,9 +270,9 @@ namespace Microsoft.PowerShell.Commands } private string _filter = "*"; - /// - /// FilterXml parameter - /// + // + // FilterXml parameter + // [Parameter( Position = 0, Mandatory = true, @@ -294,9 +294,9 @@ namespace Microsoft.PowerShell.Commands private XmlDocument _xmlQuery = null; - /// - /// FilterHashtable parameter - /// + // + // FilterHashtable parameter + // [Parameter( Position = 0, Mandatory = true, @@ -317,9 +317,9 @@ namespace Microsoft.PowerShell.Commands } private Hashtable[] _selector; - /// - /// Force switch - /// + // + // Force switch + // [Parameter(ParameterSetName="ListLogSet")] [Parameter(ParameterSetName="GetProviderSet")] [Parameter(ParameterSetName="GetLogSet")] @@ -332,9 +332,9 @@ namespace Microsoft.PowerShell.Commands } private SwitchParameter _force; - /// - /// Oldest switch - /// + // + // Oldest switch + // [Parameter(ParameterSetName="FileSet")] [Parameter(ParameterSetName="GetProviderSet")] [Parameter(ParameterSetName="GetLogSet")] @@ -391,18 +391,18 @@ namespace Microsoft.PowerShell.Commands private const string hashkey_data_lc="data"; - /// - /// BeginProcessing() is invoked once per pipeline: we will load System.Core.dll here - /// + // + // BeginProcessing() is invoked once per pipeline: we will load System.Core.dll here + // protected override void BeginProcessing() { - _resourceMgr = Microsoft.PowerShell.Commands.Diagnostics.Common.CommonUtilities.GetResourceManager(); + _resourceMgr = new ResourceManager("GetEventResources", typeof(GetWinEventCommand).GetTypeInfo().Assembly); } - /// - /// EndProcessing() is invoked once per pipeline - /// + // + // EndProcessing() is invoked once per pipeline + // protected override void EndProcessing() { @@ -426,10 +426,10 @@ namespace Microsoft.PowerShell.Commands } - /// - /// ProcessRecord() override. - /// This is the main entry point for the cmdlet. - /// + // + // ProcessRecord() override. + // This is the main entry point for the cmdlet. + // protected override void ProcessRecord() { switch (ParameterSetName) diff --git a/src/Microsoft.PowerShell.Commands.Diagnostics/ImportCounterCommand.cs b/src/Microsoft.PowerShell.Commands.Diagnostics/ImportCounterCommand.cs index ffa460119..a54c5e7b5 100644 --- a/src/Microsoft.PowerShell.Commands.Diagnostics/ImportCounterCommand.cs +++ b/src/Microsoft.PowerShell.Commands.Diagnostics/ImportCounterCommand.cs @@ -189,7 +189,7 @@ namespace Microsoft.PowerShell.Commands // protected override void BeginProcessing() { - _resourceMgr = Microsoft.PowerShell.Commands.Diagnostics.Common.CommonUtilities.GetResourceManager(); + _resourceMgr = new ResourceManager("GetEventResources", Assembly.GetExecutingAssembly()); _pdhHelper = new PdhHelper(System.Environment.OSVersion.Version.Major < 6); } diff --git a/src/Microsoft.PowerShell.Commands.Diagnostics/NewWinEventCommand.cs b/src/Microsoft.PowerShell.Commands.Diagnostics/NewWinEventCommand.cs index 0f80fa729..7c4326540 100644 --- a/src/Microsoft.PowerShell.Commands.Diagnostics/NewWinEventCommand.cs +++ b/src/Microsoft.PowerShell.Commands.Diagnostics/NewWinEventCommand.cs @@ -13,7 +13,7 @@ using System.Diagnostics.CodeAnalysis; using System.Collections.Generic; using System.Xml; using System.IO; - + namespace Microsoft.PowerShell.Commands { /// @@ -28,7 +28,7 @@ namespace Microsoft.PowerShell.Commands private const string TemplateTag = "template"; private const string DataTag = "data"; - private ResourceManager _resourceMgr = Microsoft.PowerShell.Commands.Diagnostics.Common.CommonUtilities.GetResourceManager(); + private ResourceManager _resourceMgr = new ResourceManager("GetEventResources", typeof(NewWinEventCommand).GetTypeInfo().Assembly); /// diff --git a/src/Microsoft.PowerShell.Commands.Diagnostics/PdhHelper.cs b/src/Microsoft.PowerShell.Commands.Diagnostics/PdhHelper.cs index 4e8697f22..208932dc6 100644 --- a/src/Microsoft.PowerShell.Commands.Diagnostics/PdhHelper.cs +++ b/src/Microsoft.PowerShell.Commands.Diagnostics/PdhHelper.cs @@ -479,7 +479,6 @@ namespace Microsoft.Powershell.Commands.GetCounter.PdhNative /// A helper reading in a Unicode string with embedded NULLs and splitting it into a StringCollection. /// /// - /// /// private void ReadPdhMultiString(ref IntPtr strNative, Int32 strSize, ref StringCollection strColl) diff --git a/src/Microsoft.PowerShell.Commands.Management/cimSupport/cmdletization/cim/cimConverter.cs b/src/Microsoft.PowerShell.Commands.Management/cimSupport/cmdletization/cim/cimConverter.cs index 98f35b704..41d28ddbb 100644 --- a/src/Microsoft.PowerShell.Commands.Management/cimSupport/cmdletization/cim/cimConverter.cs +++ b/src/Microsoft.PowerShell.Commands.Management/cimSupport/cmdletization/cim/cimConverter.cs @@ -96,7 +96,7 @@ namespace Microsoft.PowerShell.Cim } finally { - Marshal.ZeroFreeCoTaskMemUnicode(plainTextString); + ClrFacade.ZeroFreeCoTaskMemUnicode(plainTextString); } } diff --git a/src/Microsoft.PowerShell.Commands.Management/commands/management/Computer.cs b/src/Microsoft.PowerShell.Commands.Management/commands/management/Computer.cs index 74eb64935..88a2ee2b1 100644 --- a/src/Microsoft.PowerShell.Commands.Management/commands/management/Computer.cs +++ b/src/Microsoft.PowerShell.Commands.Management/commands/management/Computer.cs @@ -1,5 +1,3 @@ -#if !UNIX - /********************************************************************++ Copyright (c) Microsoft Corporation. All rights reserved. --********************************************************************/ @@ -7386,5 +7384,3 @@ $result #endregion }//End namespace - -#endif diff --git a/src/Microsoft.PowerShell.Commands.Management/commands/management/Navigation.cs b/src/Microsoft.PowerShell.Commands.Management/commands/management/Navigation.cs index 7ba238ccd..d2ba941ee 100644 --- a/src/Microsoft.PowerShell.Commands.Management/commands/management/Navigation.cs +++ b/src/Microsoft.PowerShell.Commands.Management/commands/management/Navigation.cs @@ -996,12 +996,6 @@ namespace Microsoft.PowerShell.Commands try { // Change the current working directory - if (string.IsNullOrEmpty(Path)) - { - // If user just typed 'cd', go to FileSystem provider home directory - Path = SessionState.Internal.GetSingleProvider(Commands.FileSystemProvider.ProviderName).Home; - } - result = SessionState.Path.SetLocation(Path, CmdletProviderContext); } catch (PSNotSupportedException notSupported) @@ -3568,22 +3562,7 @@ namespace Microsoft.PowerShell.Commands } bool shouldRecurse = Recurse; - bool treatAsFile = false; - try - { - System.IO.DirectoryInfo di = new System.IO.DirectoryInfo(providerPath); - if (!Platform.IsWindows && di != null && (di.Attributes & System.IO.FileAttributes.ReparsePoint) != 0) - { - shouldRecurse = false; - treatAsFile = true; - } - } - catch (System.IO.FileNotFoundException) - { - // not a directory - } - - if (!treatAsFile && !Recurse && hasChildren) + if (!Recurse && hasChildren) { // Get the localized prompt string diff --git a/src/Microsoft.PowerShell.Commands.Management/commands/management/ParsePathCommand.cs b/src/Microsoft.PowerShell.Commands.Management/commands/management/ParsePathCommand.cs index 09128a973..4f137484d 100644 --- a/src/Microsoft.PowerShell.Commands.Management/commands/management/ParsePathCommand.cs +++ b/src/Microsoft.PowerShell.Commands.Management/commands/management/ParsePathCommand.cs @@ -540,7 +540,7 @@ namespace Microsoft.PowerShell.Commands if (SessionState.Path.IsProviderQualified(path)) { int index = path.IndexOf("::", StringComparison.CurrentCulture); - + if (index != -1) { // remove the qualifier @@ -553,12 +553,9 @@ namespace Microsoft.PowerShell.Commands if (SessionState.Path.IsPSAbsolute(path, out driveName)) { - var driveNameLength = driveName.Length; - if (path.Length > (driveNameLength + 1) && path[driveNameLength] == ':') - { - // Remove the drive name and colon - result = path.Substring(driveNameLength + 1); - } + // Remove the drive name and colon + + result = path.Substring(driveName.Length + 1); } } diff --git a/src/Microsoft.PowerShell.Commands.Management/commands/management/Process.cs b/src/Microsoft.PowerShell.Commands.Management/commands/management/Process.cs index 8064122a1..a34f4ec45 100644 --- a/src/Microsoft.PowerShell.Commands.Management/commands/management/Process.cs +++ b/src/Microsoft.PowerShell.Commands.Management/commands/management/Process.cs @@ -866,9 +866,6 @@ namespace Microsoft.PowerShell.Commands private static string RetrieveProcessUserName(Process process, Cmdlet cmdlet) { string userName = null; -#if UNIX - userName = Platform.NonWindowsGetUserFromPid(process.Id); -#else IntPtr tokenUserInfo = IntPtr.Zero; IntPtr processTokenHandler = IntPtr.Zero; @@ -958,7 +955,6 @@ namespace Microsoft.PowerShell.Commands } } -#endif return userName; } @@ -1366,7 +1362,7 @@ namespace Microsoft.PowerShell.Commands continue; } - if (Platform.IsWindows && !Force) + if (!Force) { // Check if the process is owned by current user if (!IsProcessOwnedByCurrentUser(process)) @@ -2005,9 +2001,6 @@ namespace Microsoft.PowerShell.Commands } private SwitchParameter _UseNewEnvironment; - private StreamWriter OutputWriter; - private StreamWriter ErrorWriter; - #endregion #region overrides @@ -2101,10 +2094,7 @@ namespace Microsoft.PowerShell.Commands } //LoadUserProfile. - if (Platform.IsWindows) - { - startInfo.LoadUserProfile = _loaduserprofile; - } + startInfo.LoadUserProfile = _loaduserprofile; if (_credential != null) { @@ -2196,30 +2186,8 @@ namespace Microsoft.PowerShell.Commands } #endif //Starts the Process - Process process; - if (Platform.IsWindows) - { - process = start(startInfo); - } - else - { - process = new Process(); - process.StartInfo = startInfo; - SetupInputOutputRedirection(process); - process.Start(); - if (process.StartInfo.RedirectStandardOutput) - { - process.BeginOutputReadLine(); - } - if (process.StartInfo.RedirectStandardError) - { - process.BeginErrorReadLine(); - } - if (process.StartInfo.RedirectStandardInput) - { - WriteToStandardInput(process); - } - } + Process process = start(startInfo); + //Wait and Passthru Implementation. if (_passthru.IsPresent) @@ -2242,27 +2210,20 @@ namespace Microsoft.PowerShell.Commands { if (!process.HasExited) { - if (Platform.IsWindows) + waithandle = new ManualResetEvent(false); + + // Create and start the job object + ProcessCollection jobObject = new ProcessCollection(); + if (jobObject.AssignProcessToJobObject(process)) { - waithandle = new ManualResetEvent(false); - - // Create and start the job object - ProcessCollection jobObject = new ProcessCollection(); - if (jobObject.AssignProcessToJobObject(process)) - { - // Wait for the job object to finish - jobObject.WaitOne(waithandle); - } - else if (!process.HasExited) - { - // WinBlue: 27537 Start-Process -Wait doesn't work in a remote session on Windows 7 or lower. - process.Exited += new EventHandler(myProcess_Exited); - process.EnableRaisingEvents = true; - process.WaitForExit(); - } + // Wait for the job object to finish + jobObject.WaitOne(waithandle); } - else + else if (!process.HasExited) { + // WinBlue: 27537 Start-Process -Wait doesn't work in a remote session on Windows 7 or lower. + process.Exited += new EventHandler(myProcess_Exited); + process.EnableRaisingEvents = true; process.WaitForExit(); } } @@ -2321,104 +2282,6 @@ namespace Microsoft.PowerShell.Commands } } - private void StdOutputHandler(object sendingProcess, DataReceivedEventArgs outLine) - { - if (!String.IsNullOrEmpty(outLine.Data)) - { - OutputWriter.WriteLine(outLine.Data); - OutputWriter.Flush(); - } - } - - private void StdErrorHandler(object sendingProcess, DataReceivedEventArgs outLine) - { - if (!String.IsNullOrEmpty(outLine.Data)) - { - ErrorWriter.WriteLine(outLine.Data); - ErrorWriter.Flush(); - } - } - - private void ExitHandler(object sendingProcess, System.EventArgs e) - { - // To avoid a race condition with Std*Handler, let's wait a bit before closing the streams - // System.Timer is not supported in CoreCLR, so let's spawn a new thread to do the wait - - Thread delayedStreamClosing = new Thread(StreamClosing); - delayedStreamClosing.Start(); - } - - private void StreamClosing() - { - Thread.Sleep(1000); - - if (OutputWriter != null) - { - OutputWriter.Dispose(); - } - if (ErrorWriter != null) - { - ErrorWriter.Dispose(); - } - } - - private void SetupInputOutputRedirection(Process p) - { - if (_redirectstandardinput != null) - { - p.StartInfo.RedirectStandardInput = true; - _redirectstandardinput = ResolveFilePath(_redirectstandardinput); - } - else - { - p.StartInfo.RedirectStandardInput = false; - } - - if (_redirectstandardoutput != null) - { - p.StartInfo.RedirectStandardOutput = true; - _redirectstandardoutput = ResolveFilePath(_redirectstandardoutput); - p.OutputDataReceived += new DataReceivedEventHandler(StdOutputHandler); - - // Can't do StreamWriter(string) in coreCLR - OutputWriter = new StreamWriter(new FileStream(_redirectstandardoutput, FileMode.Create)); - } - else - { - p.StartInfo.RedirectStandardOutput = false; - OutputWriter = null; - } - - if (_redirectstandarderror != null) - { - p.StartInfo.RedirectStandardError = true; - _redirectstandarderror = ResolveFilePath(_redirectstandarderror); - p.ErrorDataReceived += new DataReceivedEventHandler(StdErrorHandler); - - // Can't do StreamWriter(string) in coreCLR - ErrorWriter = new StreamWriter(new FileStream(_redirectstandarderror, FileMode.Create)); - } - else - { - p.StartInfo.RedirectStandardError = false; - ErrorWriter = null; - } - - p.EnableRaisingEvents = true; - p.Exited += new EventHandler(ExitHandler); - } - - private void WriteToStandardInput(Process p) - { - StreamWriter writer = p.StandardInput; - using (StreamReader reader = new StreamReader(new FileStream(_redirectstandardinput, FileMode.Open))) - { - string line = reader.ReadToEnd(); - writer.WriteLine(line); - } - writer.Dispose(); - } - private Process StartWithCreateProcess(ProcessStartInfo startinfo) { @@ -2578,7 +2441,7 @@ namespace Microsoft.PowerShell.Commands { if (password != IntPtr.Zero) { - Marshal.ZeroFreeCoTaskMemUnicode(password); + ClrFacade.ZeroFreeCoTaskMemUnicode(password); } } }//end of if diff --git a/src/Microsoft.PowerShell.Commands.Management/commands/management/Service.cs b/src/Microsoft.PowerShell.Commands.Management/commands/management/Service.cs index df78a5849..c155a5dad 100644 --- a/src/Microsoft.PowerShell.Commands.Management/commands/management/Service.cs +++ b/src/Microsoft.PowerShell.Commands.Management/commands/management/Service.cs @@ -2230,7 +2230,7 @@ namespace Microsoft.PowerShell.Commands { if (IntPtr.Zero != password) { - Marshal.ZeroFreeCoTaskMemUnicode(password); + ClrFacade.ZeroFreeCoTaskMemUnicode(password); } if (IntPtr.Zero != hService) diff --git a/src/Microsoft.PowerShell.Commands.Management/commands/management/TimeZoneCommands.cs b/src/Microsoft.PowerShell.Commands.Management/commands/management/TimeZoneCommands.cs index a15be18f7..abac5b70a 100644 --- a/src/Microsoft.PowerShell.Commands.Management/commands/management/TimeZoneCommands.cs +++ b/src/Microsoft.PowerShell.Commands.Management/commands/management/TimeZoneCommands.cs @@ -1,5 +1,3 @@ -#if !UNIX - using System; using System.Collections.Generic; using System.Collections.ObjectModel; @@ -862,5 +860,3 @@ namespace Microsoft.PowerShell.Commands } } } - -#endif diff --git a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/AddType.cs b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/AddType.cs index 51528a5f3..54203c61e 100644 --- a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/AddType.cs +++ b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/AddType.cs @@ -1059,37 +1059,23 @@ namespace Microsoft.PowerShell.Commands private static PortableExecutableReference ObjectImplementationAssemblyReference = MetadataReference.CreateFromFile(typeof(object).GetTypeInfo().Assembly.Location); - private static PortableExecutableReference MscorlibAssemblyReference = - MetadataReference.CreateFromFile(Assembly.Load(new AssemblyName("mscorlib")).Location); + private static PortableExecutableReference ObjectDeclaredAssemblyReference = + MetadataReference.CreateFromFile(System.IO.Path.Combine(FrameworkFolder, "System.Runtime.dll")); - // This assembly should be System.Runtime.dll - private static PortableExecutableReference SystemRuntimeAssemblyReference = - MetadataReference.CreateFromFile(ClrFacade.GetAssemblies(typeof(object).FullName).First().Location); - - // SecureString is defined in a separate assembly. + // CoreCLR RC2 bits don't have SecureString. We are using a separate assembly with SecureString implementation. // This fact is an implementation detail and should not require the user to specify one more assembly, // if they want to use SecureString in Add-Type -TypeDefinition. // So this assembly should be in the default assemblies list to provide the best experience. + // + // TODO: This reference should be removed, if we take CoreCLR version that has SecureString implementation. private static PortableExecutableReference SecureStringAssemblyReference = MetadataReference.CreateFromFile(typeof(System.Security.SecureString).GetTypeInfo().Assembly.Location); - - // These assemlbies are always automatically added to ReferencedAssemblies. - private static PortableExecutableReference[] autoReferencedAssemblies = new PortableExecutableReference[] + private static MetadataReference[] defaultAssemblies = new MetadataReference[] { - MscorlibAssemblyReference, - SystemRuntimeAssemblyReference, - SecureStringAssemblyReference, - ObjectImplementationAssemblyReference - }; - - // These assemlbies are used, when ReferencedAssemblies parameter is not specified. - private static PortableExecutableReference[] defaultAssemblies = new PortableExecutableReference[] - { - MscorlibAssemblyReference, - SystemRuntimeAssemblyReference, - SecureStringAssemblyReference, ObjectImplementationAssemblyReference, + ObjectDeclaredAssemblyReference, + SecureStringAssemblyReference, MetadataReference.CreateFromFile(typeof(PSObject).GetTypeInfo().Assembly.Location) }; @@ -1161,7 +1147,7 @@ namespace Microsoft.PowerShell.Commands // First try by strong name try { - loadedAssembly = Assembly.Load(new AssemblyName(assemblyName)); + loadedAssembly = System.Reflection.Assembly.Load(new AssemblyName(assemblyName)); } // Generates a FileNotFoundException if you can't load the strong type. // So we'll try from the short name. @@ -1231,8 +1217,9 @@ namespace Microsoft.PowerShell.Commands if (referencedAssembliesSpecified) { var tempReferences = ReferencedAssemblies.Select(a => MetadataReference.CreateFromFile(ResolveReferencedAssembly(a))).ToList(); - tempReferences.AddRange(autoReferencedAssemblies); - + tempReferences.Add(ObjectImplementationAssemblyReference); + tempReferences.Add(ObjectDeclaredAssemblyReference); + tempReferences.Add(SecureStringAssemblyReference); references = tempReferences.ToArray(); } @@ -1944,7 +1931,7 @@ namespace Microsoft.PowerShell.Commands { foreach(string path in paths) { - generatedTypes.AddRange(ClrFacade.LoadFrom(path).GetTypes()); + generatedTypes.AddRange(System.Reflection.Assembly.LoadFrom(path).GetTypes()); } } // Load the assembly by name @@ -2062,7 +2049,7 @@ namespace Microsoft.PowerShell.Commands // First try by strong name try { - loadedAssembly = Assembly.Load(assemblyName); + loadedAssembly = System.Reflection.Assembly.Load(assemblyName); } // Generates a FileNotFoundException if you can't load the strong type. // So we'll try from the short name. @@ -2074,7 +2061,7 @@ namespace Microsoft.PowerShell.Commands // Next, try an exact match if (StrongNames.Value.ContainsKey(assemblyName)) { - return Assembly.Load(StrongNames.Value[assemblyName]); + return System.Reflection.Assembly.Load(StrongNames.Value[assemblyName]); } // If the assembly name doesn't contain wildcards, return null. The caller generates an error here. @@ -2117,7 +2104,7 @@ namespace Microsoft.PowerShell.Commands return null; // Otherwise, load the assembly. - return Assembly.Load(matchedStrongName); + return System.Reflection.Assembly.Load(matchedStrongName); } private static ConcurrentDictionary InitializeStrongNameDictionary() diff --git a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/Import-LocalizedData.cs b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/Import-LocalizedData.cs index c2c65f557..a568cd6b8 100644 --- a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/Import-LocalizedData.cs +++ b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/Import-LocalizedData.cs @@ -294,11 +294,18 @@ namespace Microsoft.PowerShell.Commands } CultureInfo currentCulture = culture; + StringBuilder stringBuilder; string filePath; - string fullFileName = fileName + ".psd1"; while (currentCulture != null && !String.IsNullOrEmpty(currentCulture.Name)) { - filePath = Path.Combine(dir, currentCulture.Name, fullFileName); + stringBuilder = new StringBuilder(dir); + stringBuilder.Append("\\"); + stringBuilder.Append(currentCulture.Name); + stringBuilder.Append("\\"); + stringBuilder.Append(fileName); + stringBuilder.Append(".psd1"); + + filePath = stringBuilder.ToString(); if (File.Exists(filePath)) { @@ -308,7 +315,12 @@ namespace Microsoft.PowerShell.Commands currentCulture = currentCulture.Parent; } - filePath = Path.Combine(dir, fullFileName); + stringBuilder = new StringBuilder(dir); + stringBuilder.Append("\\"); + stringBuilder.Append(fileName); + stringBuilder.Append(".psd1"); + + filePath = stringBuilder.ToString(); if (File.Exists(filePath)) { @@ -318,11 +330,11 @@ namespace Microsoft.PowerShell.Commands InvalidOperationException ioe = PSTraceSource.NewInvalidOperationException( ImportLocalizedDataStrings.CannotFindPsd1File, - fullFileName, - Path.Combine(dir, culture.Name) + fileName + ".psd1", + dir + "\\" + culture.Name + "\\" ); WriteError(new ErrorRecord(ioe, "ImportLocalizedData", ErrorCategory.ObjectNotFound, - Path.Combine(dir, culture.Name, fullFileName))); + dir + "\\" + culture.Name + "\\" + fileName + ".psd1")); return null; } diff --git a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/MatchString.cs b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/MatchString.cs index 2bf94a400..b839e4df3 100644 --- a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/MatchString.cs +++ b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/MatchString.cs @@ -156,7 +156,7 @@ namespace Microsoft.PowerShell.Commands /// Returns the base name of the file containing the matching line. /// /// It will be the string "InputStream" if the object came from the input stream. - /// This is a readonly property calculated from the path. + /// This is a readonly propery calculated from . /// /// /// The file name diff --git a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/Send-MailMessage.cs b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/Send-MailMessage.cs index 6584be9c6..1e691675d 100644 --- a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/Send-MailMessage.cs +++ b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/Send-MailMessage.cs @@ -261,7 +261,7 @@ namespace Microsoft.PowerShell.Commands private SwitchParameter usessl; /// - /// Specifies the Port to be used on the server. + /// Specifies the Port to be used on /// /// /// Value must be greater than zero. diff --git a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/SetDateCommand.cs b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/SetDateCommand.cs index cf5868ce2..5abd52537 100644 --- a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/SetDateCommand.cs +++ b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/SetDateCommand.cs @@ -117,28 +117,21 @@ namespace Microsoft.PowerShell.Commands if ( ShouldProcess( dateToUse.ToString() ) ) { - if (Platform.IsWindows) + #pragma warning disable 56523 + + if (!NativeMethods.SetLocalTime(ref systemTime)) { - #pragma warning disable 56523 - - if (!NativeMethods.SetLocalTime(ref systemTime)) - { - throw new Win32Exception(Marshal.GetLastWin32Error()); - } - - // MSDN says to call this twice to account for changes - // between DST - if (!NativeMethods.SetLocalTime(ref systemTime)) - { - throw new Win32Exception(Marshal.GetLastWin32Error()); - } - - #pragma warning restore 56523 + throw new Win32Exception(Marshal.GetLastWin32Error()); } - else + + // MSDN says to call this twice to account for changes + // between DST + if (!NativeMethods.SetLocalTime(ref systemTime)) { - Platform.NonWindowsSetDate(dateToUse); + throw new Win32Exception(Marshal.GetLastWin32Error()); } + + #pragma warning restore 56523 } //output DateTime object wrapped in an PSObject with DisplayHint attached diff --git a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/Common/HtmlWebResponseObject.Common.cs b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/Common/HtmlWebResponseObject.Common.cs index e07f4477b..660891ef0 100644 --- a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/Common/HtmlWebResponseObject.Common.cs +++ b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/Common/HtmlWebResponseObject.Common.cs @@ -1,5 +1,3 @@ -#if !CORECLR - /********************************************************************++ Copyright (c) Microsoft Corporation. All rights reserved. --********************************************************************/ @@ -508,4 +506,3 @@ namespace Microsoft.PowerShell.Commands } } } -#endif \ No newline at end of file diff --git a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/Common/WebRequestPSCmdlet.Common.cs b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/Common/WebRequestPSCmdlet.Common.cs index 6b070db23..9195e8a59 100644 --- a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/Common/WebRequestPSCmdlet.Common.cs +++ b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/Common/WebRequestPSCmdlet.Common.cs @@ -12,9 +12,7 @@ using System.Collections; using System.Globalization; using System.Security.Cryptography; using System.Security.Cryptography.X509Certificates; -#if !CORECLR using mshtml; -#endif using Microsoft.Win32; namespace Microsoft.PowerShell.Commands @@ -465,12 +463,9 @@ namespace Microsoft.PowerShell.Commands /// needed if an HtmlDocument will be created shortly. protected bool VerifyInternetExplorerAvailable(bool checkComObject) { - // TODO: Remove this code once the dependecy on mshtml has been resolved. -#if CORECLR - return false; -#else bool isInternetExplorerConfigurationComplete = false; - // Check for IE for both PS Full and PS Core on windows. + +#if !LINUX // Check for IE for both PS Full and PS Core on windows. // The registry key DisableFirstRunCustomize can exits at one of the following path. // IE uses the same decending orider (as mentioned) to check for the presence of this key. // If the value of DisableFirstRunCustomize key is set to greater than zero then Run first @@ -524,12 +519,15 @@ namespace Microsoft.PowerShell.Commands isInternetExplorerConfigurationComplete = false; } } +#endif +#if !CORECLR // Throw exception in PS Full only if (!isInternetExplorerConfigurationComplete) throw new NotSupportedException(WebCmdletStrings.IEDomNotSupported); - return isInternetExplorerConfigurationComplete; #endif + + return isInternetExplorerConfigurationComplete; } private Uri PrepareUri(Uri uri) diff --git a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/ConvertFromJsonCommand.cs b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/ConvertFromJsonCommand.cs index 5583941ec..ef9c26c3f 100644 --- a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/ConvertFromJsonCommand.cs +++ b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/ConvertFromJsonCommand.cs @@ -93,12 +93,6 @@ namespace Microsoft.PowerShell.Commands // The first input string does not represent a complete Json Syntax. // Hence consider the the entire input as a single Json content. } -#if CORECLR - catch (Newtonsoft.Json.JsonSerializationException) - { - // we use another serializer for CORECLR implementation - } -#endif if (successfullyConverted) { for (int index = 1; index < inputObjectBuffer.Count; index++) diff --git a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/CoreCLR/HtmlWebResponseObject.CoreClr.cs b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/CoreCLR/HtmlWebResponseObject.CoreClr.cs index 2b6fc8f97..61a16b902 100644 --- a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/CoreCLR/HtmlWebResponseObject.CoreClr.cs +++ b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/CoreCLR/HtmlWebResponseObject.CoreClr.cs @@ -60,13 +60,6 @@ namespace Microsoft.PowerShell.Commands this.RawContent = raw.ToString(); } - /// - /// Dispose the the instance of the class. - /// - public void Dispose() - { - GC.SuppressFinalize(this); - } #endregion } } diff --git a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/CoreCLR/WebRequestPSCmdlet.CoreClr.cs b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/CoreCLR/WebRequestPSCmdlet.CoreClr.cs index a13f99406..fbc84993e 100644 --- a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/CoreCLR/WebRequestPSCmdlet.CoreClr.cs +++ b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/CoreCLR/WebRequestPSCmdlet.CoreClr.cs @@ -226,7 +226,6 @@ namespace Microsoft.PowerShell.Commands content = psBody.BaseObject; } - /* TODO: This needs to be enable after the dependency on mshtml is resolved. var html = content as HtmlWebResponseObject; if (html != null) { @@ -237,9 +236,6 @@ namespace Microsoft.PowerShell.Commands } } else if (content is FormObject) - */ - - if (content is FormObject) { FormObject form = content as FormObject; SetRequestContent(request, form.Fields); @@ -535,7 +531,7 @@ namespace Microsoft.PowerShell.Commands } -#endregion Helper Methods + #endregion Helper Methods } } #endif \ No newline at end of file diff --git a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/CoreCLR/WebResponseObjectFactory.CoreClr.cs b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/CoreCLR/WebResponseObjectFactory.CoreClr.cs index f706ae5a1..8eb411fe9 100644 --- a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/CoreCLR/WebResponseObjectFactory.CoreClr.cs +++ b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/WebCmdlet/CoreCLR/WebResponseObjectFactory.CoreClr.cs @@ -17,17 +17,14 @@ namespace Microsoft.PowerShell.Commands WebResponseObject output; if (WebResponseHelper.IsText(response)) { - output = new BasicHtmlWebResponseObject(response, responseStream); - - // TODO: This code needs to be enable after the dependency on mshtml is resolved. - //if (useBasicParsing) - //{ - // output = new BasicHtmlWebResponseObject(response, responseStream); - //} - //else - //{ - // output = new HtmlWebResponseObject(response, responseStream, executionContext); - //} + if (useBasicParsing) + { + output = new BasicHtmlWebResponseObject(response, responseStream); + } + else + { + output = new HtmlWebResponseObject(response, responseStream, executionContext); + } } else { diff --git a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/sort-object.cs b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/sort-object.cs index afa1ce46a..cb06e8191 100644 --- a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/sort-object.cs +++ b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/sort-object.cs @@ -23,7 +23,7 @@ namespace Microsoft.PowerShell.Commands set { DescendingOrder = value; } } /// - /// This param specifies if only unique objects are filtered. + /// /// /// [Parameter] @@ -37,7 +37,7 @@ namespace Microsoft.PowerShell.Commands /// - /// Remove duplicates. + /// Remove Duplicated from /// private static void RemoveDuplicates(OrderByProperty orderByProperty) { diff --git a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/GetTracerCommand.cs b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/GetTracerCommand.cs index 55f4e78bf..ce47c25bb 100644 --- a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/GetTracerCommand.cs +++ b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/GetTracerCommand.cs @@ -58,3 +58,4 @@ namespace Microsoft.PowerShell.Commands #endregion Cmdlet code } } + diff --git a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/MshHostTraceListener.cs b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/MshHostTraceListener.cs index 1ddda4afa..5cafcba4f 100644 --- a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/MshHostTraceListener.cs +++ b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/MshHostTraceListener.cs @@ -3,17 +3,12 @@ Copyright (c) Microsoft Corporation. All rights reserved. --********************************************************************/ using System; using System.IO; +using System.Security.Permissions; using System.Text; using System.Management.Automation; using System.Management.Automation.Host; using System.Management.Automation.Internal.Host; -#if CORECLR -using Microsoft.PowerShell.CoreClr.Stubs; -#else -using System.Security.Permissions; -#endif - namespace Microsoft.PowerShell.Commands { /// @@ -68,9 +63,6 @@ namespace Microsoft.PowerShell.Commands [SecurityPermission(SecurityAction.LinkDemand)] protected override void Dispose(bool disposing) { -#if CORECLR - base.Dispose(disposing); -#else try { if (disposing) @@ -82,10 +74,8 @@ namespace Microsoft.PowerShell.Commands { base.Dispose(disposing); } -#endif } -#if !CORECLR /// /// Closes the dialog and then calls the base class Close /// @@ -96,7 +86,6 @@ namespace Microsoft.PowerShell.Commands base.Close(); } -#endif #endregion TraceListener constructors and disposer @@ -154,3 +143,4 @@ namespace Microsoft.PowerShell.Commands } // class PSHostTraceListener } // namespace System.Management.Automation + diff --git a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/SetTracerCommand.cs b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/SetTracerCommand.cs index 561d12a44..c6f08afe8 100644 --- a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/SetTracerCommand.cs +++ b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/SetTracerCommand.cs @@ -185,3 +185,4 @@ namespace Microsoft.PowerShell.Commands #endregion Cmdlet code } } + diff --git a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/TraceCommandBase.cs b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/TraceCommandBase.cs index 2322303a7..995754330 100644 --- a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/TraceCommandBase.cs +++ b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/TraceCommandBase.cs @@ -133,3 +133,4 @@ namespace Microsoft.PowerShell.Commands } } } + diff --git a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/TraceExpressionCommand.cs b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/TraceExpressionCommand.cs index c303bddfd..29e6de6da 100644 --- a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/TraceExpressionCommand.cs +++ b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/TraceExpressionCommand.cs @@ -333,7 +333,7 @@ namespace Microsoft.PowerShell.Commands foreach (FileStream fileStream in this.FileStreams) { fileStream.Flush(); - fileStream.Dispose(); + fileStream.Close(); } } GC.SuppressFinalize(this); @@ -572,3 +572,4 @@ namespace Microsoft.PowerShell.Commands private Collection matchingSources = new Collection(); } } + diff --git a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/TraceListenerCommandBase.cs b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/TraceListenerCommandBase.cs index 7615b910b..186f40f97 100644 --- a/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/TraceListenerCommandBase.cs +++ b/src/Microsoft.PowerShell.Commands.Utility/commands/utility/trace/TraceListenerCommandBase.cs @@ -460,7 +460,7 @@ namespace Microsoft.PowerShell.Commands true)) { listenerToRemove.Flush(); - listenerToRemove.Dispose(); + listenerToRemove.Close(); source.Listeners.RemoveAt(index); } } @@ -619,7 +619,7 @@ namespace Microsoft.PowerShell.Commands foreach (TraceListener listener in pair.Value) { listener.Flush(); - listener.Dispose(); + listener.Close(); } } storedTraceSourceState.Clear (); @@ -631,3 +631,4 @@ namespace Microsoft.PowerShell.Commands #endregion stored state } } + diff --git a/src/Microsoft.PowerShell.ConsoleHost/host/msh/CommandLineParameterParser.cs b/src/Microsoft.PowerShell.ConsoleHost/host/msh/CommandLineParameterParser.cs index e2695a7c8..fa96ee170 100644 --- a/src/Microsoft.PowerShell.ConsoleHost/host/msh/CommandLineParameterParser.cs +++ b/src/Microsoft.PowerShell.ConsoleHost/host/msh/CommandLineParameterParser.cs @@ -353,12 +353,6 @@ namespace Microsoft.PowerShell switchKey = switchKey.Substring(1); - // chop off the second dash so we're agnostic wrt specifying - or -- - if (!String.IsNullOrEmpty(switchKey) && SpecialCharacters.IsDash(switchKey[0])) - { - switchKey = switchKey.Substring(1); - } - if (MatchSwitch(switchKey, "help", "h") || MatchSwitch(switchKey, "?", "?")) { showHelp = true; @@ -483,10 +477,7 @@ namespace Microsoft.PowerShell string exceptionMessage = null; try { - // Normalize slashes - file = args[i].Replace(StringLiterals.AlternatePathSeparator, - StringLiterals.DefaultPathSeparator); - file = Path.GetFullPath(file); + file = Path.GetFullPath(args[i]); } catch (Exception e) { diff --git a/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleControl.cs b/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleControl.cs index 90bce23ca..79bc5b0ab 100644 --- a/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleControl.cs +++ b/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleControl.cs @@ -1,4 +1,3 @@ -#if !UNIX /********************************************************************++ Copyright (c) Microsoft Corporation. All rights reserved. --********************************************************************/ @@ -3608,4 +3607,4 @@ namespace Microsoft.PowerShell private static PSTraceSource tracer = PSTraceSource.GetTracer("ConsoleControl", "Console control methods"); } } // namespace -#endif + diff --git a/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleHost.cs b/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleHost.cs index adfb05726..58f192ac0 100644 --- a/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleHost.cs +++ b/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleHost.cs @@ -180,22 +180,13 @@ namespace Microsoft.PowerShell try { - string profileDir; - if (Platform.IsWindows) - { - profileDir = Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData) + - @"\Microsoft\Windows\PowerShell"; + var profileDir = Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData) + + @"\Microsoft\Windows\PowerShell"; - if (!Directory.Exists(profileDir)) - { - Directory.CreateDirectory(profileDir); - } - } - else + if (!Directory.Exists(profileDir)) { - profileDir = Platform.SelectProductNameForDirectory(Platform.XDG_Type.CACHE); + Directory.CreateDirectory(profileDir); } - ClrFacade.SetProfileOptimizationRoot(profileDir); } catch @@ -270,6 +261,7 @@ namespace Microsoft.PowerShell : "StartupProfileData-NonInteractive"); exitCode = theConsoleHost.Run(cpp, !string.IsNullOrEmpty(preStartWarning)); } + } finally { @@ -286,32 +278,10 @@ namespace Microsoft.PowerShell -#if UNIX /// - /// + /// /// The break handler for the program. Dispatches a break event to the current Executor. - /// - /// - private static void MyBreakHandler(object sender, ConsoleCancelEventArgs args) - { - // Set the Cancel property to true to prevent the process from terminating. - args.Cancel = true; - switch (args.SpecialKey) - { - case ConsoleSpecialKey.ControlC: - SpinUpBreakHandlerThread(false); - return; - case ConsoleSpecialKey.ControlBreak: - // Break into script debugger. - BreakIntoDebugger(); - return; - } - } -#else - /// - /// - /// The break handler for the program. Dispatches a break event to the current Executor. - /// + /// /// /// /// @@ -347,7 +317,6 @@ namespace Microsoft.PowerShell return false; } } -#endif private static bool BreakIntoDebugger() { @@ -466,10 +435,8 @@ namespace Microsoft.PowerShell // call the console APIs directly, instead of ui.rawui.FlushInputHandle, as ui may be finalized // already if this thread is lagging behind the main thread. -#if !UNIX ConsoleHandle handle = ConsoleControl.GetConioDeviceHandle(); ConsoleControl.FlushConsoleInputBuffer(handle); -#endif ConsoleHost.SingletonInstance.breakHandlerThread = null; } @@ -1064,12 +1031,8 @@ namespace Microsoft.PowerShell private void BindBreakHandler() { -#if UNIX - Console.CancelKeyPress += new ConsoleCancelEventHandler(MyBreakHandler); -#else breakHandlerGcHandle = GCHandle.Alloc(new ConsoleControl.BreakHandler(MyBreakHandler)); ConsoleControl.AddBreakHandler((ConsoleControl.BreakHandler)breakHandlerGcHandle.Target); -#endif } #if !CORECLR // Not used on NanoServer: CurrentDomain.UnhandledException not supported on CoreCLR @@ -1123,11 +1086,9 @@ namespace Microsoft.PowerShell { if (!isDisposed) { -#if !UNIX Dbg.Assert(breakHandlerGcHandle != null, "break handler should be set"); ConsoleControl.RemoveBreakHandler(); breakHandlerGcHandle.Free(); -#endif if (isDisposingNotFinalizing) { @@ -1570,7 +1531,7 @@ namespace Microsoft.PowerShell { // Create and open Runspace with PSReadline. defaultImportModulesList = DefaultInitialSessionState.Modules; - DefaultInitialSessionState.ImportPSModule(new[] { "PSReadLine" }); + DefaultInitialSessionState.ImportPSModule(new[] { "PSReadline" }); consoleRunspace = RunspaceFactory.CreateRunspace(this, DefaultInitialSessionState); try { @@ -2872,9 +2833,7 @@ namespace Microsoft.PowerShell /// private RunspaceRef runspaceRef; -#if !UNIX private GCHandle breakHandlerGcHandle; -#endif private System.Threading.Thread breakHandlerThread; private bool isDisposed; internal ConsoleHostUserInterface ui; diff --git a/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleHostRawUserInterface.cs b/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleHostRawUserInterface.cs index b5d4f585f..dbd319282 100644 --- a/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleHostRawUserInterface.cs +++ b/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleHostRawUserInterface.cs @@ -1,4 +1,3 @@ -#if !UNIX /********************************************************************++ Copyright (c) Microsoft Corporation. All rights reserved. --********************************************************************/ @@ -1500,359 +1499,3 @@ namespace Microsoft.PowerShell } } // namespace -#else - -// Managed code only implementation for portability - -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; -using System.Threading.Tasks; -using System.Management.Automation; -using System.Management.Automation.Runspaces; -using System.Management.Automation.Host; -using System.Globalization; -using System.Reflection; -using System.Runtime.InteropServices; - -namespace Microsoft.PowerShell -{ - // this is all originally from https://msdn.microsoft.com/en-us/library/ee706570%28v=vs.85%29.aspx - - internal sealed class ConsoleHostRawUserInterface : PSHostRawUserInterface - { - private ConsoleColor defaultForeground = ConsoleColor.Gray; - - private ConsoleColor defaultBackground = ConsoleColor.Black; - - private ConsoleHostUserInterface parent = null; - - internal ConsoleHostRawUserInterface(ConsoleHostUserInterface mshConsole) : base() - { - defaultForeground = ForegroundColor; - defaultBackground = BackgroundColor; - parent = mshConsole; - } - - /// - /// Gets or sets the background color of the displayed text. - /// This maps to the corresponding Console.Background property. - /// - public override ConsoleColor BackgroundColor - { - get - { - // Console can return UnknownColor, a private enum, equivalent - // to -1. When this is a case, map it instead to our default. - return Console.BackgroundColor == (ConsoleColor)(-1) - ? defaultBackground - : Console.BackgroundColor; - } - set { Console.BackgroundColor = value; } - } - - // TODO: Make wrap width user-customizable. - private static Size WrapSize = new Size(80, 40); - - /// - /// Gets or sets the size of the host buffer. - /// - public override Size BufferSize - { - get - { - // Console can return zero when a pseduo-TTY is allocated, which - // is useless for us. Instead, map to the wrap size. - return Console.BufferWidth == 0 || Console.BufferHeight == 0 - ? WrapSize - : new Size(Console.BufferWidth, Console.BufferHeight); - } - set { Console.SetBufferSize(value.Width, value.Height); } - } - - /// - /// Gets or sets the cursor position. - /// - public override Coordinates CursorPosition - { - get { return new Coordinates(Console.CursorLeft, Console.CursorTop); } - set { Console.SetCursorPosition(value.X < 0 ? 0 : value.X, - value.Y < 0 ? 0 : value.Y); } - } - - /// - /// Gets or sets the size of the displayed cursor. - /// This maps to the corresponding Console.CursorSize property. - /// - public override int CursorSize - { - // Future porting note: this API throws on Windows when output is - // redirected, but never throws on Unix because it's fake. - get { return Console.CursorSize; } - set { Console.CursorSize = value; } - } - - /// - /// Gets or sets the foreground color of the displayed text. - /// This maps to the corresponding Console.ForegroundColor property. - /// - public override ConsoleColor ForegroundColor - { - get - { - // Console can return UnknownColor, a private enum, equivalent - // to -1. When this is a case, map it instead to our default. - return Console.ForegroundColor == (ConsoleColor)(-1) - ? defaultForeground - : Console.ForegroundColor; - } - set { Console.ForegroundColor = value; } - } - - /// - /// Gets a value indicating whether the user has pressed a key. This maps - /// to the corresponding Console.KeyAvailable property. - /// - public override bool KeyAvailable - { - get { return Console.KeyAvailable; } - } - - /// - /// Gets the dimensions of the largest window that could be rendered in - /// the current display, if the buffer was at the least that large. - /// This maps to the MaxWindowSize. - /// - public override Size MaxPhysicalWindowSize - { - get { return MaxWindowSize; } - } - - /// - /// Gets the dimensions of the largest window size that can be - /// displayed. This maps to the Console.LargestWindowWidth and - /// Console.LargestWindowHeight properties to determine the returned - /// value of this property. - /// - public override Size MaxWindowSize - { - get - { - // Console can return zero when a pseduo-TTY is allocated, which - // is useless for us. Instead, map to the wrap size. - return Console.LargestWindowWidth == 0 || Console.LargestWindowHeight == 0 - ? WrapSize - : new Size(Console.LargestWindowWidth, Console.LargestWindowHeight); - } - } - - /// - /// Gets or sets the position of the displayed window. This maps to the - /// Console window position APIs to determine the returned value of this - /// property. - /// - public override Coordinates WindowPosition - { - get { return new Coordinates(Console.WindowLeft, Console.WindowTop); } - set { Console.SetWindowPosition(value.X, value.Y); } - } - - /// - /// Gets or sets the size of the displayed window. This example - /// uses the corresponding Console window size APIs to determine the - /// returned value of this property. - /// - public override Size WindowSize - { - get - { - // Console can return zero when a pseduo-TTY is allocated, which - // is useless for us. Instead, map to the wrap size. - return Console.WindowWidth == 0 || Console.WindowHeight == 0 - ? WrapSize - : new Size(Console.WindowWidth, Console.WindowHeight); - } - set { Console.SetWindowSize(value.Width, value.Height); } - } - - /// - /// Cached Window Title, for systems that needs it - /// - private string title = String.Empty; - - /// - /// Gets or sets the title of the displayed window. The example - /// maps the Console.Title property to the value of this property. - /// - public override string WindowTitle - { - get - { - // Console throws an exception on Unix platforms, so we handle - // caching and returning the Window title ourselves. - return Platform.IsWindows ? Console.Title : title; - } - - set - { - Console.Title = value; - title = value; - } - } - - /// - /// This API resets the input buffer. - /// - public override void FlushInputBuffer() - { - if (!Console.IsInputRedirected) - { - Console.OpenStandardInput().Flush(); - } - } - - public void ScrollBuffer(int lines) - { - for (int i=0; i - /// This API returns a rectangular region of the screen buffer. In - /// this example this functionality is not needed so the method throws - /// a NotImplementException exception. - /// - /// Defines the size of the rectangle. - /// Throws a NotImplementedException exception. - public override BufferCell[,] GetBufferContents(Rectangle rectangle) - { - throw new NotImplementedException("The method or operation is not implemented."); - } - - /// - /// This API reads a pressed, released, or pressed and released keystroke - /// from the keyboard device, blocking processing until a keystroke is - /// typed that matches the specified keystroke options. - /// - /// Unused - public override KeyInfo ReadKey(ReadKeyOptions options) - { - ConsoleKeyInfo key = Console.ReadKey(); - return new KeyInfo((int)key.Key, key.KeyChar, new ControlKeyStates(), true); - } - - /// - /// This API crops a region of the screen buffer. In this example - /// this functionality is not needed so the method throws a - /// NotImplementException exception. - /// - /// The region of the screen to be scrolled. - /// The region of the screen to receive the - /// source region contents. - /// The region of the screen to include in the operation. - /// The character and attributes to be used to fill all cell. - public override void ScrollBufferContents(Rectangle source, Coordinates destination, Rectangle clip, BufferCell fill) - { - throw new NotImplementedException("The method or operation is not implemented."); - } - - /// - /// This method copies an array of buffer cells into the screen buffer - /// at a specified location. - /// - /// The parameter used to set the origin where the buffer where begin writing to. - /// The parameter used to contain the contents to be written to the buffer. - public override void SetBufferContents(Coordinates origin, - BufferCell[,] contents) - { - //if there are no contents, there is nothing to set the buffer to - if (contents == null) - { - PSTraceSource.NewArgumentNullException("contents"); - } - - //if the cursor is on the last line, we need to make more space to print the specified buffer - if (origin.Y == BufferSize.Height - 1 && origin.X >= BufferSize.Width) - { - //for each row in the buffer, create a new line - int rows = contents.GetLength(0); - ScrollBuffer(rows); - // for each row in the buffer, move the cursor y up to the beginning of the created blank space - // but not above zero - if (origin.Y >= rows) - { - origin.Y -= rows; - } - } - - //iterate through the buffer to set - foreach (var charitem in contents) - { - //set the cursor to false to prevent cursor flicker - Console.CursorVisible = false; - - //if x is exceeding buffer width, reset to the next line - if (origin.X >= BufferSize.Width) - { - origin.X = 1; - } - - //write the character from contents - Console.Out.Write(charitem.Character); - - //advance the character one position - origin.X++; - } - - //reset the cursor to the original position - CursorPosition = origin; - //reset the cursor to visible - Console.CursorVisible = true; - } - - /// - /// This method copies a given character, foreground color, and background - /// color to a region of the screen buffer. In this example this - /// functionality is not needed so the method throws a - /// NotImplementException exception./// - /// Defines the area to be filled. - /// Defines the fill character. - public override void SetBufferContents(Rectangle rectangle, BufferCell fill) - { - throw new NotImplementedException("The method or operation is not implemented."); - } - } -} -#endif diff --git a/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleHostUserInterface.cs b/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleHostUserInterface.cs index c720693d7..2b06144bc 100644 --- a/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleHostUserInterface.cs +++ b/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleHostUserInterface.cs @@ -14,9 +14,7 @@ using System.Management.Automation.Internal; using System.Management.Automation.Host; using System.Security; using Dbg = System.Management.Automation.Diagnostics; -#if !UNIX using ConsoleHandle = Microsoft.Win32.SafeHandles.SafeFileHandle; -#endif namespace Microsoft.PowerShell { @@ -61,15 +59,13 @@ namespace Microsoft.PowerShell this.parent = parent; this.rawui = new ConsoleHostRawUserInterface(this); -#if UNIX - this._supportsVirtualTerminal = true; -#else try { // Turn on virtual terminal if possible. // This might throw - not sure how exactly (no console), but if it does, we shouldn't fail to start. var handle = ConsoleControl.GetActiveScreenBufferHandle(); + var m = ConsoleControl.GetMode(handle); if (ConsoleControl.NativeMethods.SetConsoleMode(handle.DangerousGetHandle(), (uint) (m | ConsoleControl.ConsoleModes.VirtualTerminal))) { @@ -82,7 +78,6 @@ namespace Microsoft.PowerShell catch { } -#endif isInteractiveTestToolListening = false; } @@ -238,7 +233,7 @@ namespace Microsoft.PowerShell result = ReadLineSafe(true, printToken); } SecureString secureResult = result as SecureString; - System.Management.Automation.Diagnostics.Assert(secureResult != null, "ReadLineSafe did not return a SecureString"); + Diagnostics.Assert(secureResult != null, "ReadLineSafe did not return a SecureString"); return secureResult; } @@ -251,10 +246,6 @@ namespace Microsoft.PowerShell /// It also manages the cursor as keys are entered and "backspaced". However, it is possible that /// while this method is running, the console buffer contents could change. Then, its cursor mgmt /// will likely be messed up. - /// - /// Secondary implementation for Unix based on Console.ReadKey(), where - /// the advantage is portability through abstraction. Does not support - /// arrow key movement, but supports backspace. /// /// /// @@ -297,21 +288,13 @@ namespace Microsoft.PowerShell null; SecureString secureResult = new SecureString(); StringBuilder result = new StringBuilder(); -#if UNIX - bool treatControlCAsInput = Console.TreatControlCAsInput; -#else ConsoleHandle handle = ConsoleControl.GetConioDeviceHandle(); ConsoleControl.ConsoleModes originalMode = ConsoleControl.GetMode(handle); bool isModeChanged = true; // assume ConsoleMode is changed so that if ReadLineSetMode // fails to return the value correctly, the original mode is // restored. -#endif - try { -#if UNIX - Console.TreatControlCAsInput = true; -#else // Ensure that we're in the proper line-input mode. ConsoleControl.ConsoleModes desiredMode = @@ -338,7 +321,6 @@ namespace Microsoft.PowerShell isModeChanged = false; } rawui.ClearKeyCache(); -#endif Coordinates originalCursorPos = rawui.CursorPosition; @@ -349,39 +331,22 @@ namespace Microsoft.PowerShell // end up having a immutable string holding the // secret in memory. // -#if UNIX - ConsoleKeyInfo keyInfo = Console.ReadKey(true); -#else uint unused = 0; string key = ConsoleControl.ReadConsole(handle, string.Empty, 1, false, out unused); -#endif -#if UNIX - // Handle Ctrl-C ending input - if (keyInfo.Key == ConsoleKey.C && keyInfo.Modifiers.HasFlag(ConsoleModifiers.Control)) -#else if (string.IsNullOrEmpty(key) || (char)3 == key[0]) -#endif { PipelineStoppedException e = new PipelineStoppedException(); throw e; } -#if UNIX - if (keyInfo.Key == ConsoleKey.Enter) -#else if ((char)13 == key[0]) -#endif { // // we are done if user presses ENTER key // break; } -#if UNIX - if (keyInfo.Key == ConsoleKey.Backspace) -#else if ((char)8 == key[0]) -#endif { // // for backspace, remove last char appended @@ -397,13 +362,6 @@ namespace Microsoft.PowerShell WriteBackSpace(originalCursorPos); } } -#if UNIX - else if (Char.IsControl(keyInfo.KeyChar)) - { - // blacklist control characters - continue; - } -#endif else { // @@ -411,19 +369,11 @@ namespace Microsoft.PowerShell // if (isSecureString) { -#if UNIX - secureResult.AppendChar(keyInfo.KeyChar); -#else secureResult.AppendChar(key[0]); -#endif } else { -#if UNIX - result.Append(keyInfo.KeyChar); -#else result.Append(key); -#endif } if (!string.IsNullOrEmpty(printTokenString)) { @@ -433,23 +383,12 @@ namespace Microsoft.PowerShell } while (true); } -#if UNIX - catch (InvalidOperationException) - { - // ReadKey() failed so we stop - throw new PipelineStoppedException(); - } -#endif finally { -#if UNIX - Console.TreatControlCAsInput = treatControlCAsInput; -#else if (isModeChanged) { ConsoleControl.SetMode(handle, originalMode); } -#endif } WriteLineToConsole(); PostRead(result.ToString()); @@ -463,7 +402,6 @@ namespace Microsoft.PowerShell } } - /// /// /// Handle writing print token with proper cursor adjustment for ReadLineSafe @@ -573,7 +511,7 @@ namespace Microsoft.PowerShell } -#if !UNIX + /// /// /// If is set on , unset it and return true; @@ -593,6 +531,7 @@ namespace Microsoft.PowerShell /// false otherwise /// /// + private static bool shouldUnsetMode( ConsoleControl.ConsoleModes flagToUnset, ref ConsoleControl.ConsoleModes m) @@ -604,14 +543,11 @@ namespace Microsoft.PowerShell } return false; } -#endif #region WriteToConsole internal void WriteToConsole(string value, bool transcribeResult) { - -#if !UNIX ConsoleHandle handle = ConsoleControl.GetActiveScreenBufferHandle(); // Ensure that we're in the proper line-output mode. We don't lock here as it does not matter if we @@ -628,17 +564,12 @@ namespace Microsoft.PowerShell m |= desiredMode; ConsoleControl.SetMode(handle, m); } -#endif PreWrite(); // This is atomic, so we don't lock here... -#if !UNIX ConsoleControl.WriteConsole(handle, value); -#else - Console.Out.Write(value); -#endif if (isInteractiveTestToolListening && Console.IsOutputRedirected) { @@ -1539,9 +1470,9 @@ namespace Microsoft.PowerShell - // We use System.Environment.NewLine because we are platform-agnostic + // We don't use System.Environment.NewLine because we are very platform specific with our use of the win32 console APIs - internal static string Crlf = System.Environment.NewLine; + internal const string Crlf = "\x000D\x000A"; private const string Tab = "\x0009"; internal enum ReadLineResult @@ -1688,11 +1619,10 @@ namespace Microsoft.PowerShell private string ReadLineFromConsole(bool endOnTab, string initialContent, bool calledFromPipeline, ref string restOfLine, ref ReadLineResult result) { + ConsoleHandle handle = ConsoleControl.GetConioDeviceHandle(); PreRead(); // Ensure that we're in the proper line-input mode. -#if !UNIX - ConsoleHandle handle = ConsoleControl.GetConioDeviceHandle(); ConsoleControl.ConsoleModes m = ConsoleControl.GetMode(handle); const ConsoleControl.ConsoleModes desiredMode = @@ -1706,7 +1636,6 @@ namespace Microsoft.PowerShell m |= desiredMode; ConsoleControl.SetMode(handle, m); } -#endif // If more characters are typed than you asked, then the next call to ReadConsole will return the // additional characters beyond those you requested. @@ -1723,44 +1652,18 @@ namespace Microsoft.PowerShell // If input is terminated with a break key (Ctrl-C, Ctrl-Break, Close, etc.), then the buffer will be // the empty string. -#if UNIX - // For Unix systems, we implement a basic readline loop around Console.ReadKey(), that - // supports backspace, arrow keys, Ctrl-C, and Ctrl-D. This readline is only used for - // interactive prompts (like Read-Host), otherwise it is assumed that PSReadLine is - // available. Therefore this explicitly does not support history or tab completion. - - bool treatControlCAsInput = Console.TreatControlCAsInput; - - try - { - - ConsoleKeyInfo keyInfo; - string s = ""; - int index = 0; - int cursorLeft = Console.CursorLeft; - int cursorCurrent = cursorLeft; - bool insertMode = true; - Console.TreatControlCAsInput = true; -#else - rawui.ClearKeyCache(); uint keyState = 0; + + rawui.ClearKeyCache(); + string s = ""; -#endif do { -#if UNIX - keyInfo = Console.ReadKey(true); -#else s += ConsoleControl.ReadConsole(handle, initialContent, maxInputLineLength, endOnTab, out keyState); - Dbg.Assert(s != null, "s should never be null"); -#endif -#if UNIX - // Handle Ctrl-C ending input - if (keyInfo.Key == ConsoleKey.C && keyInfo.Modifiers.HasFlag(ConsoleModifiers.Control)) -#else + Dbg.Assert(s != null, "s should never be null"); + if (s.Length == 0) -#endif { result = ReadLineResult.endedOnBreak; s = null; @@ -1774,29 +1677,13 @@ namespace Microsoft.PowerShell break; } -#if UNIX - if (keyInfo.Key == ConsoleKey.Enter) -#else if (s.EndsWith(Crlf, StringComparison.CurrentCulture)) -#endif { result = ReadLineResult.endedOnEnter; -#if UNIX - // We're intercepting characters, so we need to echo the newline - Console.Out.WriteLine(); -#else s = s.Remove(s.Length - Crlf.Length); -#endif break; } -#if UNIX - if (keyInfo.Key == ConsoleKey.Tab) - { - // This is unsupported - continue; - } -#else int i = s.IndexOf(Tab, StringComparison.CurrentCulture); if (endOnTab && i != -1) @@ -1846,139 +1733,17 @@ namespace Microsoft.PowerShell break; } -#endif -#if UNIX - if (keyInfo.Key == ConsoleKey.Backspace) - { - if (index > 0) - { - int length = s.Length; - s = s.Remove(index - 1, 1); - index--; - cursorCurrent = Console.CursorLeft; - Console.CursorLeft = cursorLeft; - Console.Out.Write(s.PadRight(length)); - Console.CursorLeft = cursorCurrent - 1; - } - continue; - } - - if (keyInfo.Key == ConsoleKey.Delete - || (keyInfo.Key == ConsoleKey.D && keyInfo.Modifiers.HasFlag(ConsoleModifiers.Control))) - { - if (index < s.Length) - { - int length = s.Length; - s = s.Remove(index, 1); - cursorCurrent = Console.CursorLeft; - Console.CursorLeft = cursorLeft; - Console.Out.Write(s.PadRight(length)); - Console.CursorLeft = cursorCurrent; - } - continue; - } - - if (keyInfo.Key == ConsoleKey.LeftArrow - || (keyInfo.Key == ConsoleKey.B && keyInfo.Modifiers.HasFlag(ConsoleModifiers.Control))) - { - if (Console.CursorLeft > cursorLeft) - { - Console.CursorLeft--; - index--; - } - continue; - } - - if (keyInfo.Key == ConsoleKey.RightArrow - || (keyInfo.Key == ConsoleKey.F && keyInfo.Modifiers.HasFlag(ConsoleModifiers.Control))) - { - if (Console.CursorLeft < cursorLeft + s.Length) - { - Console.CursorLeft++; - index++; - } - continue; - } - - if (keyInfo.Key == ConsoleKey.UpArrow - || keyInfo.Key == ConsoleKey.DownArrow - || keyInfo.Key == ConsoleKey.PageUp - || keyInfo.Key == ConsoleKey.PageDown) - { - // Arrow/Page Up/down is unimplemented, so fail gracefully - continue; - } - - if (keyInfo.Key == ConsoleKey.Home - || (keyInfo.Key == ConsoleKey.A && keyInfo.Modifiers.HasFlag(ConsoleModifiers.Control))) - { - Console.CursorLeft = cursorLeft; - index = 0; - continue; - } - - if (keyInfo.Key == ConsoleKey.End - || (keyInfo.Key == ConsoleKey.E && keyInfo.Modifiers.HasFlag(ConsoleModifiers.Control))) - { - Console.CursorLeft = cursorLeft + s.Length; - index = s.Length; - continue; - } - - if (keyInfo.Key == ConsoleKey.Escape) - { - Console.CursorLeft = cursorLeft; - index = s.Length; - s = ""; - continue; - } - - if (keyInfo.Key == ConsoleKey.Insert) - { - // Toggle insert/overwrite mode - insertMode = !insertMode; - continue; - } - - if (Char.IsControl(keyInfo.KeyChar)) - { - // blacklist control characters - continue; - } - - // Modify string - if (!insertMode) // then overwrite mode - { - s = s.Remove(index, 1); - } - s = s.Insert(index, keyInfo.KeyChar.ToString()); - index++; - - // Redisplay string - cursorCurrent = Console.CursorLeft; - Console.CursorLeft = cursorLeft; - Console.Out.Write(s); - Console.CursorLeft = cursorCurrent + 1; -#endif } while (true); Dbg.Assert( - (s == null && result == ReadLineResult.endedOnBreak) - || (s != null && result != ReadLineResult.endedOnBreak), - "s should only be null if input ended with a break"); + (s == null && result == ReadLineResult.endedOnBreak) + || (s != null && result != ReadLineResult.endedOnBreak), + "s should only be null if input ended with a break"); return s; -#if UNIX - } - finally - { - Console.TreatControlCAsInput = treatControlCAsInput; - } -#endif } -#if !UNIX /// /// Get the character at the cursor when the user types 'tab' in the middle of line. /// @@ -2006,7 +1771,6 @@ namespace Microsoft.PowerShell Dbg.Assert(false, "the character at the cursor should be retrieved, never gets to here"); return '\0'; } -#endif /// @@ -2047,15 +1811,13 @@ namespace Microsoft.PowerShell /// internal string ReadLineWithTabCompletion(Executor exec) { - string input = null; - string lastInput = ""; - - ReadLineResult rlResult = ReadLineResult.endedOnEnter; - -#if !UNIX ConsoleHandle handle = ConsoleControl.GetActiveScreenBufferHandle(); + string input = null; + string lastInput = ""; string lastCompletion = ""; + + ReadLineResult rlResult = ReadLineResult.endedOnEnter; Size screenBufferSize = RawUI.BufferSize; // Save the cursor position at the end of the prompt string so that we can restore it later to write the @@ -2065,7 +1827,6 @@ namespace Microsoft.PowerShell CommandCompletion commandCompletion = null; string completionInput = null; -#endif do { @@ -2076,6 +1837,9 @@ namespace Microsoft.PowerShell input = ReadLine(true, lastInput, out rlResult, false, false); + Coordinates endOfInputCursorPos = RawUI.CursorPosition; + string completedInput = null; + if (input == null) { break; @@ -2086,13 +1850,6 @@ namespace Microsoft.PowerShell break; } -#if UNIX // Portable code only ends on enter (or no input), so tab is not processed - throw new PlatformNotSupportedException("This readline state is unsupported in portable code!"); -#else - - Coordinates endOfInputCursorPos = RawUI.CursorPosition; - string completedInput = null; - if (rlResult == ReadLineResult.endedOnTab || rlResult == ReadLineResult.endedOnShiftTab) { int tabIndex = input.IndexOf(Tab, StringComparison.CurrentCulture); @@ -2196,7 +1953,6 @@ namespace Microsoft.PowerShell lastInput = completedInput; } -#endif } while (true); @@ -2212,7 +1968,6 @@ namespace Microsoft.PowerShell return input; } -#if !UNIX private void SendLeftArrows(int length) { var inputs = new ConsoleControl.INPUT[length * 2]; @@ -2242,7 +1997,6 @@ namespace Microsoft.PowerShell ConsoleControl.MimicKeyPress(inputs); } -#endif private CommandCompletion GetNewCompletionResults(string input) { diff --git a/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleHostUserInterfacePrompt.cs b/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleHostUserInterfacePrompt.cs index d32653318..875ea3cf1 100644 --- a/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleHostUserInterfacePrompt.cs +++ b/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleHostUserInterfacePrompt.cs @@ -400,7 +400,7 @@ namespace Microsoft.PowerShell { object userInput = ReadLineSafe(false, null); string userInputString = userInput as string; - System.Management.Automation.Diagnostics.Assert(userInputString != null, "ReadLineSafe did not return a string"); + Diagnostics.Assert(userInputString != null, "ReadLineSafe did not return a string"); rawInputString = userInputString; } if (rawInputString == null) diff --git a/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleHostUserInterfacePromptForChoice.cs b/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleHostUserInterfacePromptForChoice.cs index df674b80e..0a74f226e 100644 --- a/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleHostUserInterfacePromptForChoice.cs +++ b/src/Microsoft.PowerShell.ConsoleHost/host/msh/ConsoleHostUserInterfacePromptForChoice.cs @@ -315,7 +315,7 @@ namespace Microsoft.PowerShell Dictionary defaultChoiceKeys, bool shouldEmulateForMultipleChoiceSelection) { - System.Management.Automation.Diagnostics.Assert(defaultChoiceKeys != null, "defaultChoiceKeys cannot be null."); + Diagnostics.Assert(defaultChoiceKeys != null, "defaultChoiceKeys cannot be null."); ConsoleColor fg = RawUI.ForegroundColor; ConsoleColor bg = RawUI.BackgroundColor; diff --git a/src/Microsoft.PowerShell.ConsoleHost/host/msh/ProgressPane.cs b/src/Microsoft.PowerShell.ConsoleHost/host/msh/ProgressPane.cs index 466864c0d..d213381d1 100644 --- a/src/Microsoft.PowerShell.ConsoleHost/host/msh/ProgressPane.cs +++ b/src/Microsoft.PowerShell.ConsoleHost/host/msh/ProgressPane.cs @@ -102,30 +102,14 @@ namespace Microsoft.PowerShell location.X = 0; location.Y = Math.Min(location.Y + 2, bufSize.Height); -#if UNIX - // replace the saved region in the screen buffer with our progress display - location = rawui.CursorPosition; - - //set the cursor position back to the beginning of the region to overwrite write-progress - //if the cursor is at the bottom, back it up to overwrite the previous write progress - if (location.Y >= rawui.BufferSize.Height - rows) - { - Console.Out.Write('\n'); - if (location.Y >= rows) - { - location.Y -= rows; - } - } - - rawui.CursorPosition = location; -#else // Save off the current contents of the screen buffer in the region that we will occupy + savedRegion = rawui.GetBufferContents( new Rectangle(location.X, location.Y, location.X + cols - 1, location.Y + rows - 1)); -#endif // replace the saved region in the screen buffer with our progress display + rawui.SetBufferContents(location, tempProgressRegion); } } diff --git a/src/Microsoft.PowerShell.CoreCLR.AssemblyLoadContext/CoreCLR/CorePsAssemblyLoadContext.cs b/src/Microsoft.PowerShell.CoreCLR.AssemblyLoadContext/CoreCLR/CorePsAssemblyLoadContext.cs index 6cf0d58b8..efe63addf 100644 --- a/src/Microsoft.PowerShell.CoreCLR.AssemblyLoadContext/CoreCLR/CorePsAssemblyLoadContext.cs +++ b/src/Microsoft.PowerShell.CoreCLR.AssemblyLoadContext/CoreCLR/CorePsAssemblyLoadContext.cs @@ -30,30 +30,21 @@ namespace System.Management.Automation // 2. Load assembly with culture 'en' (Microsoft.PowerShell.CoreCLR.AssemblyLoadContext.resources, Version=3.0.0.0, Culture=en, PublicKeyToken=31bf3856ad364e35) // When the first attempt fails, we again need to retrieve the resouce string to construct another exception, which ends up with an infinite loop. private const string BaseFolderDoesNotExist = "The base directory '{0}' does not exist."; + private const string CannotFindFileBasedOnAssemblyName = "Could not load file or assembly '{0}' or one of its dependencies. The system cannot find the file specified under any probing paths."; private const string ManifestDefinitionDoesNotMatch = "Could not load file or assembly '{0}' or one of its dependencies. The located assembly's manifest definition does not match the assembly reference."; private const string AssemblyPathDoesNotExist = "Could not load file or assembly '{0}' or one of its dependencies. The system cannot find the file specified."; private const string InvalidAssemblyExtensionName = "Could not load file or assembly '{0}' or one of its dependencies. The file specified is not a DLL file."; private const string AbsolutePathRequired = "Absolute path information is required."; - private const string SingletonAlreadyInitialized = "The singleton of PowerShellAssemblyLoadContext has already been initialized."; - private const string UseResolvingEventHandlerOnly = "PowerShellAssemblyLoadContext was initialized to use its 'Resolving' event handler only."; #endregion Resource_Strings #region Constructor /// - /// Initialize a singleton of PowerShellAssemblyLoadContext + /// This constructor is for testability purpose only /// - internal static PowerShellAssemblyLoadContext InitializeSingleton(string basePaths, bool useResolvingHandlerOnly) + protected PowerShellAssemblyLoadContext() { - lock (syncObj) - { - if (Instance != null) - throw new InvalidOperationException(SingletonAlreadyInitialized); - - Instance = new PowerShellAssemblyLoadContext(basePaths, useResolvingHandlerOnly); - return Instance; - } } /// @@ -63,25 +54,7 @@ namespace System.Management.Automation /// Base directory paths that are separated by semicolon ';'. /// They will be the default paths to probe assemblies. /// - /// - /// Indicate whether this instance is going to be used as a - /// full fledged ALC, or only its 'Resolve' handler is going - /// to be used. - /// - /// - /// When is true, we will register to the 'Resolving' event of the default - /// load context with our 'Resolve' method, and depend on the default load context to resolve/load assemblies for PS. - /// This mode is used when TPA list of the native host only contains .NET Core libraries. - /// In this case, TPA binder will be consulted before hitting our resolving logic. The binding order of Assembly.Load is: - /// TPA binder --> Resolving event - /// - /// When is false, we will use this instance as a full fledged load context - /// to resolve/load assemblies for PS. This mode is used when TPA list of the native host contains both .NET Core libraries - /// and PS assemblies. - /// In this case, our Load override will kick in before consulting the TPA binder. The binding order of Assembly.Load is: - /// Load override --> TPA binder --> Resolving event - /// - private PowerShellAssemblyLoadContext(string basePaths, bool useResolvingHandlerOnly) + internal PowerShellAssemblyLoadContext(string basePaths) { #region Validation if (string.IsNullOrEmpty(basePaths)) @@ -109,34 +82,17 @@ namespace System.Management.Automation this.probingPaths = new List(this.basePaths); // NEXT: Initialize the CoreCLR type catalog dictionary [OrdinalIgnoreCase] + // - Key: namespace qualified type name (FullName) + // - Value: strong name of the TPA that contains the type represented by Key. coreClrTypeCatalog = InitializeTypeCatalog(); - - // LAST: Handle useResolvingHandlerOnly flag - this.useResolvingHandlerOnly = useResolvingHandlerOnly; - this.activeLoadContext = useResolvingHandlerOnly ? Default : this; - if (useResolvingHandlerOnly) - { - Default.Resolving += Resolve; - } - else - { - var tempSet = new HashSet(coreClrTypeCatalog.Values, StringComparer.OrdinalIgnoreCase); - tpaSet = new HashSet(StringComparer.OrdinalIgnoreCase); - foreach (string tpa in tempSet) - { - string shortName = tpa.Substring(0, tpa.IndexOf(',')); - tpaSet.Add(shortName); - } - } } #endregion Constructor #region Fields - - private readonly bool useResolvingHandlerOnly; - private readonly AssemblyLoadContext activeLoadContext; - private readonly static object syncObj = new object(); + + // Serialized type catalog file + private readonly object syncObj = new object(); private readonly string[] basePaths; // Initially, 'probingPaths' only contains psbase path. But every time we load an assembly through 'LoadFrom(string AssemblyPath)', we // add its parent path to 'probingPaths', so that we are able to support implicit loading of an assembly from the same place where the @@ -144,11 +100,8 @@ namespace System.Management.Automation // We don't need to worry about removing any paths from 'probingPaths', because once an assembly is loaded, it won't be unloaded until // the current process exits, and thus the assembly itself and its parent folder cannot be deleted or renamed. private readonly List probingPaths; - // CoreCLR type catalog dictionary - // - Key: namespace qualified type name (FullName) - // - Value: strong name of the TPA that contains the type represented by Key. + // We use dictionary because the generated binary file by DataContractSerializer is about 39% smaller in size than using Hashtable. private readonly Dictionary coreClrTypeCatalog; - private readonly HashSet tpaSet; private readonly string[] extensions = new string[] { ".ni.dll", ".dll" }; /// @@ -170,18 +123,6 @@ namespace System.Management.Automation #endregion Fields - #region Properties - - /// - /// Singleton instance of PowerShellAssemblyLoadContext - /// - internal static PowerShellAssemblyLoadContext Instance - { - get; private set; - } - - #endregion Properties - #region Events /// @@ -198,24 +139,6 @@ namespace System.Management.Automation /// Search the file "[assemblyName.Name][.ni].dll" in probing paths. If the file is found and it matches the requested AssemblyName, load it with LoadFromAssemblyPath. /// protected override Assembly Load(AssemblyName assemblyName) - { - if (useResolvingHandlerOnly) - throw new NotSupportedException(UseResolvingEventHandlerOnly); - - // We let the default context load the assemblies included in the type catalog as there - // appears to be a bug in .NET with method resolution with system libraries loaded by our - // context and not the default. We use the short name because some packages have inconsistent - // verions between reference and runtime assemblies. - if (tpaSet.Contains(assemblyName.Name)) - return null; - - return Resolve(this, assemblyName); - } - - /// - /// The handler for the Resolving event - /// - private Assembly Resolve(AssemblyLoadContext loadContext, AssemblyName assemblyName) { // Probe the assembly cache Assembly asmLoaded; @@ -262,16 +185,25 @@ namespace System.Management.Automation } } - // We failed to find the assembly file; or we found the file, but the assembly file doesn't match the request. - // In this case, return null so that other Resolving event handlers can kick in to resolve the request. - if (!isAssemblyFileFound || !isAssemblyFileMatching) + // We failed to find the file specified + if (!isAssemblyFileFound) { - return null; + ThrowFileNotFoundException( + CannotFindFileBasedOnAssemblyName, + assemblyName.FullName); + } + + // We found the file specified, but the found assembly doesn't match the request + if (!isAssemblyFileMatching) + { + ThrowFileLoadException( + ManifestDefinitionDoesNotMatch, + assemblyName.FullName); } asmLoaded = asmFilePath.EndsWith(".ni.dll", StringComparison.OrdinalIgnoreCase) - ? loadContext.LoadFromNativeImagePath(asmFilePath, null) - : loadContext.LoadFromAssemblyPath(asmFilePath); + ? base.LoadFromNativeImagePath(asmFilePath, null) + : base.LoadFromAssemblyPath(asmFilePath); if (asmLoaded != null) { // Add the loaded assembly to the cache @@ -307,8 +239,8 @@ namespace System.Management.Automation // Load the assembly through 'LoadFromNativeImagePath' or 'LoadFromAssemblyPath' asmLoaded = assemblyPath.EndsWith(".ni.dll", StringComparison.OrdinalIgnoreCase) - ? activeLoadContext.LoadFromNativeImagePath(assemblyPath, null) - : activeLoadContext.LoadFromAssemblyPath(assemblyPath); + ? base.LoadFromNativeImagePath(assemblyPath, null) + : base.LoadFromAssemblyPath(assemblyPath); if (asmLoaded != null) { @@ -350,8 +282,8 @@ namespace System.Management.Automation if (TryGetAssemblyFromCache(assemblyName, out asmLoaded)) return asmLoaded; - // Load the assembly through 'LoadFromStream' - asmLoaded = activeLoadContext.LoadFromStream(assembly); + // Load the assembly through 'base.LoadFromStream' + asmLoaded = base.LoadFromStream(assembly); if (asmLoaded != null) { // Add the loaded assembly to the cache @@ -376,19 +308,7 @@ namespace System.Management.Automation string tpaStrongName; if (coreClrTypeCatalog.TryGetValue(namespaceQualifiedTypeName, out tpaStrongName)) { - try - { - return new Assembly[] { GetTrustedPlatformAssembly(tpaStrongName) }; - } - catch (FileNotFoundException) - { - // It's possible that the type catalog generated in OPS contains more entries than - // the one generated in windows build. This is because in OPS we have more freedom - // to control what packages to depend on, such as Json.NET. - // If we deploy the PSALC.dll generated from OPS to NanoServer, then it's possible - // that 'GetTrustedPlatformAssembly(tpaStrongName)' may fail for such entries. In - // this case, we ignore the exception and return our cached assemblies. - } + return new Assembly[] { GetTrustedPlatformAssembly(tpaStrongName) }; } } @@ -468,46 +388,10 @@ namespace System.Management.Automation return coreClrTypeCatalog.Keys; } - /// - /// Set the profile optimization root on the appropriate load context - /// - /// - /// When using PS ALC as a full fledged ALC in OPS, we don't enable profile optimization. - /// This is because PS assemblies will be recorded in the profile, and the next time OPS - /// starts up, the default context will load the PS assemblies pretty early to ngen them - /// in another CPU core, so our Load override won't track the loading of them, and thus - /// OPS will fail to work. - /// The root cause is that dotnet.exe put all PS assemblies in TPA list. If PS assemblies - /// are not in TPA list, then we can enable profile optimization without a problem. - /// - internal void SetProfileOptimizationRootImpl(string directoryPath) - { - if (this.useResolvingHandlerOnly) - activeLoadContext.SetProfileOptimizationRoot(directoryPath); - } - - /// - /// Start the profile optimization on the appropriate load context - /// - /// - /// When using PS ALC as a full fledged ALC in OPS, we don't enable profile optimization. - /// This is because PS assemblies will be recorded in the profile, and the next time OPS - /// starts up, the default context will load the PS assemblies pretty early to ngen them - /// in another CPU core, so our Load override won't track the loading of them, and thus - /// OPS will fail to work. - /// The root cause is that dotnet.exe put all PS assemblies in TPA list. If PS assemblies - /// are not in TPA list, then we can enable profile optimization without a problem. - /// - internal void StartProfileOptimizationImpl(string profile) - { - if (this.useResolvingHandlerOnly) - activeLoadContext.StartProfileOptimization(profile); - } - #endregion Protected_Internal_Methods - + #region Private_Methods - + /// /// Handle the AssemblyLoad event /// @@ -650,12 +534,9 @@ namespace System.Management.Automation /// private Assembly GetTrustedPlatformAssembly(string tpaStrongName) { - // We always depend on the default context to load the TPAs that are recorded in - // the type catalog. - // - If the requested TPA is already loaded, then 'Assembly.Load' will just get - // it back from the cache of default context. - // - If the requested TPA is not loaded yet, then 'Assembly.Load' will make the - // default context to load it + // Load the specified TPA. If the TPA is already loaded, it will be somehow + // cached in CoreCLR runtime, and thus calling 'Assembly.Load' again won't + // cause any overhead. AssemblyName assemblyName = new AssemblyName(tpaStrongName); Assembly asmLoaded = Assembly.Load(assemblyName); return asmLoaded; @@ -683,129 +564,29 @@ namespace System.Management.Automation } /// + /// Set an instance of PowerShellAssemblyLoadContext to be the default Assembly Load Context. /// This is the managed entry point for Microsoft.PowerShell.CoreCLR.AssemblyLoadContext.dll. /// public class PowerShellAssemblyLoadContextInitializer { - private static object[] EmptyArray = new object[0]; + private static bool IsInitialized = false; /// - /// Create a singleton of PowerShellAssemblyLoadContext. - /// Then register to the Resolving event of the load context that loads this assembly. + /// Set the default Assembly Load Context /// - /// - /// This method is to be used by native host whose TPA list doesn't include PS assemblies, such as the - /// in-box Nano powershell.exe, the PS remote WinRM plugin, in-box Nano DSC and in-box Nano SCOM agent. - /// - /// - /// Base directory paths that are separated by semicolon ';'. - /// They will be the default paths to probe assemblies. - /// public static void SetPowerShellAssemblyLoadContext([MarshalAs(UnmanagedType.LPWStr)]string basePaths) { if (string.IsNullOrEmpty(basePaths)) + { throw new ArgumentNullException("basePaths"); + } - PowerShellAssemblyLoadContext.InitializeSingleton(basePaths, useResolvingHandlerOnly: true); - } - - /// - /// Create a singleton of PowerShellAssemblyLoadContext. - /// Then load System.Management.Automation and call the WSManPluginManagedEntryWrapper delegate. - /// - /// - /// This method is used by the native host of the PSRP plugin. - /// - /// - /// Passed to delegate. - /// - public static int WSManPluginWrapper(IntPtr wkrPtrs) - { - string basePaths = System.IO.Path.GetDirectoryName(typeof(PowerShellAssemblyLoadContextInitializer).GetTypeInfo().Assembly.Location); - string entryAssemblyName = "System.Management.Automation, Version=3.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35"; - string entryTypeName = "System.Management.Automation.Remoting.WSManPluginManagedEntryWrapper"; - string entryMethodName = "InitPlugin"; - object[] args = { wkrPtrs }; - - var psLoadContext = PowerShellAssemblyLoadContext.InitializeSingleton(basePaths, useResolvingHandlerOnly: false); - var entryAssembly = psLoadContext.LoadFromAssemblyName(new AssemblyName(entryAssemblyName)); - var entryType = entryAssembly.GetType(entryTypeName, throwOnError: true, ignoreCase: true); - var methodInfo = entryType.GetMethod(entryMethodName, BindingFlags.Static | BindingFlags.Public | BindingFlags.IgnoreCase); - - return (int)methodInfo.Invoke(null, args); - } - - /// - /// Create a singleton of PowerShellAssemblyLoadContext. - /// Then load the assembly containing the actual entry point using it. - /// - /// - /// Base directory paths that are separated by semicolon ';'. - /// They will be the default paths to probe assemblies. - /// - /// - /// Name of the assembly that contains the actual entry point. - /// - /// - /// The assembly that contains the actual entry point. - /// - public static Assembly InitializeAndLoadEntryAssembly(string basePaths, AssemblyName entryAssemblyName) - { - if (string.IsNullOrEmpty(basePaths)) - throw new ArgumentNullException("basePaths"); - - if (entryAssemblyName == null) - throw new ArgumentNullException("entryAssemblyName"); - - var psLoadContext = PowerShellAssemblyLoadContext.InitializeSingleton(basePaths, useResolvingHandlerOnly: false); - return psLoadContext.LoadFromAssemblyName(entryAssemblyName); - } - - /// - /// Create a singleton of PowerShellAssemblyLoadContext. - /// Then call into the actual entry point based on the given assembly name, type name, method name and arguments. - /// - /// - /// Base directory paths that are separated by semicolon ';'. - /// They will be the default paths to probe assemblies. - /// - /// - /// Name of the assembly that contains the actual entry point. - /// - /// - /// Name of the type that contains the actual entry point. - /// - /// - /// Name of the actual entry point method. - /// - /// - /// An array of arguments passed to the entry point method. - /// - /// - /// The return value of running the entry point method. - /// - public static object InitializeAndCallEntryMethod(string basePaths, AssemblyName entryAssemblyName, string entryTypeName, string entryMethodName, object[] args) - { - if (string.IsNullOrEmpty(basePaths)) - throw new ArgumentNullException("basePaths"); - - if (entryAssemblyName == null) - throw new ArgumentNullException("entryAssemblyName"); - - if (string.IsNullOrEmpty(entryTypeName)) - throw new ArgumentNullException("entryTypeName"); - - if (string.IsNullOrEmpty(entryMethodName)) - throw new ArgumentNullException("entryMethodName"); - - args = args ?? EmptyArray; - - var psLoadContext = PowerShellAssemblyLoadContext.InitializeSingleton(basePaths, useResolvingHandlerOnly: false); - var entryAssembly = psLoadContext.LoadFromAssemblyName(entryAssemblyName); - var entryType = entryAssembly.GetType(entryTypeName, throwOnError: true, ignoreCase: true); - var methodInfo = entryType.GetMethod(entryMethodName, BindingFlags.Static | BindingFlags.Public | BindingFlags.IgnoreCase); - - return methodInfo.Invoke(null, args); + if (!IsInitialized) + { + var psAsmLoadContext = new PowerShellAssemblyLoadContext(basePaths); + AssemblyLoadContext.InitializeDefaultContext(psAsmLoadContext); + IsInitialized = true; + } } } } diff --git a/src/Microsoft.PowerShell.GraphicalHost/commandHelpers/ShowCommandHelper.cs b/src/Microsoft.PowerShell.GraphicalHost/commandHelpers/ShowCommandHelper.cs index eb28de82e..43085f4c8 100644 --- a/src/Microsoft.PowerShell.GraphicalHost/commandHelpers/ShowCommandHelper.cs +++ b/src/Microsoft.PowerShell.GraphicalHost/commandHelpers/ShowCommandHelper.cs @@ -1303,7 +1303,7 @@ Function PSGetSerializedShowCommandInfo MessageBox.Show( String.Format( CultureInfo.CurrentUICulture, - ShowCommandResources.EndProcessingErrorMessage, + Microsoft.Management.UI.Internal.ShowCommandResources.EndProcessingErrorMessage, errorString), "Show-Command", MessageBoxButton.OK, diff --git a/src/Microsoft.PowerShell.GraphicalHost/commandHelpers/outgridview.cs b/src/Microsoft.PowerShell.GraphicalHost/commandHelpers/outgridview.cs index c25a951f8..c0a1a0807 100644 --- a/src/Microsoft.PowerShell.GraphicalHost/commandHelpers/outgridview.cs +++ b/src/Microsoft.PowerShell.GraphicalHost/commandHelpers/outgridview.cs @@ -75,12 +75,12 @@ namespace Microsoft.Management.UI.Internal /// /// OK Button's content. /// - private static readonly string OKButtonContent = XamlLocalizableResources.OutGridView_Button_OK; + private static readonly string OKButtonContent = Microsoft.Management.UI.Internal.XamlLocalizableResources.OutGridView_Button_OK; /// /// Cancel Button's content. /// - private static readonly string CancelButtonContent = XamlLocalizableResources.OutGridView_Button_Cancel; + private static readonly string CancelButtonContent = Microsoft.Management.UI.Internal.XamlLocalizableResources.OutGridView_Button_Cancel; /// /// Used to store selected items in the ok processing diff --git a/src/Microsoft.PowerShell.GraphicalHost/xamls/HelpWindow.xaml b/src/Microsoft.PowerShell.GraphicalHost/xamls/HelpWindow.xaml index 36c7a13bb..a002684f9 100644 --- a/src/Microsoft.PowerShell.GraphicalHost/xamls/HelpWindow.xaml +++ b/src/Microsoft.PowerShell.GraphicalHost/xamls/HelpWindow.xaml @@ -45,7 +45,7 @@ - + diff --git a/src/Microsoft.PowerShell.LocalAccounts/LocalAccounts/Extensions.cs b/src/Microsoft.PowerShell.LocalAccounts/LocalAccounts/Extensions.cs index fdc8c2c82..2d43f187c 100644 --- a/src/Microsoft.PowerShell.LocalAccounts/LocalAccounts/Extensions.cs +++ b/src/Microsoft.PowerShell.LocalAccounts/LocalAccounts/Extensions.cs @@ -160,7 +160,7 @@ namespace System.Management.Automation.SecurityAccountsManager.Extensions #if CORECLR IntPtr buffer = SecureStringMarshal.SecureStringToCoTaskMemUnicode(str); string clear = Marshal.PtrToStringUni(buffer); - Marshal.ZeroFreeCoTaskMemUnicode(buffer); + SecureStringMarshal.ZeroFreeCoTaskMemUnicode(buffer); #else var bstr = Marshal.SecureStringToBSTR(str); string clear = Marshal.PtrToStringAuto(bstr); @@ -200,4 +200,4 @@ namespace System.Management.Automation.SecurityAccountsManager.Extensions return ex.MakeErrorRecord(ex.ErrorName, ex.ErrorCategory, target ?? ex.Target); } } -} +} \ No newline at end of file diff --git a/src/Microsoft.PowerShell.PackageManagement/Cmdlets/CmdletBase.cs b/src/Microsoft.PowerShell.PackageManagement/Cmdlets/CmdletBase.cs index 5f2d1f9e0..85d9ddbc1 100644 --- a/src/Microsoft.PowerShell.PackageManagement/Cmdlets/CmdletBase.cs +++ b/src/Microsoft.PowerShell.PackageManagement/Cmdlets/CmdletBase.cs @@ -477,7 +477,6 @@ namespace Microsoft.PowerShell.PackageManagement.Cmdlets { #region Event and telemetry stuff //Calling PowerShell Telemetry APIs protected void TraceMessage(string message, SoftwareIdentity swidObject) { -#if !UNIX TelemetryAPI.TraceMessage(message, new { PackageName = swidObject.Name, @@ -487,7 +486,6 @@ namespace Microsoft.PowerShell.PackageManagement.Cmdlets { ExuectionStatus = swidObject.Status, ExecutionTime = DateTime.Today }); -#endif } protected enum EventTask { @@ -510,7 +508,6 @@ namespace Microsoft.PowerShell.PackageManagement.Cmdlets { protected void LogEvent(EventTask task, EventId id, string context, string name, string version, string providerName, string source, string status, string destinationPath) { -#if !UNIX var iis = InitialSessionState.CreateDefault2(); using (Runspace rs = RunspaceFactory.CreateRunspace(iis)) @@ -537,8 +534,7 @@ namespace Microsoft.PowerShell.PackageManagement.Cmdlets { Verbose(ex.Message); } } - } -#endif + } } #endregion diff --git a/src/Microsoft.PowerShell.PackageManagement/Cmdlets/FindPackage.cs b/src/Microsoft.PowerShell.PackageManagement/Cmdlets/FindPackage.cs index 5567feb86..c85a89a62 100644 --- a/src/Microsoft.PowerShell.PackageManagement/Cmdlets/FindPackage.cs +++ b/src/Microsoft.PowerShell.PackageManagement/Cmdlets/FindPackage.cs @@ -57,12 +57,7 @@ namespace Microsoft.PowerShell.PackageManagement.Cmdlets { return true; } - protected override void ProcessPackage(PackageProvider provider, IEnumerable searchKey, SoftwareIdentity package) - { - ProcessPackage(provider, searchKey, package, IncludeDependencies ? new HashSet() : null); - } - - private void ProcessPackage(PackageProvider provider, IEnumerable searchKey, SoftwareIdentity package, HashSet processedDependencies) { + protected override void ProcessPackage(PackageProvider provider, IEnumerable searchKey, SoftwareIdentity package) { try { @@ -76,24 +71,14 @@ namespace Microsoft.PowerShell.PackageManagement.Cmdlets { foreach (var dep in package.Dependencies) { // note: future work may be needed if the package sources currently selected by the user don't // contain the dependencies. + var dependendcies = PackageManagementService.FindPackageByCanonicalId(dep, this); + var depPkg = dependendcies.OrderByDescending(pp => pp, SoftwareIdentityVersionComparer.Instance).FirstOrDefault(); - // this dep is not processed yet - if (!processedDependencies.Contains(dep)) - { - var dependendcies = PackageManagementService.FindPackageByCanonicalId(dep, this); - var depPkg = dependendcies.OrderByDescending(pp => pp, SoftwareIdentityVersionComparer.Instance).FirstOrDefault(); - - processedDependencies.Add(dep); - - if (depPkg == null) - { - missingDependencies.Add(dep); - Warning(Constants.Messages.UnableToFindDependencyPackage, dep); - } - else - { - ProcessPackage(depPkg.Provider, searchKey.Select(each => each + depPkg.Name).ToArray(), depPkg, processedDependencies); - } + if (depPkg == null) { + missingDependencies.Add(dep); + Warning(Constants.Messages.UnableToFindDependencyPackage, dep); + } else { + ProcessPackage(depPkg.Provider, searchKey.Select(each => each + depPkg.Name).ToArray(), depPkg); } } if (missingDependencies.Any()) { diff --git a/src/Microsoft.PowerShell.Security/security/CatalogCommands.cs b/src/Microsoft.PowerShell.Security/security/CatalogCommands.cs index 46ba8b97c..4ccdd4386 100644 --- a/src/Microsoft.PowerShell.Security/security/CatalogCommands.cs +++ b/src/Microsoft.PowerShell.Security/security/CatalogCommands.cs @@ -1,5 +1,3 @@ -#if !UNIX - /********************************************************************++ Copyright (c) Microsoft Corporation. All rights reserved. --********************************************************************/ @@ -281,6 +279,4 @@ namespace Microsoft.PowerShell.Commands } } -} - -#endif +} \ No newline at end of file diff --git a/src/Microsoft.PowerShell.Workflow.ServiceCore/ServiceCore/WorkflowCore/PSActivityBase.cs b/src/Microsoft.PowerShell.Workflow.ServiceCore/ServiceCore/WorkflowCore/PSActivityBase.cs index 08488f263..92c070352 100644 --- a/src/Microsoft.PowerShell.Workflow.ServiceCore/ServiceCore/WorkflowCore/PSActivityBase.cs +++ b/src/Microsoft.PowerShell.Workflow.ServiceCore/ServiceCore/WorkflowCore/PSActivityBase.cs @@ -3956,12 +3956,7 @@ namespace Microsoft.PowerShell.Activities { try { - var psvar = runspace.SessionStateProxy.PSVariable.Get(name); - if (psvar == null || (psvar.Options & ScopedItemOptions.ReadOnly) == 0) - { - // don't try to overwrite read-only variables values - runspace.SessionStateProxy.PSVariable.Set(name, value); - } + runspace.SessionStateProxy.PSVariable.Set(name, value); } catch (PSNotSupportedException) { diff --git a/src/Microsoft.PowerShell.Workflow.ServiceCore/ServiceCore/WorkflowCore/WorkflowJob2.cs b/src/Microsoft.PowerShell.Workflow.ServiceCore/ServiceCore/WorkflowCore/WorkflowJob2.cs index da2669f5a..5b1ac63f4 100644 --- a/src/Microsoft.PowerShell.Workflow.ServiceCore/ServiceCore/WorkflowCore/WorkflowJob2.cs +++ b/src/Microsoft.PowerShell.Workflow.ServiceCore/ServiceCore/WorkflowCore/WorkflowJob2.cs @@ -1307,8 +1307,9 @@ namespace Microsoft.PowerShell.Workflow AddParameter("Depth", 10). AddParameter("Path", tempPath).Invoke(); - throw new Exception("Bug MSFT:246456 detected. Please capture " + tempPath + ", open a new issue " + - "at https://github.com/PowerShell/PowerShell/issues/new and attach the file."); + throw new Exception("Bug MSFT:246456 detected. Please capture " + tempPath + ", attach it to " + + "https://microsoft.visualstudio.com/DefaultCollection/WSSC/_workItems#id=246456&_a=edit, and " + + "then reassign the bug to leeholm."); } else { diff --git a/src/Microsoft.WSMan.Management/WsManHelper.cs b/src/Microsoft.WSMan.Management/WsManHelper.cs index 5de81324b..53296c141 100644 --- a/src/Microsoft.WSMan.Management/WsManHelper.cs +++ b/src/Microsoft.WSMan.Management/WsManHelper.cs @@ -87,7 +87,7 @@ namespace Microsoft.WSMan.Management private FileStream _fs; private StreamReader _sr; - private static ResourceManager g_resourceMgr = new ResourceManager("Microsoft.WSMan.Management.resources.WsManResources", typeof(WSManHelper).GetTypeInfo().Assembly); + private static ResourceManager g_resourceMgr = new ResourceManager("WsManResources", typeof(WSManHelper).GetTypeInfo().Assembly); // @@ -135,16 +135,20 @@ namespace Microsoft.WSMan.Management internal WSManHelper() { + + _resourceMgr = new ResourceManager("WsManResources", this.GetType().GetTypeInfo().Assembly); } internal WSManHelper(PSCmdlet cmdlet) { cmdletname = cmdlet; + _resourceMgr = new ResourceManager("WsManResources", this.GetType().GetTypeInfo().Assembly); } internal WSManHelper(NavigationCmdletProvider provider) { _provider = provider; + _resourceMgr = new ResourceManager("WsManResources", this.GetType().GetTypeInfo().Assembly); } internal static void ThrowIfNotAdministrator() @@ -160,13 +164,14 @@ namespace Microsoft.WSMan.Management internal string GetResourceMsgFromResourcetext(string rscname) { - return g_resourceMgr.GetString(rscname); + return _resourceMgr.GetString(rscname); } static internal string FormatResourceMsgFromResourcetextS(string rscname, params object[] args) { - return FormatResourceMsgFromResourcetextS(g_resourceMgr, rscname, args); + ResourceManager resourceManager = new ResourceManager("WsManResources", typeof(WSManHelper).GetTypeInfo().Assembly); + return FormatResourceMsgFromResourcetextS(resourceManager, rscname, args); } internal string FormatResourceMsgFromResourcetext(string resourceName, diff --git a/src/Modules/Shared/Microsoft.PowerShell.Archive/ArchiveResources.psd1 b/src/Modules/Shared/Microsoft.PowerShell.Archive/ArchiveResources.psd1 index 508ea5b41..914f951df 100644 Binary files a/src/Modules/Shared/Microsoft.PowerShell.Archive/ArchiveResources.psd1 and b/src/Modules/Shared/Microsoft.PowerShell.Archive/ArchiveResources.psd1 differ diff --git a/src/Modules/Shared/Microsoft.PowerShell.Archive/Microsoft.PowerShell.Archive.psm1 b/src/Modules/Shared/Microsoft.PowerShell.Archive/Microsoft.PowerShell.Archive.psm1 index e179118c2..bb645b27b 100644 Binary files a/src/Modules/Shared/Microsoft.PowerShell.Archive/Microsoft.PowerShell.Archive.psm1 and b/src/Modules/Shared/Microsoft.PowerShell.Archive/Microsoft.PowerShell.Archive.psm1 differ diff --git a/src/Modules/Shared/Microsoft.PowerShell.Utility/Microsoft.PowerShell.Utility.psm1 b/src/Modules/Shared/Microsoft.PowerShell.Utility/Microsoft.PowerShell.Utility.psm1 index 7a5f06360..2328d1dc9 100644 --- a/src/Modules/Shared/Microsoft.PowerShell.Utility/Microsoft.PowerShell.Utility.psm1 +++ b/src/Modules/Shared/Microsoft.PowerShell.Utility/Microsoft.PowerShell.Utility.psm1 @@ -587,7 +587,7 @@ function ConvertFrom-SddlString Begin { # On CoreCLR CryptoKeyRights and ActiveDirectoryRights are not supported. - if ($PSEdition -eq "PowerShellCore" -and ($Type -eq "CryptoKeyRights" -or $Type -eq "ActiveDirectoryRights")) + if ($PSEdition -eq "Core" -and ($Type -eq "CryptoKeyRights" -or $Type -eq "ActiveDirectoryRights")) { $errorId = "TypeNotSupported" $errorCategory = [System.Management.Automation.ErrorCategory]::InvalidArgument @@ -622,7 +622,7 @@ function ConvertFrom-SddlString { param($AccessMask, $Type) - if ($PSEdition -eq "PowerShellCore") + if ($PSEdition -eq "Core") { ## All the types of access rights understood by .NET Core $rightTypes = [Ordered] @{ diff --git a/src/Modules/Shared/PowerShellGet/PSGet.Resource.psd1 b/src/Modules/Shared/PowerShellGet/PSGet.Resource.psd1 index 395bfd6d6..178b8e8a8 100644 Binary files a/src/Modules/Shared/PowerShellGet/PSGet.Resource.psd1 and b/src/Modules/Shared/PowerShellGet/PSGet.Resource.psd1 differ diff --git a/src/Modules/Shared/PowerShellGet/PSModule.psm1 b/src/Modules/Shared/PowerShellGet/PSModule.psm1 index 3bf44f236..0e6b90e69 100644 --- a/src/Modules/Shared/PowerShellGet/PSModule.psm1 +++ b/src/Modules/Shared/PowerShellGet/PSModule.psm1 @@ -14,44 +14,25 @@ Microsoft.PowerShell.Core\Set-StrictMode -Version Latest # Check if this is nano server. [System.Runtime.Loader.AssemblyLoadContext] is only available on NanoServer $script:isNanoServer = $null -ne ('System.Runtime.Loader.AssemblyLoadContext' -as [Type]) -function IsWindows { $PSVariable = Get-Variable -Name IsWindows -ErrorAction Ignore; return (-not $PSVariable -or $PSVariable.Value) } -function IsLinux { $PSVariable = Get-Variable -Name IsLinux -ErrorAction Ignore; return ($PSVariable -and $PSVariable.Value) } -function IsOSX { $PSVariable = Get-Variable -Name IsOSX -ErrorAction Ignore; return ($PSVariable -and $PSVariable.Value) } -function IsCoreCLR { $PSVariable = Get-Variable -Name IsCoreCLR -ErrorAction Ignore; return ($PSVariable -and $PSVariable.Value) } - -if(IsWindows) +try { - $script:ProgramFilesPSPath = Microsoft.PowerShell.Management\Join-Path -Path $env:ProgramFiles -ChildPath "WindowsPowerShell" + $script:MyDocumentsFolderPath = [Environment]::GetFolderPath("MyDocuments") } -else +catch { - $script:ProgramFilesPSPath = $PSHome + $script:MyDocumentsFolderPath = $null } -if(IsWindows) -{ - try - { - $script:MyDocumentsFolderPath = [Environment]::GetFolderPath("MyDocuments") - } - catch - { - $script:MyDocumentsFolderPath = $null - } +$script:ProgramFilesPSPath = Microsoft.PowerShell.Management\Join-Path -Path $env:ProgramFiles -ChildPath "WindowsPowerShell" - $script:MyDocumentsPSPath = if($script:MyDocumentsFolderPath) - { - Microsoft.PowerShell.Management\Join-Path -Path $script:MyDocumentsFolderPath -ChildPath "WindowsPowerShell" - } - else - { - Microsoft.PowerShell.Management\Join-Path -Path $env:USERPROFILE -ChildPath "Documents\WindowsPowerShell" - } -} -else -{ - $script:MyDocumentsPSPath = Microsoft.PowerShell.Management\Join-Path -Path $HOME -ChildPath ".local/share/powershell" -} +$script:MyDocumentsPSPath = if($script:MyDocumentsFolderPath) + { + Microsoft.PowerShell.Management\Join-Path -Path $script:MyDocumentsFolderPath -ChildPath "WindowsPowerShell" + } + else + { + Microsoft.PowerShell.Management\Join-Path -Path $env:USERPROFILE -ChildPath "Documents\WindowsPowerShell" + } $script:ProgramFilesModulesPath = Microsoft.PowerShell.Management\Join-Path -Path $script:ProgramFilesPSPath -ChildPath "Modules" $script:MyDocumentsModulesPath = Microsoft.PowerShell.Management\Join-Path -Path $script:MyDocumentsPSPath -ChildPath "Modules" @@ -60,20 +41,10 @@ $script:ProgramFilesScriptsPath = Microsoft.PowerShell.Management\Join-Path -Pat $script:MyDocumentsScriptsPath = Microsoft.PowerShell.Management\Join-Path -Path $script:MyDocumentsPSPath -ChildPath "Scripts" -$script:TempPath = if(IsWindows){ ([System.IO.DirectoryInfo]$env:TEMP).FullName } else { '/tmp' } +$script:TempPath = ([System.IO.DirectoryInfo]$env:TEMP).FullName $script:PSGetItemInfoFileName = "PSGetModuleInfo.xml" - -if(IsWindows) -{ - $script:PSGetProgramDataPath = Microsoft.PowerShell.Management\Join-Path -Path $env:ProgramData -ChildPath 'Microsoft\Windows\PowerShell\PowerShellGet\' - $script:PSGetAppLocalPath = Microsoft.PowerShell.Management\Join-Path -Path $env:LOCALAPPDATA -ChildPath 'Microsoft\Windows\PowerShell\PowerShellGet\' -} -else -{ - $script:PSGetProgramDataPath = "$HOME/.config/powershell/powershellget" #TODO: Get $env:ProgramData equivalent - $script:PSGetAppLocalPath = "$HOME/.config/powershell/powershellget" -} - +$script:PSGetProgramDataPath = Microsoft.PowerShell.Management\Join-Path -Path $env:ProgramData -ChildPath 'Microsoft\Windows\PowerShell\PowerShellGet\' +$script:PSGetAppLocalPath = Microsoft.PowerShell.Management\Join-Path -Path $env:LOCALAPPDATA -ChildPath 'Microsoft\Windows\PowerShell\PowerShellGet\' $script:PSGetModuleSourcesFilePath = Microsoft.PowerShell.Management\Join-Path -Path $script:PSGetAppLocalPath -ChildPath "PSRepositories.xml" $script:PSGetModuleSources = $null $script:PSGetInstalledModules = $null @@ -118,8 +89,8 @@ $script:NuGetProviderVersion = [Version]'2.8.5.201' $script:SupportsPSModulesFeatureName="supports-powershell-modules" $script:FastPackRefHastable = @{} -$script:NuGetBinaryProgramDataPath=if(IsWindows) {"$env:ProgramFiles\PackageManagement\ProviderAssemblies"} -$script:NuGetBinaryLocalAppDataPath=if(IsWindows) {"$env:LOCALAPPDATA\PackageManagement\ProviderAssemblies"} +$script:NuGetBinaryProgramDataPath="$env:ProgramFiles\PackageManagement\ProviderAssemblies" +$script:NuGetBinaryLocalAppDataPath="$env:LOCALAPPDATA\PackageManagement\ProviderAssemblies" # go fwlink for 'https://nuget.org/nuget.exe' $script:NuGetClientSourceURL = 'http://go.microsoft.com/fwlink/?LinkID=690216&clcid=0x409' $script:NuGetExeName = 'NuGet.exe' @@ -425,7 +396,10 @@ Microsoft.PowerShell.Utility\Import-LocalizedData LocalizedData -filename PSGet # This code is required to add a .Net type and call the Telemetry APIs # This is required since PowerShell does not support generation of .Net Anonymous types # -$requiredAssembly = @( "system.management.automation, Version=3.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35" ) +$requiredAssembly = @( "system.management.automation, Version=3.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35", + "$([System.Net.IWebProxy].AssemblyQualifiedName)".Substring('System.Net.IWebProxy'.Length+1).Trim(), + "$([System.Uri].AssemblyQualifiedName)".Substring('System.Uri'.Length+1).Trim() + ) $source = @" using System; @@ -450,6 +424,47 @@ namespace Microsoft.PowerShell.Commands.PowerShellGet } } + + /// + /// Used by Ping-Endpoint function to supply webproxy to HttpClient + /// We cannot use System.Net.WebProxy because this is not available on CoreClr + /// + public class InternalWebProxy : IWebProxy + { + Uri _proxyUri; + ICredentials _credentials; + + public InternalWebProxy(Uri uri, ICredentials credentials) + { + Credentials = credentials; + _proxyUri = uri; + } + + /// + /// Credentials used by WebProxy + /// + public ICredentials Credentials + { + get + { + return _credentials; + } + set + { + _credentials = value; + } + } + + public Uri GetProxy(Uri destination) + { + return _proxyUri; + } + + public bool IsBypassed(Uri host) + { + return false; + } + } [StructLayout(LayoutKind.Sequential, CharSet=CharSet.Unicode)] public struct CERT_CHAIN_POLICY_PARA { @@ -549,7 +564,7 @@ $script:TelemetryEnabled = $false try { # If the telemetry namespace/methods are not found flow goes to the catch block where telemetry is disabled - $telemetryMethods = ([Microsoft.PowerShell.Commands.PowerShellGet.Telemetry] | Get-Member -Static).Name + $telemetryMethods = ([Microsoft.PowerShell.Get.Telemetry] | Get-Member -Static).Name if ($telemetryMethods.Contains("TraceMessageArtifactsNotFound") -and $telemetryMethods.Contains("TraceMessageNonPSGalleryRegistration")) { @@ -562,14 +577,14 @@ catch # Ignore the error and try adding the type below } -if(-not $script:TelemetryEnabled -and (IsWindows)) +if(-not $script:TelemetryEnabled) { try { Add-Type -ReferencedAssemblies $requiredAssembly -TypeDefinition $source -Language CSharp -ErrorAction SilentlyContinue # If the telemetry namespace/methods are not found flow goes to the catch block where telemetry is disabled - $telemetryMethods = ([Microsoft.PowerShell.Commands.PowerShellGet.Telemetry] | Get-Member -Static).Name + $telemetryMethods = ([Microsoft.PowerShell.Get.Telemetry] | Get-Member -Static).Name if ($telemetryMethods.Contains("TraceMessageArtifactsNotFound") -and $telemetryMethods.Contains("TraceMessageNonPSGalleryRegistration")) { @@ -584,66 +599,6 @@ if(-not $script:TelemetryEnabled -and (IsWindows)) } } -$RequiredAssembliesForInternalWebProxy = @( "$([System.Net.IWebProxy].AssemblyQualifiedName)".Substring('System.Net.IWebProxy'.Length+1).Trim(), - "$([System.Uri].AssemblyQualifiedName)".Substring('System.Uri'.Length+1).Trim() ) - -$SourceForInternalWebProxy = @" -using System; -using System.Net; - -namespace Microsoft.PowerShell.Commands.PowerShellGet -{ - /// - /// Used by Ping-Endpoint function to supply webproxy to HttpClient - /// We cannot use System.Net.WebProxy because this is not available on CoreClr - /// - public class InternalWebProxy : IWebProxy - { - Uri _proxyUri; - ICredentials _credentials; - - public InternalWebProxy(Uri uri, ICredentials credentials) - { - Credentials = credentials; - _proxyUri = uri; - } - - /// - /// Credentials used by WebProxy - /// - public ICredentials Credentials - { - get - { - return _credentials; - } - set - { - _credentials = value; - } - } - - public Uri GetProxy(Uri destination) - { - return _proxyUri; - } - - public bool IsBypassed(Uri host) - { - return false; - } - } -} -"@ - -if(-not ('Microsoft.PowerShell.Commands.PowerShellGet.InternalWebProxy' -as [Type])) -{ - Add-Type -ReferencedAssemblies $RequiredAssembliesForInternalWebProxy ` - -TypeDefinition $SourceForInternalWebProxy ` - -Language CSharp ` - -ErrorAction SilentlyContinue -} - #endregion #region *-Module cmdlets @@ -727,7 +682,7 @@ function Publish-Module Begin { - if($script:isNanoServer -or (IsCoreCLR)) { + if($script:isNanoServer) { $message = $LocalizedData.PublishPSArtifactUnsupportedOnNano -f "Module" ThrowError -ExceptionName "System.InvalidOperationException" ` -ExceptionMessage $message ` @@ -889,7 +844,7 @@ function Publish-Module } else { - $resolvedPath = Resolve-PathHelper -Path $Path -CallerPSCmdlet $PSCmdlet | Microsoft.PowerShell.Utility\Select-Object -First 1 -ErrorAction Ignore + $resolvedPath = Resolve-PathHelper -Path $Path -CallerPSCmdlet $PSCmdlet | Microsoft.PowerShell.Utility\Select-Object -First 1 if(-not $resolvedPath -or -not (Microsoft.PowerShell.Management\Test-Path -Path $resolvedPath -PathType Container)) @@ -1079,7 +1034,7 @@ function Publish-Module # Use Find-Script to check if that name is already used as scriptname $scriptPSGetItemInfo = Find-Script @FindParameters | Microsoft.PowerShell.Core\Where-Object {$_.Name -eq $moduleName} | - Microsoft.PowerShell.Utility\Select-Object -Last 1 -ErrorAction Ignore + Microsoft.PowerShell.Utility\Select-Object -Last 1 if($scriptPSGetItemInfo) { $message = $LocalizedData.SpecifiedNameIsAlearyUsed -f ($moduleName, $Repository, 'Find-Script') @@ -1094,7 +1049,7 @@ function Publish-Module $null = $FindParameters.Remove('Tag') $currentPSGetItemInfo = Find-Module @FindParameters | Microsoft.PowerShell.Core\Where-Object {$_.Name -eq $moduleInfo.Name} | - Microsoft.PowerShell.Utility\Select-Object -Last 1 -ErrorAction Ignore + Microsoft.PowerShell.Utility\Select-Object -Last 1 if($currentPSGetItemInfo) { @@ -1432,7 +1387,7 @@ function Save-Module { if($Path) { - $destinationPath = Resolve-PathHelper -Path $Path -CallerPSCmdlet $PSCmdlet | Microsoft.PowerShell.Utility\Select-Object -First 1 -ErrorAction Ignore + $destinationPath = Resolve-PathHelper -Path $Path -CallerPSCmdlet $PSCmdlet | Microsoft.PowerShell.Utility\Select-Object -First 1 if(-not $destinationPath -or -not (Microsoft.PowerShell.Management\Test-path $destinationPath)) { @@ -1449,7 +1404,7 @@ function Save-Module } else { - $destinationPath = Resolve-PathHelper -Path $LiteralPath -IsLiteralPath -CallerPSCmdlet $PSCmdlet | Microsoft.PowerShell.Utility\Select-Object -First 1 -ErrorAction Ignore + $destinationPath = Resolve-PathHelper -Path $LiteralPath -IsLiteralPath -CallerPSCmdlet $PSCmdlet | Microsoft.PowerShell.Utility\Select-Object -First 1 if(-not $destinationPath -or -not (Microsoft.PowerShell.Management\Test-Path -LiteralPath $destinationPath)) { @@ -1898,7 +1853,7 @@ function Update-Module if(-not $installedPackages -and -not (Test-WildcardPattern -Name $moduleName)) { - $availableModules = Get-Module -ListAvailable $moduleName -Verbose:$false | Microsoft.PowerShell.Utility\Select-Object -Unique -ErrorAction Ignore + $availableModules = Get-Module -ListAvailable $moduleName -Verbose:$false | Microsoft.PowerShell.Utility\Select-Object -Unique if(-not $availableModules) { @@ -2526,7 +2481,7 @@ function Publish-Script Begin { - if($script:isNanoServer -or (IsCoreCLR)) { + if($script:isNanoServer) { $message = $LocalizedData.PublishPSArtifactUnsupportedOnNano -f "Script" ThrowError -ExceptionName "System.InvalidOperationException" ` -ExceptionMessage $message ` @@ -2547,7 +2502,7 @@ function Publish-Script if($Path) { $scriptFilePath = Resolve-PathHelper -Path $Path -CallerPSCmdlet $PSCmdlet | - Microsoft.PowerShell.Utility\Select-Object -First 1 -ErrorAction Ignore + Microsoft.PowerShell.Utility\Select-Object -First 1 if(-not $scriptFilePath -or -not (Microsoft.PowerShell.Management\Test-Path -Path $scriptFilePath -PathType Leaf)) @@ -2564,7 +2519,7 @@ function Publish-Script else { $scriptFilePath = Resolve-PathHelper -Path $LiteralPath -IsLiteralPath -CallerPSCmdlet $PSCmdlet | - Microsoft.PowerShell.Utility\Select-Object -First 1 -ErrorAction Ignore + Microsoft.PowerShell.Utility\Select-Object -First 1 if(-not $scriptFilePath -or -not (Microsoft.PowerShell.Management\Test-Path -LiteralPath $scriptFilePath -PathType Leaf)) @@ -2718,7 +2673,7 @@ function Publish-Script # Use Find-Module to check if that name is already used as module name $modulePSGetItemInfo = Find-Module @FindParameters | Microsoft.PowerShell.Core\Where-Object {$_.Name -eq $scriptName} | - Microsoft.PowerShell.Utility\Select-Object -Last 1 -ErrorAction Ignore + Microsoft.PowerShell.Utility\Select-Object -Last 1 if($modulePSGetItemInfo) { $message = $LocalizedData.SpecifiedNameIsAlearyUsed -f ($scriptName, $Repository, 'Find-Module') @@ -2735,7 +2690,7 @@ function Publish-Script $currentPSGetItemInfo = $null $currentPSGetItemInfo = Find-Script @FindParameters | Microsoft.PowerShell.Core\Where-Object {$_.Name -eq $scriptName} | - Microsoft.PowerShell.Utility\Select-Object -Last 1 -ErrorAction Ignore + Microsoft.PowerShell.Utility\Select-Object -Last 1 if($currentPSGetItemInfo) { @@ -3094,7 +3049,7 @@ function Save-Script if($Path) { $destinationPath = Resolve-PathHelper -Path $Path -CallerPSCmdlet $PSCmdlet | - Microsoft.PowerShell.Utility\Select-Object -First 1 -ErrorAction Ignore + Microsoft.PowerShell.Utility\Select-Object -First 1 if(-not $destinationPath -or -not (Microsoft.PowerShell.Management\Test-path $destinationPath)) { @@ -3112,7 +3067,7 @@ function Save-Script else { $destinationPath = Resolve-PathHelper -Path $LiteralPath -IsLiteralPath -CallerPSCmdlet $PSCmdlet | - Microsoft.PowerShell.Utility\Select-Object -First 1 -ErrorAction Ignore + Microsoft.PowerShell.Utility\Select-Object -First 1 if(-not $destinationPath -or -not (Microsoft.PowerShell.Management\Test-Path -LiteralPath $destinationPath)) { @@ -4479,7 +4434,7 @@ function Test-ScriptFileInfo $scriptFilePath = $null if($Path) { - $scriptFilePath = Resolve-PathHelper -Path $Path -CallerPSCmdlet $PSCmdlet | Microsoft.PowerShell.Utility\Select-Object -First 1 -ErrorAction Ignore + $scriptFilePath = Resolve-PathHelper -Path $Path -CallerPSCmdlet $PSCmdlet | Microsoft.PowerShell.Utility\Select-Object -First 1 if(-not $scriptFilePath -or -not (Microsoft.PowerShell.Management\Test-Path -Path $scriptFilePath -PathType Leaf)) { @@ -4495,7 +4450,7 @@ function Test-ScriptFileInfo } else { - $scriptFilePath = Resolve-PathHelper -Path $LiteralPath -IsLiteralPath -CallerPSCmdlet $PSCmdlet | Microsoft.PowerShell.Utility\Select-Object -First 1 -ErrorAction Ignore + $scriptFilePath = Resolve-PathHelper -Path $LiteralPath -IsLiteralPath -CallerPSCmdlet $PSCmdlet | Microsoft.PowerShell.Utility\Select-Object -First 1 if(-not $scriptFilePath -or -not (Microsoft.PowerShell.Management\Test-Path -LiteralPath $scriptFilePath -PathType Leaf)) { @@ -4552,7 +4507,7 @@ function Test-ScriptFileInfo $psscriptInfoComments = $CommentTokens | Microsoft.PowerShell.Core\Where-Object { $_.Extent.Text -match "<#PSScriptInfo" } | - Microsoft.PowerShell.Utility\Select-Object -First 1 -ErrorAction Ignore + Microsoft.PowerShell.Utility\Select-Object -First 1 if(-not $psscriptInfoComments) { @@ -4741,20 +4696,20 @@ function Test-ScriptFileInfo if($allCommands) { - $allCommandNames = $allCommands | ForEach-Object {$_.Name} | Select-Object -Unique -ErrorAction Ignore + $allCommandNames = $allCommands | ForEach-Object {$_.Name} | Select-Object -Unique ValidateAndAdd-PSScriptInfoEntry -PSScriptInfo $PSScriptInfo ` -PropertyName $script:DefinedCommands ` -PropertyValue $allCommandNames ` -CallerPSCmdlet $PSCmdlet - $allFunctionNames = $allCommands | Where-Object {-not $_.IsWorkflow} | ForEach-Object {$_.Name} | Select-Object -Unique -ErrorAction Ignore + $allFunctionNames = $allCommands | Where-Object {-not $_.IsWorkflow} | ForEach-Object {$_.Name} | Select-Object -Unique ValidateAndAdd-PSScriptInfoEntry -PSScriptInfo $PSScriptInfo ` -PropertyName $script:DefinedFunctions ` -PropertyValue $allFunctionNames ` -CallerPSCmdlet $PSCmdlet - $allWorkflowNames = $allCommands | Where-Object {$_.IsWorkflow} | ForEach-Object {$_.Name} | Select-Object -Unique -ErrorAction Ignore + $allWorkflowNames = $allCommands | Where-Object {$_.IsWorkflow} | ForEach-Object {$_.Name} | Select-Object -Unique ValidateAndAdd-PSScriptInfoEntry -PSScriptInfo $PSScriptInfo ` -PropertyName $script:DefinedWorkflows ` -PropertyValue $allWorkflowNames ` @@ -4926,14 +4881,7 @@ function New-ScriptFileInfo if(-not $Author) { - if(IsWindows) - { - $Author = (Get-EnvironmentVariable -Name 'USERNAME' -Target $script:EnvironmentVariableTarget.Process -ErrorAction SilentlyContinue) - } - else - { - $Author = $env:USER - } + $Author = (Get-EnvironmentVariable -Name 'USERNAME' -Target $script:EnvironmentVariableTarget.Process -ErrorAction SilentlyContinue) } if(-not $Guid) @@ -4990,7 +4938,7 @@ function New-ScriptFileInfo $ScriptMetadataString += $ScriptCommentHelpInfoString $ScriptMetadataString += "Param()`r`n`r`n" - $tempScriptFilePath = Microsoft.PowerShell.Management\Join-Path -Path $script:TempPath -ChildPath "$(Get-Random).ps1" + $tempScriptFilePath = Microsoft.PowerShell.Management\Join-Path -Path $env:TEMP -ChildPath "$(Get-Random).ps1" try { @@ -5137,7 +5085,7 @@ function Update-ScriptFileInfo if($Path) { $scriptFilePath = Resolve-PathHelper -Path $Path -CallerPSCmdlet $PSCmdlet | - Microsoft.PowerShell.Utility\Select-Object -First 1 -ErrorAction Ignore + Microsoft.PowerShell.Utility\Select-Object -First 1 if(-not $scriptFilePath -or -not (Microsoft.PowerShell.Management\Test-Path -Path $scriptFilePath -PathType Leaf)) @@ -5154,7 +5102,7 @@ function Update-ScriptFileInfo else { $scriptFilePath = Resolve-PathHelper -Path $LiteralPath -IsLiteralPath -CallerPSCmdlet $PSCmdlet | - Microsoft.PowerShell.Utility\Select-Object -First 1 -ErrorAction Ignore + Microsoft.PowerShell.Utility\Select-Object -First 1 if(-not $scriptFilePath -or -not (Microsoft.PowerShell.Management\Test-Path -LiteralPath $scriptFilePath -PathType Leaf)) @@ -5214,14 +5162,7 @@ function Update-ScriptFileInfo if(-not $Author) { - if(IsWindows) - { - $Author = (Get-EnvironmentVariable -Name 'USERNAME' -Target $script:EnvironmentVariableTarget.Process -ErrorAction SilentlyContinue) - } - else - { - $Author = $env:USER - } + $Author = (Get-EnvironmentVariable -Name 'USERNAME' -Target $script:EnvironmentVariableTarget.Process -ErrorAction SilentlyContinue) } if(-not $Guid) @@ -5358,7 +5299,7 @@ function Update-ScriptFileInfo return } - $tempScriptFilePath = Microsoft.PowerShell.Management\Join-Path -Path $script:TempPath -ChildPath "$(Get-Random).ps1" + $tempScriptFilePath = Microsoft.PowerShell.Management\Join-Path -Path $env:TEMP -ChildPath "$(Get-Random).ps1" try { @@ -5414,7 +5355,7 @@ function Update-ScriptFileInfo $psscriptInfoComments = $CommentTokens | Microsoft.PowerShell.Core\Where-Object { $_.Extent.Text -match "<#PSScriptInfo" } | - Microsoft.PowerShell.Utility\Select-Object -First 1 -ErrorAction Ignore + Microsoft.PowerShell.Utility\Select-Object -First 1 if(-not $psscriptInfoComments) { @@ -6041,15 +5982,10 @@ function Check-PSGalleryApiAvailability { $connected = Microsoft.PowerShell.Management\Test-Connection -ComputerName $microsoftDomain -Count 1 -Quiet } - elseif(Get-Command NetTCPIP\Test-Connection -ErrorAction Ignore) + else { $connected = NetTCPIP\Test-NetConnection -ComputerName $microsoftDomain -InformationLevel Quiet } - else - { - $connected = [System.Net.NetworkInformation.NetworkInterface]::GetIsNetworkAvailable() - } - if ( -not $connected) { return @@ -6189,7 +6125,7 @@ function Ping-Endpoint $results = @{} $WebProxy = $null - if($Proxy -and (IsWindows)) + if($Proxy) { $ProxyNetworkCredential = $null if($ProxyCredential) @@ -6197,7 +6133,7 @@ function Ping-Endpoint $ProxyNetworkCredential = $ProxyCredential.GetNetworkCredential() } - $WebProxy = New-Object Microsoft.PowerShell.Commands.PowerShellGet.InternalWebProxy -ArgumentList $Proxy,$ProxyNetworkCredential + $WebProxy = New-Object Microsoft.PowerShell.Get.InternalWebProxy -ArgumentList $Proxy,$ProxyNetworkCredential } if(HttpClientApisAvailable) @@ -6419,11 +6355,6 @@ function ValidateAndSet-PATHVariableIfUserAccepts $Request ) - if(-not (IsWindows)) - { - return - } - Set-PSGetSettingsVariable # Check and add the scope path to PATH environment variable if USER accepts the prompt. @@ -7219,10 +7150,9 @@ function Install-NuGetClientBinaries $Force ) - if(-not (IsWindows) -or - ($script:NuGetProvider -and - (-not $BootstrapNuGetExe -or - ($script:NuGetExePath -and (Microsoft.PowerShell.Management\Test-Path -Path $script:NuGetExePath))))) + if($script:NuGetProvider -and + (-not $BootstrapNuGetExe -or + ($script:NuGetExePath -and (Microsoft.PowerShell.Management\Test-Path -Path $script:NuGetExePath)))) { return } @@ -7306,7 +7236,7 @@ function Install-NuGetClientBinaries $_.Path -and ((Microsoft.PowerShell.Management\Split-Path -Path $_.Path -Leaf) -eq $script:NuGetExeName) -and (-not $_.Path.StartsWith($env:windir, [System.StringComparison]::OrdinalIgnoreCase)) - } | Microsoft.PowerShell.Utility\Select-Object -First 1 -ErrorAction Ignore + } | Microsoft.PowerShell.Utility\Select-Object -First 1 if($nugetCmd -and $nugetCmd.Path) { @@ -7322,7 +7252,7 @@ function Install-NuGetClientBinaries } # On Nano server we don't need NuGet.exe - if(-not $bootstrapNuGetProvider -and ($script:isNanoServer -or (IsCoreCLR) -or -not $BootstrapNuGetExe)) + if(-not $bootstrapNuGetProvider -and ($script:isNanoServer -or -not $BootstrapNuGetExe)) { return } @@ -7379,7 +7309,7 @@ function Install-NuGetClientBinaries } } - if($BootstrapNuGetExe -and -not $script:isNanoServer -and -not (IsCoreCLR)) + if($BootstrapNuGetExe -and -not $script:isNanoServer) { Write-Verbose -Message $LocalizedData.DownloadingNugetExe @@ -7463,21 +7393,10 @@ function Test-RunningAsElevated [OutputType([bool])] Param() - if(IsWindows) - { - $wid=[System.Security.Principal.WindowsIdentity]::GetCurrent() - $prp=new-object System.Security.Principal.WindowsPrincipal($wid) - $adm=[System.Security.Principal.WindowsBuiltInRole]::Administrator - return $prp.IsInRole($adm) - } - elseif((IsLinux) -or (IsOSX)) - { - # Permission models on *nix can be very complex, to the point that you could never possibly guess without simply trying what you need to try; - # This is totally different from Windows where you can know what you can or cannot do with/without admin rights. - return $true - } - - return $false + $wid=[System.Security.Principal.WindowsIdentity]::GetCurrent() + $prp=new-object System.Security.Principal.WindowsPrincipal($wid) + $adm=[System.Security.Principal.WindowsBuiltInRole]::Administrator + return $prp.IsInRole($adm) } function Get-EscapedString @@ -7563,7 +7482,7 @@ function ValidateAndGet-ScriptDependencies $psgetItemInfo = Find-Module @FindModuleArguments | Microsoft.PowerShell.Core\Where-Object {$_.Name -eq $ModuleName} | - Microsoft.PowerShell.Utility\Select-Object -Last 1 -ErrorAction Ignore + Microsoft.PowerShell.Utility\Select-Object -Last 1 if(-not $psgetItemInfo) { @@ -7606,7 +7525,7 @@ function ValidateAndGet-ScriptDependencies $psgetItemInfo = Find-Script @FindScriptArguments | Microsoft.PowerShell.Core\Where-Object {$_.Name -eq $requiredScript} | - Microsoft.PowerShell.Utility\Select-Object -Last 1 -ErrorAction Ignore + Microsoft.PowerShell.Utility\Select-Object -Last 1 if(-not $psgetItemInfo) { @@ -7733,7 +7652,7 @@ function ValidateAndGet-RequiredModuleDetails $psgetItemInfo = Find-Module @FindModuleArguments | Microsoft.PowerShell.Core\Where-Object {$_.Name -eq $ModuleName} | - Microsoft.PowerShell.Utility\Select-Object -Last 1 -ErrorAction Ignore + Microsoft.PowerShell.Utility\Select-Object -Last 1 if(-not $psgetItemInfo) { @@ -7777,7 +7696,7 @@ function ValidateAndGet-RequiredModuleDetails $psgetItemInfo = Find-Module @FindModuleArguments | Microsoft.PowerShell.Core\Where-Object {$_.Name -eq $ModuleName} | - Microsoft.PowerShell.Utility\Select-Object -Last 1 -ErrorAction Ignore + Microsoft.PowerShell.Utility\Select-Object -Last 1 if(-not $psgetItemInfo) { @@ -9559,7 +9478,7 @@ function Find-Package if($options.ContainsKey($script:Tag)) { - $userSpecifiedTags = $options[$script:Tag] | Microsoft.PowerShell.Utility\Select-Object -Unique -ErrorAction Ignore + $userSpecifiedTags = $options[$script:Tag] | Microsoft.PowerShell.Utility\Select-Object -Unique } else { @@ -9570,7 +9489,7 @@ function Find-Package if($options.ContainsKey('DscResource')) { $specifiedDscResources = $options['DscResource'] | - Microsoft.PowerShell.Utility\Select-Object -Unique -ErrorAction Ignore | + Microsoft.PowerShell.Utility\Select-Object -Unique | Microsoft.PowerShell.Core\ForEach-Object {"$($script:DscResource)_$_"} } @@ -9578,7 +9497,7 @@ function Find-Package if($options.ContainsKey('RoleCapability')) { $specifiedRoleCapabilities = $options['RoleCapability'] | - Microsoft.PowerShell.Utility\Select-Object -Unique -ErrorAction Ignore | + Microsoft.PowerShell.Utility\Select-Object -Unique | Microsoft.PowerShell.Core\ForEach-Object {"$($script:RoleCapability)_$_"} } @@ -9586,7 +9505,7 @@ function Find-Package if($options.ContainsKey('Command')) { $specifiedCommands = $options['Command'] | - Microsoft.PowerShell.Utility\Select-Object -Unique -ErrorAction Ignore | + Microsoft.PowerShell.Utility\Select-Object -Unique | Microsoft.PowerShell.Core\ForEach-Object {"$($script:Command)_$_"} } @@ -9594,7 +9513,7 @@ function Find-Package if($options.ContainsKey('Includes')) { $includes = $options['Includes'] | - Microsoft.PowerShell.Utility\Select-Object -Unique -ErrorAction Ignore | + Microsoft.PowerShell.Utility\Select-Object -Unique | Microsoft.PowerShell.Core\ForEach-Object {"$($script:Includes)_$_"} # Add PSIncludes_DscResource to $specifiedIncludes iff -DscResource names are not specified @@ -10509,7 +10428,7 @@ function Install-PackageUtility } } - $InstalledItemsList | Select-Object -Unique -ErrorAction Ignore + $InstalledItemsList | Select-Object -Unique if($Debug) { @@ -10595,11 +10514,11 @@ function Install-PackageUtility $InstalledItemDetails = $null if($packageType -eq $script:PSArtifactTypeModule) { - $InstalledItemDetails = Get-InstalledModuleDetails -Name $pkg.Name | Select-Object -Last 1 -ErrorAction Ignore + $InstalledItemDetails = Get-InstalledModuleDetails -Name $pkg.Name | Select-Object -Last 1 } elseif($packageType -eq $script:PSArtifactTypeScript) { - $InstalledItemDetails = Get-InstalledScriptDetails -Name $pkg.Name | Select-Object -Last 1 -ErrorAction Ignore + $InstalledItemDetails = Get-InstalledScriptDetails -Name $pkg.Name | Select-Object -Last 1 } if($InstalledItemDetails -and @@ -11020,11 +10939,11 @@ function Uninstall-Package } $dependentModulesJob = Microsoft.PowerShell.Core\Start-Job -ScriptBlock $dependentModuleScript -ArgumentList $moduleName Microsoft.PowerShell.Core\Wait-Job -job $dependentModulesJob - $dependentModules = Microsoft.PowerShell.Core\Receive-Job -job $dependentModulesJob -ErrorAction Ignore + $dependentModules = Microsoft.PowerShell.Core\Receive-Job -job $dependentModulesJob if(-not $Force -and $dependentModules) { - $message = $LocalizedData.UnableToUninstallAsOtherModulesNeedThisModule -f ($moduleName, $version, $moduleBase, $(($dependentModules.Name | Select-Object -Unique -ErrorAction Ignore) -join ','), $moduleName) + $message = $LocalizedData.UnableToUninstallAsOtherModulesNeedThisModule -f ($moduleName, $version, $moduleBase, $(($dependentModules.Name | Select-Object -Unique) -join ','), $moduleName) ThrowError -ExceptionName "System.InvalidOperationException" ` -ExceptionMessage $message ` @@ -11170,7 +11089,7 @@ function Uninstall-Package ($scriptName, $version, $scriptBase, - $(($dependentScriptNames | Select-Object -Unique -ErrorAction Ignore) -join ','), + $(($dependentScriptNames | Select-Object -Unique) -join ','), $scriptName) ThrowError -ExceptionName 'System.InvalidOperationException' ` @@ -11715,20 +11634,11 @@ function Set-InstalledModulesVariable foreach ($location in $modulePaths) { # find all modules installed using PowerShellGet - $GetChildItemParams = @{ - Path = $location - Recurse = $true - Filter = $script:PSGetItemInfoFileName - ErrorAction = 'SilentlyContinue' - WarningAction = 'SilentlyContinue' - } - - if(IsWindows) - { - $GetChildItemParams['Attributes'] = 'Hidden' - } - - $moduleBases = Get-ChildItem @GetChildItemParams | Foreach-Object { $_.Directory } + $moduleBases = Get-ChildItem $location -Recurse ` + -Attributes Hidden -Filter $script:PSGetItemInfoFileName ` + -ErrorAction SilentlyContinue ` + -WarningAction SilentlyContinue ` + | Foreach-Object { $_.Directory } foreach ($moduleBase in $moduleBases) @@ -12042,7 +11952,7 @@ function Log-ArtifactNotFoundInPSGallery # Perform Telemetry only if searched artifacts are not available in specified Gallery if ($notFoundArtifacts) { - [Microsoft.PowerShell.Commands.PowerShellGet.Telemetry]::TraceMessageArtifactsNotFound($notFoundArtifacts, $operationName) + [Microsoft.PowerShell.Get.Telemetry]::TraceMessageArtifactsNotFound($notFoundArtifacts, $operationName) } } @@ -12102,7 +12012,7 @@ function Log-NonPSGalleryRegistration $scriptPublishLocationHash = Get-Hash -locationString $scriptPublishLocation # Log the telemetry event - [Microsoft.PowerShell.Commands.PowerShellGet.Telemetry]::TraceMessageNonPSGalleryRegistration($sourceLocationType, $sourceLocationHash, $installationPolicy, $packageManagementProvider, $publishLocationHash, $scriptSourceLocationHash, $scriptPublishLocationHash, $operationName) + [Microsoft.PowerShell.Get.Telemetry]::TraceMessageNonPSGalleryRegistration($sourceLocationType, $sourceLocationHash, $installationPolicy, $packageManagementProvider, $publishLocationHash, $scriptSourceLocationHash, $scriptPublishLocationHash, $operationName) } # Returns a SHA1 hash of the specified string @@ -12256,7 +12166,7 @@ function Test-ModuleInstalled # Check if module is already installed $availableModule = Microsoft.PowerShell.Core\Get-Module -ListAvailable -Name $Name -Verbose:$false | Microsoft.PowerShell.Core\Where-Object {-not (Test-ModuleSxSVersionSupport) -or -not $RequiredVersion -or ($RequiredVersion -eq $_.Version)} | - Microsoft.PowerShell.Utility\Select-Object -Unique -ErrorAction Ignore + Microsoft.PowerShell.Utility\Select-Object -Unique return $availableModule } @@ -12317,7 +12227,7 @@ function Test-ScriptInstalled $scriptInfo = $scriptInfos | Microsoft.PowerShell.Core\Where-Object { (-not $RequiredVersion) -or ($RequiredVersion -eq $_.Version) - } | Microsoft.PowerShell.Utility\Select-Object -First 1 -ErrorAction Ignore + } | Microsoft.PowerShell.Utility\Select-Object -First 1 return $scriptInfo } @@ -12545,7 +12455,7 @@ function Update-ModuleManifest $ProcessorArchitecture, [Parameter()] - [ValidateSet('WindowsPowerShell','PowerShellCore')] + [ValidateSet('Desktop','Core')] [string[]] $CompatiblePSEditions, @@ -13910,7 +13820,7 @@ function Validate-ModuleCommandAlreadyAvailable -WarningAction SilentlyContinue | Microsoft.PowerShell.Core\Where-Object { ($CommandNames -contains $_.Name) -and ($_.Source -ne $CurrentModuleInfo.Name) } | - Microsoft.PowerShell.Utility\Select-Object -First 1 -ErrorAction Ignore + Microsoft.PowerShell.Utility\Select-Object -First 1 -ErrorAction SilentlyContinue if($AvailableCommand) { $message = $LocalizedData.ModuleCommandAlreadyAvailable -f ($AvailableCommand.Name, $CurrentModuleInfo.Name) @@ -14085,11 +13995,11 @@ function Get-InstalledModuleAuthenticodeSignature $SourceModule = $AvailableModules | Microsoft.PowerShell.Core\Where-Object { $_.ModuleBase.StartsWith($InstallLocation, [System.StringComparison]::OrdinalIgnoreCase) - } | Microsoft.PowerShell.Utility\Select-Object -First 1 -ErrorAction Ignore + } | Microsoft.PowerShell.Utility\Select-Object -First 1 if(-not $SourceModule) { - $SourceModule = $AvailableModules | Microsoft.PowerShell.Utility\Select-Object -First 1 -ErrorAction Ignore + $SourceModule = $AvailableModules | Microsoft.PowerShell.Utility\Select-Object -First 1 } else { @@ -14147,8 +14057,6 @@ function Test-MicrosoftCertificate $AuthenticodeSignature ) - $result = $false - if($AuthenticodeSignature.SignerCertificate) { try @@ -14162,11 +14070,10 @@ function Test-MicrosoftCertificate } $SafeX509ChainHandle = [Microsoft.PowerShell.Commands.PowerShellGet.Win32Helpers]::CertDuplicateCertificateChain($X509Chain.ChainContext) - $result = [Microsoft.PowerShell.Commands.PowerShellGet.Win32Helpers]::IsMicrosoftCertificate($SafeX509ChainHandle) - $SafeX509ChainHandle.Close() + return [Microsoft.PowerShell.Commands.PowerShellGet.Win32Helpers]::IsMicrosoftCertificate($SafeX509ChainHandle) } - return $result + return $false } function Test-ValidManifestModule @@ -14215,7 +14122,7 @@ function Test-ValidManifestModule -CallerPSCmdlet $PSCmdlet ` -ErrorCategory InvalidOperation } - elseif(IsWindows) + else { $ValidationResult = Validate-ModuleAuthenticodeSignature -CurrentModuleInfo $PSModuleInfo ` -InstallLocation $InstallLocation ` diff --git a/src/Modules/Shared/PowerShellGet/PowerShellGet.psd1 b/src/Modules/Shared/PowerShellGet/PowerShellGet.psd1 index 38870d214..e1b86328d 100644 Binary files a/src/Modules/Shared/PowerShellGet/PowerShellGet.psd1 and b/src/Modules/Shared/PowerShellGet/PowerShellGet.psd1 differ diff --git a/src/Modules/Windows+Unix-Core/Microsoft.PowerShell.Utility/Microsoft.PowerShell.Utility.psd1 b/src/Modules/Windows+Unix-Core/Microsoft.PowerShell.Utility/Microsoft.PowerShell.Utility.psd1 index 34c87b2d5..2b1c2cf57 100644 --- a/src/Modules/Windows+Unix-Core/Microsoft.PowerShell.Utility/Microsoft.PowerShell.Utility.psd1 +++ b/src/Modules/Windows+Unix-Core/Microsoft.PowerShell.Utility/Microsoft.PowerShell.Utility.psd1 @@ -1,8 +1,8 @@ -@{ +@{ GUID="1DA87E53-152B-403E-98DC-74D7B4D63D59" Author="Microsoft Corporation" CompanyName="Microsoft Corporation" -Copyright="© Microsoft Corporation. All rights reserved." +Copyright=" Microsoft Corporation. All rights reserved." ModuleVersion="3.1.0.0" PowerShellVersion="3.0" CmdletsToExport= "Format-List", "Format-Custom", "Format-Table", "Format-Wide", diff --git a/src/Modules/Windows-Core+Full/CimCmdlets/CimCmdlets.psd1 b/src/Modules/Windows-Core+Full/CimCmdlets/CimCmdlets.psd1 index d46e3c7e8..2c2d0e0a5 100644 Binary files a/src/Modules/Windows-Core+Full/CimCmdlets/CimCmdlets.psd1 and b/src/Modules/Windows-Core+Full/CimCmdlets/CimCmdlets.psd1 differ diff --git a/src/Modules/Windows-Core+Full/Microsoft.PowerShell.LocalAccounts/Microsoft.PowerShell.LocalAccounts.psd1 b/src/Modules/Windows-Core+Full/Microsoft.PowerShell.LocalAccounts/Microsoft.PowerShell.LocalAccounts.psd1 index 7edc55e33..4145c314a 100644 Binary files a/src/Modules/Windows-Core+Full/Microsoft.PowerShell.LocalAccounts/Microsoft.PowerShell.LocalAccounts.psd1 and b/src/Modules/Windows-Core+Full/Microsoft.PowerShell.LocalAccounts/Microsoft.PowerShell.LocalAccounts.psd1 differ diff --git a/src/Modules/Windows-Core+Full/Microsoft.WSMan.Management/Microsoft.WSMan.Management.psd1 b/src/Modules/Windows-Core+Full/Microsoft.WSMan.Management/Microsoft.WSMan.Management.psd1 index 972d36886..3e05410ba 100644 --- a/src/Modules/Windows-Core+Full/Microsoft.WSMan.Management/Microsoft.WSMan.Management.psd1 +++ b/src/Modules/Windows-Core+Full/Microsoft.WSMan.Management/Microsoft.WSMan.Management.psd1 @@ -10,6 +10,6 @@ AliasesToExport = @() FunctionsToExport = @() CmdletsToExport="Disable-WSManCredSSP", "Enable-WSManCredSSP", "Get-WSManCredSSP", "Set-WSManQuickConfig", "Test-WSMan", "Invoke-WSManAction", "Connect-WSMan", "Disconnect-WSMan", "Get-WSManInstance", "Set-WSManInstance", "Remove-WSManInstance", "New-WSManInstance", "New-WSManSessionOption" NestedModules="Microsoft.WSMan.Management.dll" -FormatsToProcess="WSMan.format.ps1xml" +FormatsToProcess="..\..\WSMan.format.ps1xml" HelpInfoURI = 'http://go.microsoft.com/fwlink/?linkid=390788' } diff --git a/src/Modules/Windows-Core+Full/Microsoft.WSMan.Management/WSMan.format.ps1xml b/src/Modules/Windows-Core+Full/Microsoft.WSMan.Management/WSMan.format.ps1xml index eed79bc54..8e34497aa 100644 Binary files a/src/Modules/Windows-Core+Full/Microsoft.WSMan.Management/WSMan.format.ps1xml and b/src/Modules/Windows-Core+Full/Microsoft.WSMan.Management/WSMan.format.ps1xml differ diff --git a/src/Modules/Windows-Core+Full/PSDiagnostics/PSDiagnostics.psd1 b/src/Modules/Windows-Core+Full/PSDiagnostics/PSDiagnostics.psd1 index 4533f0991..3d73330c0 100644 Binary files a/src/Modules/Windows-Core+Full/PSDiagnostics/PSDiagnostics.psd1 and b/src/Modules/Windows-Core+Full/PSDiagnostics/PSDiagnostics.psd1 differ diff --git a/src/Modules/Windows-Core+Full/PSDiagnostics/PSDiagnostics.psm1 b/src/Modules/Windows-Core+Full/PSDiagnostics/PSDiagnostics.psm1 index 2e5e94a02..bc893f13d 100644 Binary files a/src/Modules/Windows-Core+Full/PSDiagnostics/PSDiagnostics.psm1 and b/src/Modules/Windows-Core+Full/PSDiagnostics/PSDiagnostics.psm1 differ diff --git a/src/Modules/Windows-Full/Microsoft.PowerShell.Diagnostics/Diagnostics.format.ps1xml b/src/Modules/Windows-Full/Microsoft.PowerShell.Diagnostics/Diagnostics.format.ps1xml index 8d1bb7ff6..6c6fc81f1 100644 Binary files a/src/Modules/Windows-Full/Microsoft.PowerShell.Diagnostics/Diagnostics.format.ps1xml and b/src/Modules/Windows-Full/Microsoft.PowerShell.Diagnostics/Diagnostics.format.ps1xml differ diff --git a/src/Modules/Windows-Full/Microsoft.PowerShell.Diagnostics/Event.format.ps1xml b/src/Modules/Windows-Full/Microsoft.PowerShell.Diagnostics/Event.format.ps1xml index d0a56b23c..1b8f45b06 100644 Binary files a/src/Modules/Windows-Full/Microsoft.PowerShell.Diagnostics/Event.format.ps1xml and b/src/Modules/Windows-Full/Microsoft.PowerShell.Diagnostics/Event.format.ps1xml differ diff --git a/src/Modules/Windows-Full/Microsoft.PowerShell.Diagnostics/GetEvent.types.ps1xml b/src/Modules/Windows-Full/Microsoft.PowerShell.Diagnostics/GetEvent.types.ps1xml index 1d23d921b..5a5731b8b 100644 Binary files a/src/Modules/Windows-Full/Microsoft.PowerShell.Diagnostics/GetEvent.types.ps1xml and b/src/Modules/Windows-Full/Microsoft.PowerShell.Diagnostics/GetEvent.types.ps1xml differ diff --git a/src/Modules/Windows-Full/Microsoft.PowerShell.Diagnostics/Microsoft.PowerShell.Diagnostics.psd1 b/src/Modules/Windows-Full/Microsoft.PowerShell.Diagnostics/Microsoft.PowerShell.Diagnostics.psd1 index d72eb9e28..3be74226f 100644 --- a/src/Modules/Windows-Full/Microsoft.PowerShell.Diagnostics/Microsoft.PowerShell.Diagnostics.psd1 +++ b/src/Modules/Windows-Full/Microsoft.PowerShell.Diagnostics/Microsoft.PowerShell.Diagnostics.psd1 @@ -10,7 +10,7 @@ AliasesToExport = @() FunctionsToExport = @() CmdletsToExport="Get-WinEvent", "Get-Counter", "Import-Counter", "Export-Counter", "New-WinEvent" NestedModules="Microsoft.PowerShell.Commands.Diagnostics.dll" -TypesToProcess="GetEvent.types.ps1xml" -FormatsToProcess="Event.format.ps1xml","Diagnostics.format.ps1xml" +TypesToProcess="..\..\GetEvent.types.ps1xml" +FormatsToProcess="..\..\Event.format.ps1xml","..\..\Diagnostics.format.ps1xml" HelpInfoURI = 'http://go.microsoft.com/fwlink/?linkid=390783' } diff --git a/src/Modules/Windows-Full/Microsoft.PowerShell.ODataUtils/Microsoft.PowerShell.ODataAdapter.ps1 b/src/Modules/Windows-Full/Microsoft.PowerShell.ODataUtils/Microsoft.PowerShell.ODataAdapter.ps1 index f54b50b93..c5db4047d 100644 Binary files a/src/Modules/Windows-Full/Microsoft.PowerShell.ODataUtils/Microsoft.PowerShell.ODataAdapter.ps1 and b/src/Modules/Windows-Full/Microsoft.PowerShell.ODataUtils/Microsoft.PowerShell.ODataAdapter.ps1 differ diff --git a/src/Modules/Windows-Full/Microsoft.PowerShell.ODataUtils/Microsoft.PowerShell.ODataUtils.psd1 b/src/Modules/Windows-Full/Microsoft.PowerShell.ODataUtils/Microsoft.PowerShell.ODataUtils.psd1 index 4b611f2dc..7f85bb3ae 100644 Binary files a/src/Modules/Windows-Full/Microsoft.PowerShell.ODataUtils/Microsoft.PowerShell.ODataUtils.psd1 and b/src/Modules/Windows-Full/Microsoft.PowerShell.ODataUtils/Microsoft.PowerShell.ODataUtils.psd1 differ diff --git a/src/Modules/Windows-Full/Microsoft.PowerShell.ODataUtils/Microsoft.PowerShell.ODataUtils.psm1 b/src/Modules/Windows-Full/Microsoft.PowerShell.ODataUtils/Microsoft.PowerShell.ODataUtils.psm1 index 139ec4b6d..685e4786a 100644 Binary files a/src/Modules/Windows-Full/Microsoft.PowerShell.ODataUtils/Microsoft.PowerShell.ODataUtils.psm1 and b/src/Modules/Windows-Full/Microsoft.PowerShell.ODataUtils/Microsoft.PowerShell.ODataUtils.psm1 differ diff --git a/src/Modules/Windows-Full/Microsoft.PowerShell.ODataUtils/Microsoft.PowerShell.ODataUtilsHelper.ps1 b/src/Modules/Windows-Full/Microsoft.PowerShell.ODataUtils/Microsoft.PowerShell.ODataUtilsHelper.ps1 index 622ca0354..8a14cedd2 100644 Binary files a/src/Modules/Windows-Full/Microsoft.PowerShell.ODataUtils/Microsoft.PowerShell.ODataUtilsHelper.ps1 and b/src/Modules/Windows-Full/Microsoft.PowerShell.ODataUtils/Microsoft.PowerShell.ODataUtilsHelper.ps1 differ diff --git a/src/Modules/Windows-Full/Microsoft.PowerShell.ODataUtils/en-US/Microsoft.PowerShell.ODataUtilsStrings.psd1 b/src/Modules/Windows-Full/Microsoft.PowerShell.ODataUtils/en-US/Microsoft.PowerShell.ODataUtilsStrings.psd1 index d472d0146..6010408f1 100644 Binary files a/src/Modules/Windows-Full/Microsoft.PowerShell.ODataUtils/en-US/Microsoft.PowerShell.ODataUtilsStrings.psd1 and b/src/Modules/Windows-Full/Microsoft.PowerShell.ODataUtils/en-US/Microsoft.PowerShell.ODataUtilsStrings.psd1 differ diff --git a/src/Modules/Windows-Full/PSScheduledJob/PSScheduledJob.Format.ps1xml b/src/Modules/Windows-Full/PSScheduledJob/PSScheduledJob.Format.ps1xml index be7f28d74..94605a6d3 100644 Binary files a/src/Modules/Windows-Full/PSScheduledJob/PSScheduledJob.Format.ps1xml and b/src/Modules/Windows-Full/PSScheduledJob/PSScheduledJob.Format.ps1xml differ diff --git a/src/Modules/Windows-Full/PSScheduledJob/PSScheduledJob.types.ps1xml b/src/Modules/Windows-Full/PSScheduledJob/PSScheduledJob.types.ps1xml index c58b8f35a..5476073bb 100644 Binary files a/src/Modules/Windows-Full/PSScheduledJob/PSScheduledJob.types.ps1xml and b/src/Modules/Windows-Full/PSScheduledJob/PSScheduledJob.types.ps1xml differ diff --git a/src/Modules/Windows-Full/PSWorkflow/PSWorkflow.psd1 b/src/Modules/Windows-Full/PSWorkflow/PSWorkflow.psd1 index 5affd0ed0..383962602 100644 Binary files a/src/Modules/Windows-Full/PSWorkflow/PSWorkflow.psd1 and b/src/Modules/Windows-Full/PSWorkflow/PSWorkflow.psd1 differ diff --git a/src/Modules/Windows-Full/PSWorkflow/PSWorkflow.psm1 b/src/Modules/Windows-Full/PSWorkflow/PSWorkflow.psm1 index 5a733d51e..c8116e41a 100644 Binary files a/src/Modules/Windows-Full/PSWorkflow/PSWorkflow.psm1 and b/src/Modules/Windows-Full/PSWorkflow/PSWorkflow.psm1 differ diff --git a/src/Modules/Windows-Full/PSWorkflow/PSWorkflow.types.ps1xml b/src/Modules/Windows-Full/PSWorkflow/PSWorkflow.types.ps1xml index 621b1fb4f..267a72eaa 100644 Binary files a/src/Modules/Windows-Full/PSWorkflow/PSWorkflow.types.ps1xml and b/src/Modules/Windows-Full/PSWorkflow/PSWorkflow.types.ps1xml differ diff --git a/src/Modules/Windows-Full/PSWorkflowUtility/PSWorkflowUtility.psd1 b/src/Modules/Windows-Full/PSWorkflowUtility/PSWorkflowUtility.psd1 index 144c57e43..9af4f347d 100644 Binary files a/src/Modules/Windows-Full/PSWorkflowUtility/PSWorkflowUtility.psd1 and b/src/Modules/Windows-Full/PSWorkflowUtility/PSWorkflowUtility.psd1 differ diff --git a/src/Modules/Windows-Full/PSWorkflowUtility/PSWorkflowUtility.psm1 b/src/Modules/Windows-Full/PSWorkflowUtility/PSWorkflowUtility.psm1 index 3eaa04411..4db5fcec4 100644 Binary files a/src/Modules/Windows-Full/PSWorkflowUtility/PSWorkflowUtility.psm1 and b/src/Modules/Windows-Full/PSWorkflowUtility/PSWorkflowUtility.psm1 differ diff --git a/src/Schemas/PSMaml/Maml_HTML.xsl b/src/Schemas/PSMaml/Maml_HTML.xsl index e3c0c990c..a0fa6cb34 100644 Binary files a/src/Schemas/PSMaml/Maml_HTML.xsl and b/src/Schemas/PSMaml/Maml_HTML.xsl differ diff --git a/src/System.Management.Automation/CoreCLR/CorePsExtensions.cs b/src/System.Management.Automation/CoreCLR/CorePsExtensions.cs index 94e35a3ac..3f081a55e 100644 --- a/src/System.Management.Automation/CoreCLR/CorePsExtensions.cs +++ b/src/System.Management.Automation/CoreCLR/CorePsExtensions.cs @@ -1,8 +1,9 @@ -#if CORECLR /********************************************************************++ Copyright (c) Microsoft Corporation. All rights reserved. --********************************************************************/ +#if CORECLR + using System.Globalization; using System.Linq; using System.Reflection; @@ -824,37 +825,7 @@ namespace System.Management.Automation public static string GetEnvironmentVariable(string variable) { - string value = System.Environment.GetEnvironmentVariable(variable); - - // Porting note: if not otherwise defined, map Windows environment - // variables to their corresponding Linux counterparts - if (!Platform.IsWindows && String.IsNullOrEmpty(value)) - { - switch (variable) - { - case "OS": - return "Linux"; - - case "COMPUTERNAME": - return System.Environment.GetEnvironmentVariable("HOSTNAME"); - - case "USERNAME": - return System.Environment.GetEnvironmentVariable("USER"); - - case "HOMEPATH": - case "USERPROFILE": - return System.Environment.GetEnvironmentVariable("HOME"); - - case "TMP": - case "TEMP": - return System.Environment.GetEnvironmentVariable("TMPDIR"); - - default: - break; - } - } - - return value; + return System.Environment.GetEnvironmentVariable(variable); } public static IDictionary GetEnvironmentVariables() @@ -892,11 +863,7 @@ namespace System.Management.Automation { return GetEnvironmentVariables(); } - -#if UNIX - return null; -#else - + if( target == EnvironmentVariableTarget.Machine) { using (RegistryKey environmentKey = @@ -913,7 +880,6 @@ namespace System.Management.Automation return GetRegistryKeyNameValuePairs(environmentKey); } } -#endif } /// @@ -954,10 +920,6 @@ namespace System.Management.Automation return System.Environment.GetEnvironmentVariable(variable); } -#if UNIX - return null; -#else - if (target == EnvironmentVariableTarget.Machine) { using (RegistryKey environmentKey = @@ -979,38 +941,12 @@ namespace System.Management.Automation return value; } } -#endif } #endregion EnvironmentVariable_Extensions #region Property_Extensions - internal static string WinGetUserDomainName() - { - StringBuilder domainName = new StringBuilder(1024); - uint domainNameLen = (uint)domainName.Capacity; - - byte ret = Win32Native.GetUserNameEx(Win32Native.NameSamCompatible, domainName, ref domainNameLen); - if (ret == 1) - { - string samName = domainName.ToString(); - int index = samName.IndexOf('\\'); - if (index != -1) - { - return samName.Substring(0, index); - } - } - else - { - int errorCode = Marshal.GetLastWin32Error(); - throw new InvalidOperationException(Win32Native.GetMessage(errorCode)); - } - - // Cannot use LookupAccountNameW to get DomainName because 'GetUserName' is not available in CSS and thus we cannot get the account. - throw new InvalidOperationException(CoreClrStubResources.CannotGetDomainName); - } - /// /// UserDomainName /// @@ -1018,33 +954,28 @@ namespace System.Management.Automation { get { - if (Platform.IsWindows) + StringBuilder domainName = new StringBuilder(1024); + uint domainNameLen = (uint)domainName.Capacity; + + byte ret = Win32Native.GetUserNameEx(Win32Native.NameSamCompatible, domainName, ref domainNameLen); + if (ret == 1) { - return WinGetUserDomainName(); + string samName = domainName.ToString(); + int index = samName.IndexOf('\\'); + if (index != -1) + { + return samName.Substring(0, index); + } } else { - return Platform.NonWindowsGetDomainName(); + int errorCode = Marshal.GetLastWin32Error(); + throw new InvalidOperationException(Win32Native.GetMessage(errorCode)); } - } - } - - internal static string WinGetUserName() - { - StringBuilder domainName = new StringBuilder(1024); - uint domainNameLen = (uint)domainName.Capacity; - byte ret = Win32Native.GetUserNameEx(Win32Native.NameSamCompatible, domainName, ref domainNameLen); - if (ret == 1) - { - string samName = domainName.ToString(); - int index = samName.IndexOf('\\'); - if (index != -1) - { - return samName.Substring(index + 1); - } + // Cannot use LookupAccountNameW to get DomainName because 'GetUserName' is not available in CSS and thus we cannot get the account. + throw new InvalidOperationException(CoreClrStubResources.CannotGetDomainName); } - return string.Empty; } /// @@ -1054,14 +985,20 @@ namespace System.Management.Automation { get { - if (Platform.IsWindows) + StringBuilder domainName = new StringBuilder(1024); + uint domainNameLen = (uint)domainName.Capacity; + + byte ret = Win32Native.GetUserNameEx(Win32Native.NameSamCompatible, domainName, ref domainNameLen); + if (ret == 1) { - return WinGetUserName(); - } - else - { - return Platform.NonWindowsGetUserName(); + string samName = domainName.ToString(); + int index = samName.IndexOf('\\'); + if (index != -1) + { + return samName.Substring(index + 1); + } } + return string.Empty; } } @@ -1072,7 +1009,13 @@ namespace System.Management.Automation { get { - return System.Environment.MachineName; + // In future release of operating systems, you might be able to rename a machine without + // rebooting. Therefore, don't cache this machine name. + StringBuilder buf = new StringBuilder(MaxMachineNameLength); + int len = MaxMachineNameLength; + if (Win32Native.GetComputerName(buf, ref len) == 0) + throw new InvalidOperationException(CoreClrStubResources.CannotGetComputerName); + return buf.ToString(); } } @@ -1085,45 +1028,22 @@ namespace System.Management.Automation { if (m_os == null) { - if (Platform.IsWindows) + Win32Native.OSVERSIONINFOEX osviex = new Win32Native.OSVERSIONINFOEX(); + osviex.OSVersionInfoSize = Marshal.SizeOf(osviex); + if (!Win32Native.GetVersionEx(ref osviex)) { - m_os = WinOSVersion; + int errorCode = Marshal.GetLastWin32Error(); + throw new Win32Exception(errorCode); } - else - { - // TODO:PSL use P/Invoke to provide proper version - // Porting note: cannot put this in CorePsPlatform since - // System.Management.Automation.Environment only exists in CoreCLR - // builds of monad. - m_os = new Environment.OperatingSystem(new Version(1,0,0,0),""); - } + Version v = new Version(osviex.MajorVersion, osviex.MinorVersion, osviex.BuildNumber, (osviex.ServicePackMajor << 16) | osviex.ServicePackMinor); + m_os = new OperatingSystem(v, osviex.CSDVersion); } return m_os; } } private static volatile OperatingSystem m_os; - /// - /// Windows OSVersion implementation - /// - private static OperatingSystem WinOSVersion - { - get - { - Win32Native.OSVERSIONINFOEX osviex = new Win32Native.OSVERSIONINFOEX(); - osviex.OSVersionInfoSize = Marshal.SizeOf(osviex); - if (!Win32Native.GetVersionEx(ref osviex)) - { - int errorCode = Marshal.GetLastWin32Error(); - throw new Win32Exception(errorCode); - } - - Version v = new Version(osviex.MajorVersion, osviex.MinorVersion, osviex.BuildNumber, (osviex.ServicePackMajor << 16) | osviex.ServicePackMinor); - return new OperatingSystem(v, osviex.CSDVersion); - } - } - #endregion Property_Extensions #region SpecialFolder_Extensions @@ -1146,11 +1066,6 @@ namespace System.Management.Automation /// private static string InternalGetFolderPath(SpecialFolder folder) { - if (!Platform.IsWindows) - { - return Platform.NonWindowsGetFolderPath(folder); - } - // The API 'SHGetFolderPath' is not available on OneCore, so we have to rely on environment variables string folderPath = null; string systemRoot = null; @@ -1231,7 +1146,7 @@ namespace System.Management.Automation /// DllImport uses the ApiSet dll that is available on CSS, since this code /// will only be included when building targeting CoreCLR. /// - internal static class Win32Native + private static class Win32Native { internal const int NameSamCompatible = 2; // EXTENDED_NAME_FORMAT - NameSamCompatible @@ -1243,6 +1158,9 @@ namespace System.Management.Automation // Win32 return type is BOOLEAN (which is 1 byte and not BOOL which is 4bytes) internal static extern byte GetUserNameEx(int format, [Out] StringBuilder domainName, ref uint domainNameLen); + [DllImport("api-ms-win-downlevel-kernel32-l2-1-0.dll", CharSet = CharSet.Unicode, SetLastError = true)] + internal extern static int GetComputerName([Out]StringBuilder nameBuffer, ref int bufferSize); + [DllImport("api-ms-win-core-localization-l1-2-1.dll", CharSet = CharSet.Unicode)] internal static extern int FormatMessage(int dwFlags, IntPtr lpSource, int dwMessageId, int dwLanguageId, [Out]StringBuilder lpBuffer, @@ -1295,17 +1213,13 @@ namespace System.Management.Automation #region NestedTypes - // Porting note: MyDocuments does not exist on .NET Core, but Personal does, and - // they both point to your "documents repository," which on linux, is just the - // home directory. - /// /// It only contains the values that get used in powershell /// internal enum SpecialFolder { - Personal = 0x05, - MyDocuments = 0x05, + MyDocuments = 5, + Personal = 5, LocalApplicationData = 0x1c, ProgramFiles = 0x26, ProgramFilesX86 = 0x2a, @@ -1631,7 +1545,7 @@ namespace Microsoft.PowerShell.CoreCLR public static Assembly LoadFrom(string assemblyPath) { return ClrFacade.LoadFrom(assemblyPath); - } + } /// /// Load an assembly given its byte stream diff --git a/src/System.Management.Automation/CoreCLR/CorePsStub.cs b/src/System.Management.Automation/CoreCLR/CorePsStub.cs index 7dda497c8..2f16820aa 100644 --- a/src/System.Management.Automation/CoreCLR/CorePsStub.cs +++ b/src/System.Management.Automation/CoreCLR/CorePsStub.cs @@ -1,4 +1,3 @@ -#if CORECLR /********************************************************************++ Copyright (c) Microsoft Corporation. All rights reserved. --********************************************************************/ @@ -12,6 +11,8 @@ using System.Diagnostics.CodeAnalysis; using Microsoft.Win32; using System.Management.Automation.Remoting; +#if CORECLR + #pragma warning disable 1591, 1572, 1571, 1573, 1587, 1570, 0067 #region CLR_STUBS @@ -1408,351 +1409,6 @@ namespace System.Management.Automation.Security } } - -#if UNIX - -// Porting note: Tracing is absolutely not available on Linux -namespace System.Management.Automation.Tracing -{ - using System.Management.Automation.Internal; - - /// - /// - /// - [SuppressMessage("Microsoft.Naming", "CA1704:IdentifiersShouldBeSpelledCorrectly")] - public abstract class EtwActivity - { - /// - /// - /// - /// - /// - public static bool SetActivityId(Guid activityId) - { - return false; - } - - /// - /// - /// - /// - public static Guid CreateActivityId() - { - return Guid.Empty; - } - - /// - /// - /// - /// - public static Guid GetActivityId() - { - return Guid.Empty; - } - } - - internal static class PSEtwLog - { - static internal void LogAnalyticError(PSEventId id, PSOpcode opcode, PSTask task, PSKeyword keyword, params object[] args) { } - static internal void LogAnalyticWarning(PSEventId id, PSOpcode opcode, PSTask task, PSKeyword keyword, params object[] args) { } - static internal void LogAnalyticVerbose(PSEventId id, PSOpcode opcode, PSTask task, PSKeyword keyword, - Int64 objectId, - Int64 fragmentId, - int isStartFragment, - int isEndFragment, - UInt32 fragmentLength, - PSETWBinaryBlob fragmentData) - { } - static internal void LogAnalyticVerbose(PSEventId id, PSOpcode opcode, PSTask task, PSKeyword keyword, params object[] args) { } - static internal void SetActivityIdForCurrentThread(Guid newActivityId) { } - static internal void LogOperationalVerbose(PSEventId id, PSOpcode opcode, PSTask task, PSKeyword keyword, params object[] args){ } - static internal void LogOperationalWarning(PSEventId id, PSOpcode opcode, PSTask task, PSKeyword keyword, params object[] args){ } - static internal void ReplaceActivityIdForCurrentThread(Guid newActivityId, PSEventId eventForOperationalChannel, PSEventId eventForAnalyticChannel, PSKeyword keyword, PSTask task) { } - static internal void LogOperationalError(PSEventId id, PSOpcode opcode, PSTask task, PSKeyword keyword, params object[] args) { } - static internal void LogOperationalError(PSEventId id, PSOpcode opcode, PSTask task, LogContext logContext, string payLoad) { } - static internal void LogAnalyticInformational(PSEventId id, PSOpcode opcode, PSTask task, PSKeyword keyword, params object[] args){ } - static internal void LogOperationalInformation(PSEventId id, PSOpcode opcode, PSTask task, PSKeyword keyword, params object[] args){ } - } - - public enum PowerShellTraceTask - { - /// - /// None - /// - None = 0, - - /// - /// CreateRunspace - /// - CreateRunspace = 1, - - /// - /// ExecuteCommand - /// - ExecuteCommand = 2, - - /// - /// Serialization - /// - Serialization = 3, - - /// - /// PowerShellConsoleStartup - /// - PowerShellConsoleStartup = 4, - } - - /// - /// Defines Keywords. - /// - [System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Design", "CA1028")] - [Flags] - public enum PowerShellTraceKeywords : ulong - { - /// - /// None - /// - None = 0, - - /// - /// Runspace - /// - Runspace = 0x1, - - /// - /// Pipeline - /// - Pipeline = 0x2, - - /// - /// Protocol - /// - Protocol = 0x4, - - /// - /// Transport - /// - Transport = 0x8, - - /// - /// Host - /// - Host = 0x10, - - /// - /// Cmdlets - /// - Cmdlets = 0x20, - - /// - /// Serializer - /// - Serializer = 0x40, - - /// - /// Session - /// - Session = 0x80, - - /// - /// ManagedPlugIn - /// - ManagedPlugIn = 0x100, - - /// - /// - /// - UseAlwaysDebug = 0x2000000000000000, - - /// - /// - /// - UseAlwaysOperational = 0x8000000000000000, - - /// - /// - /// - UseAlwaysAnalytic = 0x4000000000000000, - } - - public sealed partial class Tracer : System.Management.Automation.Tracing.EtwActivity - { - static Tracer() {} - - public void EndpointRegistered(string endpointName, string endpointType, string registeredBy) - { - } - - public void EndpointUnregistered(string endpointName, string unregisteredBy) - { - } - - public void EndpointDisabled(string endpointName, string disabledBy) - { - } - - public void EndpointEnabled(string endpointName, string enabledBy) - { - } - - public void EndpointModified(string endpointName, string modifiedBy) - { - } - - public void BeginContainerParentJobExecution(Guid containerParentJobInstanceId) - { - } - - public void BeginProxyJobExecution(Guid proxyJobInstanceId) - { - } - - public void ProxyJobRemoteJobAssociation(Guid proxyJobInstanceId, Guid containerParentJobInstanceId) - { - } - - public void EndProxyJobExecution(Guid proxyJobInstanceId) - { - } - - public void BeginProxyJobEventHandler(Guid proxyJobInstanceId) - { - } - - public void EndProxyJobEventHandler(Guid proxyJobInstanceId) - { - } - - public void BeginProxyChildJobEventHandler(Guid proxyChildJobInstanceId) - { - } - - public void EndContainerParentJobExecution(Guid containerParentJobInstanceId) - { - } - } - - public sealed class PowerShellTraceSource : IDisposable - { - internal PowerShellTraceSource(PowerShellTraceTask task, PowerShellTraceKeywords keywords) - { - } - - public void Dispose() - { - } - - public bool WriteMessage(String message) - { - return false; - } - - /// - /// - /// - /// - /// - /// - public bool WriteMessage(string message1, string message2) - { - return false; - } - - /// - /// - /// - /// - /// - /// - public bool WriteMessage(string message, Guid instanceId) - { - return false; - } - - - /// - /// - /// - /// - /// - /// - /// - /// - /// - public void WriteMessage(string className, string methodName, Guid workflowId, string message, params string[] parameters) - { - return ; - } - - /// - /// - /// - /// - /// - /// - /// - /// - /// - /// - public void WriteMessage(string className, string methodName, Guid workflowId, Job job, string message, params string[] parameters) - { - return; - } - - public bool TraceException(Exception exception) - { - return false; - } - } - - /// - /// TraceSourceFactory will return an instance of TraceSource every time GetTraceSource method is called. - /// - public static class PowerShellTraceSourceFactory - { - /// - /// Returns an instance of BaseChannelWriter. - /// If the Etw is not supported by the platform it will return NullWriter.Instance - /// - /// A Task and a set of Keywords can be specified in the GetTraceSource method (See overloads). - /// The supplied task and keywords are used to pass to the Etw provider in case they are - /// not defined in the manifest file. - /// - public static PowerShellTraceSource GetTraceSource() - { - return new PowerShellTraceSource(PowerShellTraceTask.None, PowerShellTraceKeywords.None); - } - - /// - /// Returns an instance of BaseChannelWriter. - /// If the Etw is not supported by the platform it will return NullWriter.Instance - /// - /// A Task and a set of Keywords can be specified in the GetTraceSource method (See overloads). - /// The supplied task and keywords are used to pass to the Etw provider in case they are - /// not defined in the manifest file. - /// - public static PowerShellTraceSource GetTraceSource(PowerShellTraceTask task) - { - return new PowerShellTraceSource(task, PowerShellTraceKeywords.None); - } - - /// - /// Returns an instance of BaseChannelWriter. - /// If the Etw is not supported by the platform it will return NullWriter.Instance - /// - /// A Task and a set of Keywords can be specified in the GetTraceSource method (See overloads). - /// The supplied task and keywords are used to pass to the Etw provider in case they are - /// not defined in the manifest file. - /// - public static PowerShellTraceSource GetTraceSource(PowerShellTraceTask task, PowerShellTraceKeywords keywords) - { - return new PowerShellTraceSource(task, keywords); - } - } -} - -#endif - namespace Microsoft.PowerShell { internal static class NativeCultureResolver diff --git a/src/System.Management.Automation/cimSupport/cmdletization/xml/CoreCLR/cmdlets-over-objects.objectModel.autogen.cs b/src/System.Management.Automation/cimSupport/cmdletization/xml/CoreCLR/cmdlets-over-objects.objectModel.autogen.cs index 1a24c5bac..a32b560d8 100644 --- a/src/System.Management.Automation/cimSupport/cmdletization/xml/CoreCLR/cmdlets-over-objects.objectModel.autogen.cs +++ b/src/System.Management.Automation/cimSupport/cmdletization/xml/CoreCLR/cmdlets-over-objects.objectModel.autogen.cs @@ -1,5 +1,4 @@ -#if CORECLR -// THIS FILE IS MANUALLY CHANGED BASED ON THE GENERATED FILE +// THIS FILE IS MANUALLY CHANGED BASED ON THE GENERATED FILE // // The original file has been generated by admin\monad\src\cimSupport\cmdletization\xml\generate.ps1 // based on the following input file: d:\bluedev\admin\monad\src\cimSupport\cmdletization\xml\cmdlets-over-objects.xsd @@ -1726,5 +1725,3 @@ namespace Microsoft.PowerShell.Cmdletization.Xml { } #endif - -#endif diff --git a/src/System.Management.Automation/cimSupport/cmdletization/xml/CoreCLR/cmdlets-over-objects.xmlSerializer.autogen.cs b/src/System.Management.Automation/cimSupport/cmdletization/xml/CoreCLR/cmdlets-over-objects.xmlSerializer.autogen.cs index fdbae2d56..8e351221b 100644 --- a/src/System.Management.Automation/cimSupport/cmdletization/xml/CoreCLR/cmdlets-over-objects.xmlSerializer.autogen.cs +++ b/src/System.Management.Automation/cimSupport/cmdletization/xml/CoreCLR/cmdlets-over-objects.xmlSerializer.autogen.cs @@ -1,5 +1,4 @@ -#if CORECLR -// THIS FILE IS MANUALLY CHANGED BASED ON THE GENERATED FILE +// THIS FILE IS MANUALLY CHANGED BASED ON THE GENERATED FILE // // The original file has been generated by admin\monad\src\cimSupport\cmdletization\xml\generate.ps1 // based on the following input file: d:\bluedev\admin\monad\src\cimSupport\cmdletization\xml\cmdlets-over-objects.xsd @@ -5290,5 +5289,3 @@ namespace Microsoft.PowerShell.Cmdletization.Xml { } #endif - -#endif diff --git a/src/System.Management.Automation/commands/utility/FormatAndOutput/common/DisplayDatabase/FormatTable.cs b/src/System.Management.Automation/commands/utility/FormatAndOutput/common/DisplayDatabase/FormatTable.cs index 9109d5237..46f2c8ee4 100644 --- a/src/System.Management.Automation/commands/utility/FormatAndOutput/common/DisplayDatabase/FormatTable.cs +++ b/src/System.Management.Automation/commands/utility/FormatAndOutput/common/DisplayDatabase/FormatTable.cs @@ -316,9 +316,23 @@ namespace System.Management.Automation.Runspaces string shellId = Utils.DefaultPowerShellShellID; string psHome = Utils.GetApplicationBase(shellId); List defaultFormatFiles = new List(); + List fileList = new List() + { + "Certificate.Format.ps1xml", + "Event.Format.ps1xml", + "Diagnostics.Format.ps1xml", + "DotNetTypes.Format.ps1xml", + "FileSystem.Format.ps1xml", + "Help.Format.ps1xml", + "HelpV3.Format.ps1xml", + "PowerShellCore.format.ps1xml", + "PowerShellTrace.format.ps1xml", + "Registry.format.ps1xml", + "WSMan.Format.ps1xml" + }; if (!string.IsNullOrEmpty(psHome)) { - defaultFormatFiles.AddRange(Platform.FormatFileNames.Select(file => Path.Combine(psHome, file))); + defaultFormatFiles.AddRange(fileList.Select(file => Path.Combine(psHome, file))); } return new FormatTable(defaultFormatFiles); diff --git a/src/System.Management.Automation/commands/utility/FormatAndOutput/common/DisplayDatabase/displayResourceManagerCache.cs b/src/System.Management.Automation/commands/utility/FormatAndOutput/common/DisplayDatabase/displayResourceManagerCache.cs index 3c7295a6f..f2c4b0100 100644 --- a/src/System.Management.Automation/commands/utility/FormatAndOutput/common/DisplayDatabase/displayResourceManagerCache.cs +++ b/src/System.Management.Automation/commands/utility/FormatAndOutput/common/DisplayDatabase/displayResourceManagerCache.cs @@ -165,10 +165,6 @@ namespace Microsoft.PowerShell.Commands.Internal.Format retVal = ResolveAssemblyNameInLoadedAssemblies(assemblyName, false); } // NOTE: we cache the result (both for success and failure) - - // Porting note: this won't be hit in normal usage, but can be hit with bad build setup - Diagnostics.Assert(retVal != null, "AssemblyName resolution failed, a resource file might be broken"); - _assemblyReferences.Add(assemblyName, retVal); return retVal; } diff --git a/src/System.Management.Automation/engine/CommandCompletion/CompletionCompleters.cs b/src/System.Management.Automation/engine/CommandCompletion/CompletionCompleters.cs index 51cb463a5..78131c5fd 100644 --- a/src/System.Management.Automation/engine/CommandCompletion/CompletionCompleters.cs +++ b/src/System.Management.Automation/engine/CommandCompletion/CompletionCompleters.cs @@ -4324,9 +4324,8 @@ namespace System.Management.Automation { var sessionStateInternal = executionContext.EngineSessionState; completionText = sessionStateInternal.NormalizeRelativePath(path, sessionStateInternal.CurrentLocation.ProviderPath); - string parentDirectory = ".." + Path.DirectorySeparatorChar; - if (!completionText.StartsWith(parentDirectory, StringComparison.Ordinal)) - completionText = Path.Combine(".", completionText); + if (!completionText.StartsWith("..\\", StringComparison.Ordinal)) + completionText = ".\\" + completionText; } catch (Exception e) { @@ -4464,9 +4463,6 @@ namespace System.Management.Automation internal static List GetFileShares(string machine, bool ignoreHidden) { -#if UNIX - return new List(); -#else IntPtr shBuf; uint numEntries; uint totalEntries; @@ -4492,7 +4488,6 @@ namespace System.Management.Automation } } return shares; -#endif } private static bool CheckFileExtension(string path, HashSet extension) @@ -5905,32 +5900,21 @@ namespace System.Management.Automation /// The namespace private static void HandleNamespace(Dictionary entryCache, string @namespace) { - if (string.IsNullOrEmpty(@namespace)) + if (!string.IsNullOrEmpty(@namespace)) { - return; - } - - int dotIndex = 0; - while (dotIndex != -1) - { - dotIndex = @namespace.IndexOf('.', dotIndex + 1); - string subNamespace = dotIndex != -1 - ? @namespace.Substring(0, dotIndex) - : @namespace; - TypeCompletionMapping entry; - if (!entryCache.TryGetValue(subNamespace, out entry)) + if (!entryCache.TryGetValue(@namespace, out entry)) { entry = new TypeCompletionMapping { - Key = subNamespace, - Completions = { new NamespaceCompletion { Namespace = subNamespace } } + Key = @namespace, + Completions = { new NamespaceCompletion { Namespace = @namespace } } }; - entryCache.Add(subNamespace, entry); + entryCache.Add(@namespace, entry); } else if (!entry.Completions.OfType().Any()) { - entry.Completions.Add(new NamespaceCompletion { Namespace = subNamespace }); + entry.Completions.Add(new NamespaceCompletion { Namespace = @namespace }); } } } diff --git a/src/System.Management.Automation/engine/CommandDiscovery.cs b/src/System.Management.Automation/engine/CommandDiscovery.cs index c69a72358..0370bfd58 100644 --- a/src/System.Management.Automation/engine/CommandDiscovery.cs +++ b/src/System.Management.Automation/engine/CommandDiscovery.cs @@ -1321,8 +1321,6 @@ namespace System.Management.Automation } } - // TODO: this causes AppVeyor builds to fail due to invalid XML being output -#if !CORECLR // Close the progress pane that may have popped up from analyzing UNC paths. if (context.CurrentCommandProcessor != null) { @@ -1330,7 +1328,6 @@ namespace System.Management.Automation analysisProgress.RecordType = ProgressRecordType.Completed; context.CurrentCommandProcessor.CommandRuntime.WriteProgress(analysisProgress); } -#endif } } } @@ -1518,7 +1515,8 @@ namespace System.Management.Automation /// /// /// - /// The contents of the PATH environment variable split on System.IO.Path.PathSeparator. + /// The contents of the PATH environment variable split using a semi-colon + /// as a delimiter. /// /// /// @@ -1551,7 +1549,7 @@ namespace System.Management.Automation if (pathCacheKey != null) { - string[] tokenizedPath = pathCacheKey.Split(new char[] { System.IO.Path.PathSeparator }, StringSplitOptions.RemoveEmptyEntries); + string[] tokenizedPath = pathCacheKey.Split(Utils.Separators.Semicolon, StringSplitOptions.RemoveEmptyEntries); cachedPath = new Collection(); foreach (string directory in tokenizedPath) @@ -1642,7 +1640,7 @@ namespace System.Management.Automation lock (lockObject) { cachedPathExtCollection = pathExt != null - ? pathExt.Split(new char[] { System.IO.Path.PathSeparator }, StringSplitOptions.RemoveEmptyEntries) + ? pathExt.Split(Utils.Separators.Semicolon, StringSplitOptions.RemoveEmptyEntries) : Utils.EmptyArray(); cachedPathExtCollectionWithPs1 = new string[cachedPathExtCollection.Length + 1]; cachedPathExtCollectionWithPs1[0] = StringLiterals.PowerShellScriptFileExtension; @@ -1907,7 +1905,6 @@ namespace System.Management.Automation { string result = null; -#if !UNIX try { RegistryKey shellKey = Registry.LocalMachine.OpenSubKey(Utils.GetRegistryConfigurationPath(shellID)); @@ -1933,7 +1930,6 @@ namespace System.Management.Automation catch (ArgumentException) { } -#endif return result; } diff --git a/src/System.Management.Automation/engine/CommandPathSearch.cs b/src/System.Management.Automation/engine/CommandPathSearch.cs index d05ecc283..7e6302cd2 100644 --- a/src/System.Management.Automation/engine/CommandPathSearch.cs +++ b/src/System.Management.Automation/engine/CommandPathSearch.cs @@ -50,33 +50,21 @@ namespace System.Management.Automation ExecutionContext context, Collection acceptableCommandNames) { - string[] commandPatterns; if (acceptableCommandNames != null) { // The name passed in is not a pattern. To minimize enumerating the file system, we // turn the command name into a pattern and then match against extensions in PATHEXT. // The old code would enumerate the file system many more times, once per possible extension. - if (Platform.IsWindows) - { - commandPatterns = new [] { commandName + ".*" }; - } - else - { - // Porting note: on non-Windows platforms, we want to always allow just 'commandName' - // as an acceptable command name. However, we also want to allow commands to be - // called with the .ps1 extension, so that 'script.ps1' can be called by 'script'. - commandPatterns = new [] { commandName + ".ps1", commandName }; - } + commandName = commandName + ".*"; this.postProcessEnumeratedFiles = CheckAgainstAcceptableCommandNames; this.acceptableCommandNames = acceptableCommandNames; } else { - commandPatterns = new [] { commandName }; postProcessEnumeratedFiles = JustCheckExtensions; } - - Init(commandPatterns, lookupPaths, context); + + Init(new [] { commandName }, lookupPaths, context); this.orderedPathExt = CommandDiscovery.PathExtensionsWithPs1Prepended; } @@ -473,10 +461,8 @@ namespace System.Management.Automation { var baseNames = fileNames.Select(Path.GetFileName).ToArray(); - // Result must be ordered by PATHEXT order of precedence. - // acceptableCommandNames is in this order, so - - // Porting note: allow files with executable bit on non-Windows platforms + // Result must be ordered by PATHEXT order of precdence. + // accpetableCommandNames is in this order, so Collection result = null; if (baseNames.Length > 0) @@ -485,8 +471,7 @@ namespace System.Management.Automation { for (int i = 0; i < baseNames.Length; i++) { - if (name.Equals(baseNames[i], StringComparison.OrdinalIgnoreCase) - || (!Platform.IsWindows && Platform.NonWindowsIsExecutable(name))) + if (name.Equals(baseNames[i], StringComparison.OrdinalIgnoreCase)) { if (result == null) result = new Collection(); @@ -502,18 +487,14 @@ namespace System.Management.Automation private IEnumerable JustCheckExtensions(string[] fileNames) { - // Warning: pretty duplicated code - // Result must be ordered by PATHEXT order of precedence. - - // Porting note: allow files with executable bit on non-Windows platforms + // Result must be ordered by PATHEXT order of precdence. Collection result = null; foreach (var allowedExt in orderedPathExt) { foreach (var fileName in fileNames) { - if (fileName.EndsWith(allowedExt, StringComparison.OrdinalIgnoreCase) - || (!Platform.IsWindows && Platform.NonWindowsIsExecutable(fileName))) + if (fileName.EndsWith(allowedExt, StringComparison.OrdinalIgnoreCase)) { if (result == null) result = new Collection(); diff --git a/src/System.Management.Automation/engine/Credential.cs b/src/System.Management.Automation/engine/Credential.cs index 3a6b07a77..3d15e1cd8 100644 --- a/src/System.Management.Automation/engine/Credential.cs +++ b/src/System.Management.Automation/engine/Credential.cs @@ -9,7 +9,6 @@ using System.Net; using System.Security; using SafeString=System.String; using System.Runtime.Serialization; -using System.Runtime.InteropServices; using System.Security.Cryptography; using Microsoft.PowerShell; @@ -287,7 +286,7 @@ namespace System.Management.Automation { if (unmanagedPtr != IntPtr.Zero) { - Marshal.ZeroFreeCoTaskMemUnicode(unmanagedPtr); + ClrFacade.ZeroFreeCoTaskMemUnicode(unmanagedPtr); } } #else diff --git a/src/System.Management.Automation/engine/DataStoreAdapter.cs b/src/System.Management.Automation/engine/DataStoreAdapter.cs index e6f926e2c..4c796937b 100644 --- a/src/System.Management.Automation/engine/DataStoreAdapter.cs +++ b/src/System.Management.Automation/engine/DataStoreAdapter.cs @@ -299,58 +299,6 @@ namespace System.Management.Automation } private string displayRoot = null; - /// - /// Gets or sets if the drive-root relative paths on this drive are separated by a - /// colon or not. - /// - /// This is true for all PSDrives on all platforms, except for filesystems on - /// non-Windows platforms. - /// - /// This is not a path separator in the sense of separating paths in a single - /// string. - /// - /// The biggest difference in filesystem handling between PS internally, and Unix - /// style systems is, that paths on Windows separate the drive letter from the - /// actual path by a colon. The second difference is, that a path that starts with - /// a \ or / on Windows is considered to be a relative path (drive-relative in - /// that case) where a similar path on a Unix style filesystem would be - /// root-relative, which is basically drive-relative for the filesystem, as there - /// is only one filesystem drive. - /// - /// This property indicates, that a path can be checked for that drive-relativity - /// by checking for a colon. The main reason for this can be seen in all the - /// places that use this property, where PowerShell's code checks/splits/string - /// manipulates paths according to the colon character. This happens in many - /// places. - /// - /// The idea here was to introduce a property that allows a code to query if a - /// PSDrive expects colon to be such a separator or not. I talked to Jim back then - /// about the problem, and this seemed to be a reasonable solution, given that - /// there is no other way to know for a PSDrive if paths can be qualified only in - /// a certain windows way on all platforms, or need special treatment on platforms - /// where colon does not exist as drive separator (regular filesystems on Unix - /// platforms are the only exception). - /// - /// Globally this property can also be only true for one single PSDrive, because - /// if there is no drive separator, there is also no drive, and because there is - /// no drive there is no way to match against multiple such drives. - /// - /// Additional data: - /// It seems that on single rooted filesystems, only the default - /// drive of "/" needs to set this VolumeSeparatedByColon to false - /// otherwise, creating new drives from the filesystem should actually - /// have this set to true as all the drives will have : except - /// for "/" - /// - /// - public bool VolumeSeparatedByColon - { - get { return _volumeSeparatedByColon; } - internal set { _volumeSeparatedByColon = value; } - } - private bool _volumeSeparatedByColon = true; - - #region ctor /// diff --git a/src/System.Management.Automation/engine/DataStoreAdapterProvider.cs b/src/System.Management.Automation/engine/DataStoreAdapterProvider.cs index a8f5c30ab..74e9115ba 100644 --- a/src/System.Management.Automation/engine/DataStoreAdapterProvider.cs +++ b/src/System.Management.Automation/engine/DataStoreAdapterProvider.cs @@ -301,20 +301,6 @@ namespace System.Management.Automation Thread.AllocateDataSlot(); #endif - /// - /// Gets or sets if the drive-root relative paths on drives of this provider - /// are separated by a colon or not. - /// - /// This is true for all PSDrives on all platforms, except for filesystems on - /// non-windows platforms - /// - public bool VolumeSeparatedByColon - { - get { return volumeSeparatedByColon; } - internal set { volumeSeparatedByColon = value; } - } - private bool volumeSeparatedByColon = true; - /// /// Constructs an instance of the class using an existing reference /// as a template. @@ -350,7 +336,6 @@ namespace System.Management.Automation this.helpFile = providerInfo.helpFile; this.pssnapin = providerInfo.pssnapin; this.sessionState = providerInfo.sessionState; - this.volumeSeparatedByColon = providerInfo.volumeSeparatedByColon; } /// @@ -496,13 +481,6 @@ namespace System.Management.Automation null); hiddenDrive.Hidden = true; - - // TODO:PSL - // this is probably not right here - if (implementingType == typeof(Microsoft.PowerShell.Commands.FileSystemProvider) && !Platform.IsWindows) - { - volumeSeparatedByColon = false; - } } #if SUPPORTS_CMDLETPROVIDER_FILE diff --git a/src/System.Management.Automation/engine/InformationRecord.cs b/src/System.Management.Automation/engine/InformationRecord.cs index 34546787e..e3e373a16 100644 --- a/src/System.Management.Automation/engine/InformationRecord.cs +++ b/src/System.Management.Automation/engine/InformationRecord.cs @@ -38,15 +38,7 @@ namespace System.Management.Automation this.TimeGenerated = DateTime.Now; this.Tags = new List(); - if (Platform.IsWindows) - { - this.User = System.Security.Principal.WindowsIdentity.GetCurrent().Name; - } - else - { - this.User = Platform.NonWindowsGetUserName(); - } - // Porting note: PsUtils.GetHostName() already handles platform specifics + this.User = System.Security.Principal.WindowsIdentity.GetCurrent().Name; this.Computer = PsUtils.GetHostName(); this.ProcessId = (uint) System.Diagnostics.Process.GetCurrentProcess().Id; this.NativeThreadId = PsUtils.GetNativeThreadId(); @@ -233,4 +225,4 @@ namespace System.Management.Automation return Message; } } -} +} \ No newline at end of file diff --git a/src/System.Management.Automation/engine/InitialSessionState.cs b/src/System.Management.Automation/engine/InitialSessionState.cs index a31e7799c..76b37dafa 100644 --- a/src/System.Management.Automation/engine/InitialSessionState.cs +++ b/src/System.Management.Automation/engine/InitialSessionState.cs @@ -60,10 +60,7 @@ namespace System.Management.Automation.Runspaces var unused0 = RunspaceInit.OutputEncodingDescription; // Amsi initialize can also be a little slow - if (Platform.IsWindows) - { - AmsiUtils.Init(); - } + AmsiUtils.Init(); // This will init some tables and could load some assemblies. var unused1 = TypeAccelerators.builtinTypeAccelerators; @@ -1676,9 +1673,19 @@ namespace System.Management.Automation.Runspaces return iss; } - // Porting note: moved to Platform so we have one list to maintain - private static string[] PSCoreFormatFileNames = Platform.FormatFileNames.ToArray(); - + private static string[] PSCoreFormatFileNames = { + "Certificate.format.ps1xml", + "Diagnostics.Format.ps1xml", + "DotNetTypes.format.ps1xml", + "Event.Format.ps1xml", + "FileSystem.format.ps1xml", + "Help.format.ps1xml", + "HelpV3.format.ps1xml", + "PowerShellCore.format.ps1xml", + "PowerShellTrace.format.ps1xml", + "Registry.format.ps1xml", + "WSMan.Format.ps1xml" + }; private static void IncludePowerShellCoreFormats(InitialSessionState iss) { string psHome = Utils.GetApplicationBase(Utils.DefaultPowerShellShellID); @@ -1778,14 +1785,25 @@ namespace System.Management.Automation.Runspaces } } - // Porting note: copy so it can be modified - List allowedFormats = new List(Platform.FormatFileNames); + List allowedFormats = new List + { + "Certificate.Format.ps1xml", + "Event.format.ps1xml", + "Diagnostics.format.ps1xml", + "DotNetTypes.Format.ps1xml", + "FileSystem.Format.ps1xml", + "Help.Format.ps1xml", + "HelpV3.format.ps1xml", + "PowerShellCore.format.ps1xml", + "PowerShellTrace.format.ps1xml", + "Registry.format.ps1xml", + "WSMan.format.ps1xml" + }; RemoveDisallowedEntries( iss.Formats, allowedFormats, formatEntry => IO.Path.GetFileName(formatEntry.FileName)); - // Porting note: type files were deprecated List allowedTypes = new List(); allowedTypes.AddRange(DefaultTypeFiles); RemoveDisallowedEntries( @@ -1853,14 +1871,25 @@ namespace System.Management.Automation.Runspaces } } - // Porting note: copy so it can be modified - List allowedFormats = new List(Platform.FormatFileNames); + List allowedFormats = new List + { + "Certificate.Format.ps1xml", + "Event.format.ps1xml", + "Diagnostics.format.ps1xml", + "DotNetTypes.Format.ps1xml", + "FileSystem.Format.ps1xml", + "Help.Format.ps1xml", + "HelpV3.format.ps1xml", + "PowerShellCore.format.ps1xml", + "PowerShellTrace.format.ps1xml", + "Registry.format.ps1xml", + "WSMan.format.ps1xml" + }; RemoveDisallowedEntries( iss.Formats, allowedFormats, formatEntry => IO.Path.GetFileName(formatEntry.FileName)); - // Porting note: type files were deprecated List allowedTypes = new List(); allowedTypes.AddRange(DefaultTypeFiles); RemoveDisallowedEntries( @@ -4256,7 +4285,6 @@ namespace System.Management.Automation.Runspaces return coreSnapin; } - // WARNING: THIS CODE IS COMPLETELY DUPLICATED IN RunspaceConfigForSingleShell internal PSSnapInInfo ImportPSSnapIn(PSSnapInInfo psSnapInInfo, out PSSnapInException warning) { // See if the snapin is already loaded. If has been then there will be an entry in the @@ -4718,32 +4746,6 @@ End /// private static string ImportSystemModulesText = @""; - /// - /// This is the default function to use for clear-host. On Windows it rewrites the - /// host, and on Linux, it delegates to the native binary, 'clear'. - /// - internal static string GetClearHostFunctionText() - { - if (Platform.IsWindows) - { - return @" -$RawUI = $Host.UI.RawUI -$RawUI.CursorPosition = @{X=0;Y=0} -$RawUI.SetBufferContents( - @{Top = -1; Bottom = -1; Right = -1; Left = -1}, - @{Character = ' '; ForegroundColor = $rawui.ForegroundColor; BackgroundColor = $rawui.BackgroundColor}) -# .Link -# http://go.microsoft.com/fwlink/?LinkID=225747 -# .ExternalHelp System.Management.Automation.dll-help.xml -"; - } - else - { - // Porting note: non-Windows platforms use `clear` - return "& (Get-Command -CommandType Application clear | Select-Object -First 1).Definition"; - } - } - /// /// This is the default function to use for man/help. It uses /// splatting to pass in the parameters. @@ -5101,32 +5103,6 @@ end RemotingErrorIdStrings.PSSessionAppName, ScopedItemOptions.None), // End: Variables which control remoting behavior - - #region Platform - new SessionStateVariableEntry( - SpecialVariables.IsLinux, - Platform.IsLinux, - String.Empty, - ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), - - new SessionStateVariableEntry( - SpecialVariables.IsOSX, - Platform.IsOSX, - String.Empty, - ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), - - new SessionStateVariableEntry( - SpecialVariables.IsWindows, - Platform.IsWindows, - String.Empty, - ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), - - new SessionStateVariableEntry( - SpecialVariables.IsCoreCLR, - Platform.IsCoreCLR, - String.Empty, - ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), - #endregion }; /// @@ -5147,6 +5123,8 @@ end "Where-Object", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), new SessionStateAliasEntry("?", "Where-Object", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), + new SessionStateAliasEntry("ac", + "Add-Content", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), new SessionStateAliasEntry("clc", "Clear-Content", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), new SessionStateAliasEntry("cli", @@ -5155,18 +5133,26 @@ end "Clear-ItemProperty", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), new SessionStateAliasEntry("clv", "Clear-Variable", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), + new SessionStateAliasEntry("compare", + "Compare-Object", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), new SessionStateAliasEntry("cpi", "Copy-Item", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), + new SessionStateAliasEntry("cpp", + "Copy-ItemProperty", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), new SessionStateAliasEntry("cvpa", "Convert-Path", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), new SessionStateAliasEntry("dbp", "Disable-PSBreakpoint", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), + new SessionStateAliasEntry("diff", + "Compare-Object", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), new SessionStateAliasEntry("ebp", "Enable-PSBreakpoint", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), new SessionStateAliasEntry("epal", "Export-Alias", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), new SessionStateAliasEntry("epcsv", "Export-Csv", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), + new SessionStateAliasEntry("fc", + "Format-Custom", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), new SessionStateAliasEntry("fl", "Format-List", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), new SessionStateAliasEntry("ft", @@ -5276,75 +5262,26 @@ end "Set-Item", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), new SessionStateAliasEntry("sl", "Set-Location", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), + new SessionStateAliasEntry("sleep", + "Start-Sleep", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), + new SessionStateAliasEntry("sort", + "Sort-Object", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), new SessionStateAliasEntry("sp", "Set-ItemProperty", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), new SessionStateAliasEntry("saps", "Start-Process", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), + new SessionStateAliasEntry("start", + "Start-Process", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), new SessionStateAliasEntry("spps", "Stop-Process", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), new SessionStateAliasEntry("spsv", "Stop-Service", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), new SessionStateAliasEntry("sv", "Set-Variable", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), -// Porting note: #if !UNIX is used to disable alises for cmdlets which conflict with Linux / OS X -#if !UNIX - // ac is a native command on OS X - new SessionStateAliasEntry("ac", - "Add-Content", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), - new SessionStateAliasEntry("compare", - "Compare-Object", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), - new SessionStateAliasEntry("cpp", - "Copy-ItemProperty", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), - new SessionStateAliasEntry("diff", - "Compare-Object", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), - new SessionStateAliasEntry("sleep", - "Start-Sleep", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), - new SessionStateAliasEntry("sort", - "Sort-Object", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), - new SessionStateAliasEntry("start", - "Start-Process", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), new SessionStateAliasEntry("tee", "Tee-Object", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), new SessionStateAliasEntry("write", "Write-Output", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), - // These were traqnsferred from the "transferred from the profile" section - new SessionStateAliasEntry("cat", - "Get-Content", "", ScopedItemOptions.AllScope), - new SessionStateAliasEntry("cp", - "Copy-Item", "", ScopedItemOptions.AllScope), - new SessionStateAliasEntry("ls", - "Get-ChildItem", "", ScopedItemOptions.AllScope), - new SessionStateAliasEntry("man", - "help", "", ScopedItemOptions.AllScope), - new SessionStateAliasEntry("mount", - "New-PSDrive", "", ScopedItemOptions.AllScope), - new SessionStateAliasEntry("mv", - "Move-Item", "", ScopedItemOptions.AllScope), - new SessionStateAliasEntry("ps", - "Get-Process", "", ScopedItemOptions.AllScope), - new SessionStateAliasEntry("rm", - "Remove-Item", "", ScopedItemOptions.AllScope), - new SessionStateAliasEntry("rmdir", - "Remove-Item", "", ScopedItemOptions.AllScope), -#endif - // Bash built-ins we purposefully keep even if they override native commands - new SessionStateAliasEntry("cd", - "Set-Location", "", ScopedItemOptions.AllScope), - new SessionStateAliasEntry("dir", - "Get-ChildItem", "", ScopedItemOptions.AllScope), - new SessionStateAliasEntry("echo", - "Write-Output", "", ScopedItemOptions.AllScope), - new SessionStateAliasEntry("fc", - "Format-Custom", "", ScopedItemOptions.ReadOnly | ScopedItemOptions.AllScope), - new SessionStateAliasEntry("kill", - "Stop-Process", "", ScopedItemOptions.AllScope), - new SessionStateAliasEntry("pwd", - "Get-Location", "", ScopedItemOptions.AllScope), - new SessionStateAliasEntry("type", - "Get-Content", "", ScopedItemOptions.AllScope), - // Native commands we keep because the functions act correctly on Linux - new SessionStateAliasEntry("clear", - "Clear-Host", "", ScopedItemOptions.AllScope), //#if !CORECLR is used to disable aliases for cmdlets which are not available on OneCore #if !CORECLR new SessionStateAliasEntry("asnp", @@ -5381,18 +5318,46 @@ end "Out-Printer", "", ScopedItemOptions.AllScope), #endif // Aliases transferred from the profile + new SessionStateAliasEntry("cat", + "Get-Content", "", ScopedItemOptions.AllScope), + new SessionStateAliasEntry("cd", + "Set-Location", "", ScopedItemOptions.AllScope), + new SessionStateAliasEntry("clear", + "Clear-Host", "", ScopedItemOptions.AllScope), + new SessionStateAliasEntry("cp", + "Copy-Item", "", ScopedItemOptions.AllScope), new SessionStateAliasEntry("h", "Get-History", "", ScopedItemOptions.AllScope), new SessionStateAliasEntry("history", "Get-History", "", ScopedItemOptions.AllScope), + new SessionStateAliasEntry("kill", + "Stop-Process", "", ScopedItemOptions.AllScope), + new SessionStateAliasEntry("ls", + "Get-ChildItem", "", ScopedItemOptions.AllScope), + new SessionStateAliasEntry("man", + "help", "", ScopedItemOptions.AllScope), + new SessionStateAliasEntry("mount", + "New-PSDrive", "", ScopedItemOptions.AllScope), new SessionStateAliasEntry("md", "mkdir", "", ScopedItemOptions.AllScope), + new SessionStateAliasEntry("mv", + "Move-Item", "", ScopedItemOptions.AllScope), new SessionStateAliasEntry("popd", "Pop-Location", "", ScopedItemOptions.AllScope), + new SessionStateAliasEntry("ps", + "Get-Process", "", ScopedItemOptions.AllScope), new SessionStateAliasEntry("pushd", "Push-Location", "", ScopedItemOptions.AllScope), + new SessionStateAliasEntry("pwd", + "Get-Location", "", ScopedItemOptions.AllScope), new SessionStateAliasEntry("r", "Invoke-History", "", ScopedItemOptions.AllScope), + new SessionStateAliasEntry("rm", + "Remove-Item", "", ScopedItemOptions.AllScope), + new SessionStateAliasEntry("rmdir", + "Remove-Item", "", ScopedItemOptions.AllScope), + new SessionStateAliasEntry("echo", + "Write-Output", "", ScopedItemOptions.AllScope), new SessionStateAliasEntry("cls", "Clear-Host", "", ScopedItemOptions.AllScope), new SessionStateAliasEntry("chdir", @@ -5401,6 +5366,8 @@ end "Copy-Item", "", ScopedItemOptions.AllScope), new SessionStateAliasEntry("del", "Remove-Item", "", ScopedItemOptions.AllScope), + new SessionStateAliasEntry("dir", + "Get-ChildItem", "", ScopedItemOptions.AllScope), new SessionStateAliasEntry("erase", "Remove-Item", "", ScopedItemOptions.AllScope), new SessionStateAliasEntry("move", @@ -5411,6 +5378,8 @@ end "Rename-Item", "", ScopedItemOptions.AllScope), new SessionStateAliasEntry("set", "Set-Variable", "", ScopedItemOptions.AllScope), + new SessionStateAliasEntry("type", + "Get-Content", "", ScopedItemOptions.AllScope), new SessionStateAliasEntry("icm", "Invoke-Command", "", ScopedItemOptions.AllScope), new SessionStateAliasEntry("clhy", @@ -5472,30 +5441,40 @@ end # .ExternalHelp System.Management.Automation.dll-help.xml "; + internal const string DefaultClearHostFunctionText = @" +$RawUI = $Host.UI.RawUI +$RawUI.CursorPosition = @{X=0;Y=0} +$RawUI.SetBufferContents( + @{Top = -1; Bottom = -1; Right = -1; Left = -1}, + @{Character = ' '; ForegroundColor = $rawui.ForegroundColor; BackgroundColor = $rawui.BackgroundColor}) +# .Link +# http://go.microsoft.com/fwlink/?LinkID=225747 +# .ExternalHelp System.Management.Automation.dll-help.xml +"; +// Workaround for OS bug 7844078 = 'More.com problem with UTF8 on Nano' +#if CORECLR internal const string DefaultMoreFunctionText = @" param([string[]]$paths) -# Nano needs to use Unicode, but Windows and Linux need the default -$OutputEncoding = if ($IsWindows -and $IsCoreCLR) { - [System.Text.Encoding]::Unicode -} else { - [System.Console]::OutputEncoding -} - -# Respect PAGER, use more on Windows, and use less on Linux -if (Test-Path env:PAGER) { - $moreCommand = (Get-Command -CommandType Application $env:PAGER | Select-Object -First 1).Definition -} elseif ($IsWindows) { - $moreCommand = (Get-Command -CommandType Application more | Select-Object -First 1).Definition -} else { - $moreCommand = (Get-Command -CommandType Application less | Select-Object -First 1).Definition -} - +$OutputEncoding = [System.Text.Encoding]::Unicode if($paths) { - foreach ($file in $paths) { - Get-Content $file | & $moreCommand + foreach ($file in $paths) + { + Get-Content $file | more.com } -} else { $input | & $moreCommand } +} else { $input | more.com } "; +#else + internal const string DefaultMoreFunctionText = @" +param([string[]]$paths) +$OutputEncoding = [System.Console]::OutputEncoding +if($paths) { + foreach ($file in $paths) + { + Get-Content $file | more.com + } +} else { $input | more.com } +"; +#endif internal const string DefaultSetDriveFunctionText = "Set-Location $MyInvocation.MyCommand.Name"; internal static ScriptBlock SetDriveScriptBlock = ScriptBlock.CreateDelayParsedScriptBlock(DefaultSetDriveFunctionText, isProductCode: true); @@ -5503,21 +5482,16 @@ if($paths) { internal static SessionStateFunctionEntry[] BuiltInFunctions = new SessionStateFunctionEntry[] { // Functions. Only the name and definitions are used + SessionStateFunctionEntry.GetDelayParsedFunctionEntry("prompt", DefaultPromptFunctionText, isProductCode: true), SessionStateFunctionEntry.GetDelayParsedFunctionEntry("TabExpansion2", TabExpansionFunctionText, isProductCode: true), - SessionStateFunctionEntry.GetDelayParsedFunctionEntry("Clear-Host", GetClearHostFunctionText(), isProductCode: true), - // Porting note: we keep more because the function acts correctly on Linux + SessionStateFunctionEntry.GetDelayParsedFunctionEntry("Clear-Host", DefaultClearHostFunctionText, isProductCode: true), SessionStateFunctionEntry.GetDelayParsedFunctionEntry("more", DefaultMoreFunctionText, isProductCode: true), SessionStateFunctionEntry.GetDelayParsedFunctionEntry("help", GetHelpPagingFunctionText(), isProductCode: true), - // Porting note: we remove mkdir on Linux because it is a conflict - #if !UNIX SessionStateFunctionEntry.GetDelayParsedFunctionEntry("mkdir", GetMkdirFunctionText(), isProductCode: true), - #endif SessionStateFunctionEntry.GetDelayParsedFunctionEntry("Get-Verb", GetGetVerbText(), isProductCode: true), SessionStateFunctionEntry.GetDelayParsedFunctionEntry("oss", GetOSTFunctionText(), isProductCode: true), - // Porting note: we remove the drive functions from Linux because they make no sense - #if !UNIX // Default drives SessionStateFunctionEntry.GetDelayParsedFunctionEntry("A:", DefaultSetDriveFunctionText, SetDriveScriptBlock), SessionStateFunctionEntry.GetDelayParsedFunctionEntry("B:", DefaultSetDriveFunctionText, SetDriveScriptBlock), @@ -5545,7 +5519,6 @@ if($paths) { SessionStateFunctionEntry.GetDelayParsedFunctionEntry("X:", DefaultSetDriveFunctionText, SetDriveScriptBlock), SessionStateFunctionEntry.GetDelayParsedFunctionEntry("Y:", DefaultSetDriveFunctionText, SetDriveScriptBlock), SessionStateFunctionEntry.GetDelayParsedFunctionEntry("Z:", DefaultSetDriveFunctionText, SetDriveScriptBlock), - #endif SessionStateFunctionEntry.GetDelayParsedFunctionEntry("cd..", "Set-Location ..", isProductCode: true), SessionStateFunctionEntry.GetDelayParsedFunctionEntry("cd\\", "Set-Location \\", isProductCode: true), @@ -5673,7 +5646,6 @@ if($paths) { try { - // WARNING: DUPLICATE CODE see RunspaceConfigForSingleShell assembly = Assembly.Load(new AssemblyName(psSnapInInfo.AssemblyName)); } catch (BadImageFormatException e) @@ -5697,7 +5669,6 @@ if($paths) { try { AssemblyName assemblyName = ClrFacade.GetAssemblyName(psSnapInInfo.AbsoluteModulePath); - if (!string.Equals(assemblyName.FullName, psSnapInInfo.AssemblyName, StringComparison.OrdinalIgnoreCase)) { string message = StringUtil.Format(ConsoleInfoErrorStrings.PSSnapInAssemblyNameMismatch, psSnapInInfo.AbsoluteModulePath, psSnapInInfo.AssemblyName); diff --git a/src/System.Management.Automation/engine/LanguagePrimitives.cs b/src/System.Management.Automation/engine/LanguagePrimitives.cs index 28669cb69..25efbaa39 100644 --- a/src/System.Management.Automation/engine/LanguagePrimitives.cs +++ b/src/System.Management.Automation/engine/LanguagePrimitives.cs @@ -480,14 +480,12 @@ namespace System.Management.Automation { return null; } - #if !CORECLR static IEnumerable DataTableEnumerable(object obj) { return (((DataTable)obj).Rows); } #endif - static IEnumerable TypicalEnumerable(object obj) { IEnumerable e = (IEnumerable)obj; @@ -530,7 +528,6 @@ namespace System.Management.Automation return LanguagePrimitives.DataTableEnumerable; } #endif - // Don't treat IDictionary or XmlNode as enumerable... if (typeof(IEnumerable).IsAssignableFrom(objectType) && !typeof(IDictionary).IsAssignableFrom(objectType) diff --git a/src/System.Management.Automation/engine/Modules/AnalysisCache.cs b/src/System.Management.Automation/engine/Modules/AnalysisCache.cs index 09189ed04..13bff6b29 100644 --- a/src/System.Management.Automation/engine/Modules/AnalysisCache.cs +++ b/src/System.Management.Automation/engine/Modules/AnalysisCache.cs @@ -1027,10 +1027,8 @@ namespace System.Management.Automation { cacheStoreLocation = Environment.GetEnvironmentVariable("PSModuleAnalysisCachePath") ?? - (Platform.IsWindows - ? Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData), - @"Microsoft\Windows\PowerShell\ModuleAnalysisCache") - : Path.Combine(Platform.SelectProductNameForDirectory(Platform.XDG_Type.CACHE), "ModuleAnalysisCache")); + Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData), + @"Microsoft\Windows\PowerShell\ModuleAnalysisCache"); } } diff --git a/src/System.Management.Automation/engine/Modules/ImportModuleCommand.cs b/src/System.Management.Automation/engine/Modules/ImportModuleCommand.cs index 3f429b20b..543c4126b 100644 --- a/src/System.Management.Automation/engine/Modules/ImportModuleCommand.cs +++ b/src/System.Management.Automation/engine/Modules/ImportModuleCommand.cs @@ -652,11 +652,7 @@ namespace Microsoft.PowerShell.Commands else if (Directory.Exists(rootedPath)) { // Load the latest valid version if it is a multi-version module directory - foundModule = LoadUsingMultiVersionModuleBase(rootedPath, - ManifestProcessingFlags.LoadElements | - ManifestProcessingFlags.WriteErrors | - ManifestProcessingFlags.NullOnFirstError, - importModuleOptions, out found); + foundModule = LoadUsingMultiVersionModuleBase(rootedPath, importModuleOptions, out found); if (!found) { diff --git a/src/System.Management.Automation/engine/Modules/ModuleCmdletBase.cs b/src/System.Management.Automation/engine/Modules/ModuleCmdletBase.cs index 648674beb..1af1da7b9 100644 --- a/src/System.Management.Automation/engine/Modules/ModuleCmdletBase.cs +++ b/src/System.Management.Automation/engine/Modules/ModuleCmdletBase.cs @@ -388,7 +388,7 @@ namespace Microsoft.PowerShell.Commands string qualifiedPath = Path.Combine(path, fileBaseName); // Load the latest valid version if it is a multi-version module directory - module = LoadUsingMultiVersionModuleBase(qualifiedPath, manifestProcessingFlags, options, out found); + module = LoadUsingMultiVersionModuleBase(qualifiedPath, options, out found); if (!found) { @@ -432,11 +432,10 @@ namespace Microsoft.PowerShell.Commands /// Loads the latest valid version if moduleBase is a multi-versioned module directory /// /// module directory path - /// The flag that indicate manifest processing option /// The set of options that are used while importing a module /// True if a module was found /// - internal PSModuleInfo LoadUsingMultiVersionModuleBase(string moduleBase, ManifestProcessingFlags manifestProcessingFlags, ImportModuleOptions importModuleOptions, out bool found) + internal PSModuleInfo LoadUsingMultiVersionModuleBase(string moduleBase, ImportModuleOptions importModuleOptions, out bool found) { PSModuleInfo foundModule = null; found = false; @@ -466,7 +465,9 @@ namespace Microsoft.PowerShell.Commands null, this.BasePrefix, /*SessionState*/ null, importModuleOptions, - manifestProcessingFlags, + ManifestProcessingFlags.LoadElements | + ManifestProcessingFlags.WriteErrors | + ManifestProcessingFlags.NullOnFirstError, out found); if (found) { @@ -1193,11 +1194,11 @@ namespace Microsoft.PowerShell.Commands if (!ModuleUtils.IsModuleInVersionSubdirectory(file, out directoryVersion) || directoryVersion == module.Version) { - availableModules.Add(module); + availableModules.Add(module); + } } } } - } ClearAnalysisCaches(); @@ -1817,7 +1818,7 @@ namespace Microsoft.PowerShell.Commands DirectoryInfo parent = null; try { - parent = Directory.GetParent(moduleManifestPath); + parent = ClrFacade.GetParent(moduleManifestPath); } catch (IOException) { @@ -6894,6 +6895,7 @@ namespace Microsoft.PowerShell.Commands InitialSessionState iss = InitialSessionState.Create(); List detectedCmdlets = null; List> detectedAliases = null; + PSSnapInException warning; Assembly assembly = null; Exception error = null; bool importSuccessful = false; @@ -6951,9 +6953,6 @@ namespace Microsoft.PowerShell.Commands { PSSnapInInfo snapin = null; -#if !CORECLR - // Avoid trying to load SnapIns with Import-Module - PSSnapInException warning; try { if (importingModule) @@ -6966,7 +6965,6 @@ namespace Microsoft.PowerShell.Commands //BUGBUG - brucepay - probably want to have a verbose message here... ; } -#endif if (snapin != null) { diff --git a/src/System.Management.Automation/engine/Modules/ModuleIntrinsics.cs b/src/System.Management.Automation/engine/Modules/ModuleIntrinsics.cs index 8d6046551..947326ee5 100644 --- a/src/System.Management.Automation/engine/Modules/ModuleIntrinsics.cs +++ b/src/System.Management.Automation/engine/Modules/ModuleIntrinsics.cs @@ -541,27 +541,18 @@ namespace System.Management.Automation } /// - /// Gets the personal module path - /// (i.e. C:\Users\lukasza\Documents\WindowsPowerShell\modules, or - /// ~/.powershell/Modules on Linux) + /// Gets the personal module path (i.e. C:\Users\lukasza\Documents\WindowsPowerShell\modules) /// /// personal module path internal static string GetPersonalModulePath() { - if (Platform.IsWindows) - { - string personalModuleRoot = Path.Combine( - Path.Combine( - Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments), - Utils.ProductNameForDirectory), - Utils.ModuleDirectory); - return personalModuleRoot; - } - else - { - string personalModuleRoot = Platform.SelectProductNameForDirectory(Platform.XDG_Type.MODULES); - return personalModuleRoot; - } + string personalModuleRoot = Path.Combine( + Path.Combine( + Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments), + Utils.ProductNameForDirectory), + Utils.ModuleDirectory); + + return personalModuleRoot; } /// @@ -597,12 +588,7 @@ namespace System.Management.Automation // Because of this, the module that is getting loaded during startup (through LocalRunspace) // is using "SysWow64" in the key. Later, when Import-Module is called, it loads the // module using ""System32" in the key. - - // Porting note: psHome cannot be lower-cased on case sensitive file systems - if (Platform.IsWindows) - { - psHome = psHome.ToLowerInvariant().Replace("\\syswow64\\", "\\system32\\"); - } + psHome = psHome.ToLowerInvariant().Replace("\\syswow64\\", "\\system32\\"); Interlocked.CompareExchange(ref SystemWideModulePath, Path.Combine(psHome, Utils.ModuleDirectory), null); } @@ -617,11 +603,6 @@ namespace System.Management.Automation /// internal static string GetDscModulePath() { - if (!Platform.IsWindows) - { - return string.Empty; - } - string dscModulePath = null; string programFilesPath = Environment.GetFolderPath(Environment.SpecialFolder.ProgramFiles); if (!string.IsNullOrEmpty(programFilesPath)) @@ -755,7 +736,7 @@ namespace System.Management.Automation if (currentProcessModulePath == null) // EVT.Process does Not exist - really corner case { // Handle the default case... - if (String.IsNullOrEmpty(hkcuUserModulePath)) // EVT.User does Not exist -> set to location + if (hkcuUserModulePath == null) // EVT.User does Not exist -> set to location { currentProcessModulePath = GetPersonalModulePath(); // = SpecialFolder.MyDocuments + Utils.ProductNameForDirectory + Utils.ModuleDirectory } @@ -765,7 +746,7 @@ namespace System.Management.Automation } currentProcessModulePath += ';'; - if (String.IsNullOrEmpty(hklmMachineModulePath)) // EVT.Machine does Not exist + if (hklmMachineModulePath == null) // EVT.Machine does Not exist { currentProcessModulePath += CombineSystemModulePaths(); // += (DscModulePath + $PSHome\Modules) } @@ -778,14 +759,6 @@ namespace System.Management.Automation { // Now handle the case where the environment variable is already set. - // CoreCLR PowerShell on Windows has a Modules folder in the the application base - // path which contains the built-in modules It must be in the front of the path no - // matter what, regardless of inherited path. -#if CORECLR && !UNIX - // TODO: #1184 will resolve this work-around - currentProcessModulePath = AddToPath(currentProcessModulePath, GetSystemwideModulePath(), 0); -#endif - // If there is no personal path key, then if the env variable doesn't match the system variable, // the user modified it somewhere, else prepend the default personel module path if (hklmMachineModulePath != null) // EVT.Machine exists @@ -904,11 +877,11 @@ namespace System.Management.Automation string newModulePathString = GetModulePath(currentModulePath, systemWideModulePath, personalModulePath); - if(!string.IsNullOrEmpty(newModulePathString)) - { - // Set the environment variable... + if(!string.IsNullOrEmpty(newModulePathString)) + { + // Set the environment variable... Environment.SetEnvironmentVariable("PSMODULEPATH", newModulePathString); - } + } return newModulePathString; } @@ -936,13 +909,13 @@ namespace System.Management.Automation if (!string.IsNullOrWhiteSpace(modulePathString)) { - foreach (string envPath in modulePathString.Split(Utils.Separators.Semicolon, StringSplitOptions.RemoveEmptyEntries)) - { - var processedPath = ProcessOneModulePath(context, envPath, processedPathSet); - if (processedPath != null) - yield return processedPath; + foreach (string envPath in modulePathString.Split(Utils.Separators.Semicolon, StringSplitOptions.RemoveEmptyEntries)) + { + var processedPath = ProcessOneModulePath(context, envPath, processedPathSet); + if (processedPath != null) + yield return processedPath; + } } - } if (includeSystemModulePath) { @@ -1001,8 +974,7 @@ namespace System.Management.Automation catch (NotSupportedException) { // silently skip invalid path - // NotSupportedException is thrown if path contains a colon (":") that is not part of a - // volume identifier (for example, "c:\" is Supported but not "c:\temp\Z:\invalidPath") + // NotSupportedException is thrown if path contains a colon (":") that is not part of a volume identifier (for example, "c:\" is Supported but not "c:\temp\Z:\invalidPath") } if (provider != null && resolvedPaths != null && provider.NameEquals(context.ProviderNames.FileSystem)) diff --git a/src/System.Management.Automation/engine/Modules/NewModuleManifestCommand.cs b/src/System.Management.Automation/engine/Modules/NewModuleManifestCommand.cs index e78a3d6d7..b6fd09895 100644 --- a/src/System.Management.Automation/engine/Modules/NewModuleManifestCommand.cs +++ b/src/System.Management.Automation/engine/Modules/NewModuleManifestCommand.cs @@ -386,7 +386,7 @@ namespace Microsoft.PowerShell.Commands /// [Parameter] [AllowEmptyCollection] - [ValidateSet("WindowsPowerShell", "PowerShellCore")] + [ValidateSet("Desktop", "Core")] [SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays", Justification = "Cmdlets use arrays for parameters.")] public string[] CompatiblePSEditions diff --git a/src/System.Management.Automation/engine/Modules/TestModuleManifestCommand.cs b/src/System.Management.Automation/engine/Modules/TestModuleManifestCommand.cs index 50fd817bd..b74c18bfa 100644 --- a/src/System.Management.Automation/engine/Modules/TestModuleManifestCommand.cs +++ b/src/System.Management.Automation/engine/Modules/TestModuleManifestCommand.cs @@ -175,7 +175,7 @@ namespace Microsoft.PowerShell.Commands { foreach (ModuleSpecification requiredModule in requiredModules) { - var modules = GetModule(new[] { requiredModule.Name }, false, true); + var modules = GetModule(new[] { requiredModule.Name }, true, true); if (modules.Count == 0) { string errorMsg = StringUtil.Format(Modules.InvalidRequiredModulesinModuleManifest, requiredModule.Name, filePath); @@ -241,7 +241,7 @@ namespace Microsoft.PowerShell.Commands DirectoryInfo parent = null; try { - parent = Directory.GetParent(filePath); + parent = ClrFacade.GetParent(filePath); } catch (IOException) { } catch (UnauthorizedAccessException) { } diff --git a/src/System.Management.Automation/engine/NativeCommandParameterBinder.cs b/src/System.Management.Automation/engine/NativeCommandParameterBinder.cs index 102ba2ede..067a55caf 100644 --- a/src/System.Management.Automation/engine/NativeCommandParameterBinder.cs +++ b/src/System.Management.Automation/engine/NativeCommandParameterBinder.cs @@ -16,6 +16,11 @@ namespace System.Management.Automation /// internal class NativeCommandParameterBinder : ParameterBinderBase { + #region tracer + [TraceSource("NativeCommandParameterBinder","The parameter binder for native commands")] + static private PSTraceSource tracer = PSTraceSource.GetTracer ("NativeCommandParameterBinder", "The parameter binder for native commands"); + #endregion tracer + #region ctor /// @@ -124,7 +129,21 @@ namespace System.Management.Automation { get { - return arguments.ToString(); + var rawArgs = arguments.ToString(); + + if (tracer.IsEnabled) + { + // This tracing really shouldn't be in the property getter... + tracer.WriteLine("Raw argument string: {0}", rawArgs); + string[] parsedArguments = CommandLineParameterBinderNativeMethods.PreParseCommandLine(rawArgs); + + for (int counter = 0; counter < parsedArguments.Length; counter++) + { + tracer.WriteLine("Argument {0}: {1}", counter, parsedArguments[counter]); + } + } + + return rawArgs; } } // Arguments private readonly StringBuilder arguments = new StringBuilder(); @@ -231,4 +250,39 @@ namespace System.Management.Automation #endregion private members } + internal static class CommandLineParameterBinderNativeMethods + { + public static string[] PreParseCommandLine(string commandLine) + { + int numberOfArguments = 0; + IntPtr parsedCommandLine = CommandLineToArgvW(commandLine, out numberOfArguments); + + if(parsedCommandLine == IntPtr.Zero) + return null; + + try + { + string[] results = new string[numberOfArguments - 1]; + for (int counter = 1; counter < numberOfArguments; counter++) + { + results[counter - 1] = Marshal.PtrToStringUni( + Marshal.ReadIntPtr(parsedCommandLine, counter * IntPtr.Size)); + } + + return results; + } + finally + { + LocalFree(parsedCommandLine); + } + } + + [DllImport(PinvokeDllNames.CommandLineToArgvDllName, SetLastError = true)] + static extern IntPtr CommandLineToArgvW( + [MarshalAs(UnmanagedType.LPWStr)] string lpCmdLine, + out int pNumArgs); + + [DllImport(PinvokeDllNames.LocalFreeDllName)] + static extern IntPtr LocalFree(IntPtr hMem); + } } // namespace System.Management.Automation diff --git a/src/System.Management.Automation/engine/NativeCommandProcessor.cs b/src/System.Management.Automation/engine/NativeCommandProcessor.cs index fb025bce9..a2385aac0 100644 --- a/src/System.Management.Automation/engine/NativeCommandProcessor.cs +++ b/src/System.Management.Automation/engine/NativeCommandProcessor.cs @@ -1024,10 +1024,8 @@ namespace System.Management.Automation ProcessStartInfo startInfo = new ProcessStartInfo(); startInfo.FileName = this.Path; - // On Windows, check the extension list and see if we should try to execute this directly. - // Otherwise, use the platform library to check executability - if ((Platform.IsWindows && ValidateExtension(this.Path)) - || (!Platform.IsWindows && Platform.NonWindowsIsExecutable(this.Path))) + // Check the extension list and see if we should try to execute this directly. + if (ValidateExtension(this.Path)) { startInfo.UseShellExecute = false; if (redirectInput) diff --git a/src/System.Management.Automation/engine/PSVersionInfo.cs b/src/System.Management.Automation/engine/PSVersionInfo.cs index 7a8ba3b8b..ec7839855 100644 --- a/src/System.Management.Automation/engine/PSVersionInfo.cs +++ b/src/System.Management.Automation/engine/PSVersionInfo.cs @@ -4,8 +4,6 @@ Copyright (c) Microsoft Corporation. All rights reserved. using System.Diagnostics; using System.Reflection; using System.Collections; -using System.Globalization; -using System.Management.Automation.Internal; using Microsoft.Win32; namespace System.Management.Automation @@ -39,7 +37,6 @@ namespace System.Management.Automation static Version _psV4Version = new Version(4, 0); static Version _psV5Version = new Version(5, 0); static Version _psV51Version = new Version(5, 1, NTVerpVars.PRODUCTBUILD, NTVerpVars.PRODUCTBUILD_QFE); - static SemanticVersion _psV6Version = new SemanticVersion(6, 0, 0, "alpha"); /// /// A constant to track current PowerShell Edition @@ -50,9 +47,11 @@ namespace System.Management.Automation /// Linux -- All PS on Linux flavors. This may need to be subdivided based on compatibility between distros. /// #if !CORECLR - internal const string PSEditionValue = "WindowsPowerShell"; + internal const string PSEditionValue = "Desktop"; +#elif LINUX + internal const string PSEditionValue = "Linux"; #else - internal const string PSEditionValue = "PowerShellCore"; + internal const string PSEditionValue = "Core"; #endif // Static Constructor. @@ -60,11 +59,10 @@ namespace System.Management.Automation { _psVersionTable = new Hashtable(StringComparer.OrdinalIgnoreCase); - _psVersionTable[PSVersionInfo.PSVersionName] = _psV6Version; + _psVersionTable[PSVersionInfo.PSVersionName] = _psV51Version; _psVersionTable["PSEdition"] = PSEditionValue; _psVersionTable["BuildVersion"] = GetBuildVersion(); - _psVersionTable["GitCommitId"] = GetCommitInfo(); - _psVersionTable["PSCompatibleVersions"] = new Version[] { _psV1Version, _psV2Version, _psV3Version, _psV4Version, _psV5Version, _psV51Version, _psV6Version }; + _psVersionTable["PSCompatibleVersions"] = new Version[] { _psV1Version, _psV2Version, _psV3Version, _psV4Version, _psV5Version, _psV51Version }; _psVersionTable[PSVersionInfo.SerializationVersionName] = new Version(InternalSerializer.DefaultVersion); _psVersionTable[PSVersionInfo.PSRemotingProtocolVersionName] = RemotingConstants.ProtocolVersion; _psVersionTable[PSVersionInfo.WSManStackVersionName] = GetWSManStackVersion(); @@ -87,18 +85,6 @@ namespace System.Management.Automation return new Version(buildVersion); } - // Get the commit id from the powershell.version file. If the powershell.version file doesn't exist, use the string "N/A" - static internal string GetCommitInfo() - { - try { - string assemblyPath = IO.Path.GetDirectoryName(typeof(PSVersionInfo).GetTypeInfo().Assembly.Location); - return (IO.File.ReadAllLines(IO.Path.Combine(assemblyPath,"powershell.version"))[0]); - } - catch (Exception e){ - return e.Message; - } - } - #region Private helper methods // Gets the current WSMan stack version from the registry. @@ -106,7 +92,6 @@ namespace System.Management.Automation { Version version = null; -#if !UNIX try { using (RegistryKey wsManStackVersionKey = Registry.LocalMachine.OpenSubKey(@"Software\Microsoft\Windows\CurrentVersion\WSMAN")) @@ -130,7 +115,6 @@ namespace System.Management.Automation catch (FormatException) { } catch (OverflowException) { } catch (InvalidCastException) { } -#endif return version ?? System.Management.Automation.Remoting.Client.WSManNativeApi.WSMAN_STACK_VERSION; } @@ -143,7 +127,7 @@ namespace System.Management.Automation { get { - return (SemanticVersion) GetPSVersionTable()[PSVersionInfo.PSVersionName]; + return (Version) GetPSVersionTable()[PSVersionInfo.PSVersionName]; } } @@ -250,10 +234,6 @@ namespace System.Management.Automation static internal bool IsValidPSVersion(Version version) { - if (version.Major == _psV6Version.Major) - { - return version.Minor == _psV6Version.Minor; - } if (version.Major == _psV5Version.Major) { return (version.Minor == _psV5Version.Minor || version.Minor == _psV51Version.Minor); @@ -293,460 +273,7 @@ namespace System.Management.Automation get { return _psV51Version; } } - static internal SemanticVersion PSV6Version - { - get { return _psV6Version; } - } - #endregion } - - /// - /// An implementation of semantic versioning (http://semver.org) - /// that can be converted to/from . - /// - /// When converting to , a PSNoteProperty is - /// added to the instance to store the semantic version label so - /// that it can be recovered when creating a new SemanticVersion. - /// - public sealed class SemanticVersion : IComparable, IComparable, IEquatable - { - /// - /// Construct a SemanticVersion from a string. - /// - /// The version to parse - /// - /// - /// - /// - public SemanticVersion(string version) - { - var v = SemanticVersion.Parse(version); - - Major = v.Major; - Minor = v.Minor; - Patch = v.Patch; - Label = v.Label; - } - - /// - /// Construct a SemanticVersion. - /// - /// The major version - /// The minor version - /// The minor version - /// The label for the version - /// - /// If , , or is less than 0. - /// - /// - /// If is null or an empty string. - /// - public SemanticVersion(int major, int minor, int patch, string label) - : this(major, minor, patch) - { - if (string.IsNullOrEmpty(label)) throw PSTraceSource.NewArgumentNullException(nameof(label)); - - Label = label; - } - - /// - /// Construct a SemanticVersion. - /// - /// The major version - /// The minor version - /// The minor version - /// - /// If , , or is less than 0. - /// - public SemanticVersion(int major, int minor, int patch) - { - if (major < 0) throw PSTraceSource.NewArgumentException(nameof(major)); - if (minor < 0) throw PSTraceSource.NewArgumentException(nameof(minor)); - if (patch < 0) throw PSTraceSource.NewArgumentException(nameof(patch)); - - Major = major; - Minor = minor; - Patch = patch; - Label = null; - } - - const string LabelPropertyName = "PSSemanticVersionLabel"; - - /// - /// Construct a from a , - /// copying the NoteProperty storing the label if the expected property exists. - /// - /// The version. - public SemanticVersion(Version version) - { - if (version.Revision > 0 || version.Build < 0) throw PSTraceSource.NewArgumentException(nameof(version)); - - Major = version.Major; - Minor = version.Minor; - Patch = version.Build; - var psobj = new PSObject(version); - var labelNote = psobj.Properties[LabelPropertyName]; - if (labelNote != null) - { - Label = labelNote.Value as string; - } - } - - /// - /// Convert a to a . - /// If there is a , it is added as a NoteProperty to the - /// result so that you can round trip back to a - /// without losing the label. - /// - /// - public static implicit operator Version(SemanticVersion semver) - { - var result = new Version(semver.Major, semver.Minor, semver.Patch); - - if (!string.IsNullOrEmpty(semver.Label)) - { - var psobj = new PSObject(result); - psobj.Properties.Add(new PSNoteProperty(LabelPropertyName, semver.Label)); - } - - return result; - } - - /// - /// The major version number, never negative. - /// - public int Major { get; } - - /// - /// The minor version number, never negative. - /// - public int Minor { get; } - - /// - /// The patch version, -1 if not specified. - /// - public int Patch { get; } - - /// - /// The last component in a SemanticVersion - may be null if not specified. - /// - public string Label { get; } - - /// - /// Parse and return the result if it is a valid , otherwise throws an exception. - /// - /// The string to parse - /// - /// - /// - /// - /// - public static SemanticVersion Parse(string version) - { - if (version == null) throw PSTraceSource.NewArgumentNullException(nameof(version)); - - var r = new VersionResult(); - r.Init(true); - TryParseVersion(version, ref r); - - return r._parsedVersion; - } - - /// - /// Parse and return true if it is a valid , otherwise return false. - /// No exceptions are raised. - /// - /// The string to parse - /// The return value when the string is a valid - public static bool TryParse(string version, out SemanticVersion result) - { - if (version != null) - { - var r = new VersionResult(); - r.Init(false); - - if (TryParseVersion(version, ref r)) - { - result = r._parsedVersion; - return true; - } - } - - result = null; - return false; - } - - private static bool TryParseVersion(string version, ref VersionResult result) - { - var dashIndex = version.IndexOf('-'); - - // Empty label? - if (dashIndex == version.Length - 1) - { - result.SetFailure(ParseFailureKind.ArgumentException); - return false; - } - - var versionSansLabel = (dashIndex < 0) ? version : version.Substring(0, dashIndex); - string[] parsedComponents = versionSansLabel.Split(Utils.Separators.Dot); - if (parsedComponents.Length != 3) - { - result.SetFailure(ParseFailureKind.ArgumentException); - return false; - } - - int major, minor, patch; - if (!TryParseComponent(parsedComponents[0], "major", ref result, out major)) - { - return false; - } - - if (!TryParseComponent(parsedComponents[1], "minor", ref result, out minor)) - { - return false; - } - - if (!TryParseComponent(parsedComponents[2], "patch", ref result, out patch)) - { - return false; - } - - result._parsedVersion = dashIndex < 0 - ? new SemanticVersion(major, minor, patch) - : new SemanticVersion(major, minor, patch, version.Substring(dashIndex + 1)); - return true; - } - - private static bool TryParseComponent(string component, string componentName, ref VersionResult result, out int parsedComponent) - { - if (!Int32.TryParse(component, NumberStyles.Integer, CultureInfo.InvariantCulture, out parsedComponent)) - { - result.SetFailure(ParseFailureKind.FormatException, component); - return false; - } - - if (parsedComponent < 0) - { - result.SetFailure(ParseFailureKind.ArgumentOutOfRangeException, componentName); - return false; - } - - return true; - } - - /// - /// ToString - /// - public override string ToString() - { - if (Patch < 0) - { - return string.IsNullOrEmpty(Label) - ? StringUtil.Format("{0}.{1}", Major, Minor) - : StringUtil.Format("{0}.{1}-{2}", Major, Minor, Label); - } - - return string.IsNullOrEmpty(Label) - ? StringUtil.Format("{0}.{1}.{2}", Major, Minor, Patch) - : StringUtil.Format("{0}.{1}.{2}-{3}", Major, Minor, Patch, Label); - } - - /// - /// Implement - /// - public int CompareTo(object version) - { - if (version == null) - { - return 1; - } - - var v = version as SemanticVersion; - if (v == null) - { - throw PSTraceSource.NewArgumentException(nameof(version)); - } - - return CompareTo(v); - } - - /// - /// Implement - /// - public int CompareTo(SemanticVersion value) - { - if ((object)value == null) - return 1; - - if (Major != value.Major) - return Major > value.Major ? 1 : -1; - - if (Minor != value.Minor) - return Minor > value.Minor ? 1 : -1; - - if (Patch != value.Patch) - return Patch > value.Patch ? 1 : -1; - - if (Label == null) - return value.Label == null ? 0 : 1; - - if (value.Label == null) - return -1; - - if (!string.Equals(Label, value.Label, StringComparison.Ordinal)) - return string.Compare(Label, value.Label, StringComparison.Ordinal); - - return 0; - } - - /// - /// Override - /// - public override bool Equals(object obj) - { - return Equals(obj as SemanticVersion); - } - - /// - /// Implement - /// - public bool Equals(SemanticVersion other) - { - return other != null && - (Major == other.Major) && (Minor == other.Minor) && (Patch == other.Patch) && - string.Equals(Label, other.Label, StringComparison.Ordinal); - } - - /// - /// Override - /// - public override int GetHashCode() - { - return Utils.CombineHashCodes( - Major.GetHashCode(), - Minor.GetHashCode(), - Patch.GetHashCode(), - Label == null ? 0 : Label.GetHashCode()); - } - - /// - /// Overloaded == operator - /// - public static bool operator ==(SemanticVersion v1, SemanticVersion v2) - { - if (object.ReferenceEquals(v1, null)) { - return object.ReferenceEquals(v2, null); - } - - return v1.Equals(v2); - } - - /// - /// Overloaded != operator - /// - public static bool operator !=(SemanticVersion v1, SemanticVersion v2) - { - return !(v1 == v2); - } - - /// - /// Overloaded < operator - /// - public static bool operator <(SemanticVersion v1, SemanticVersion v2) - { - if ((object) v1 == null) throw PSTraceSource.NewArgumentException(nameof(v1)); - return (v1.CompareTo(v2) < 0); - } - - /// - /// Overloaded <= operator - /// - public static bool operator <=(SemanticVersion v1, SemanticVersion v2) - { - if ((object) v1 == null) throw PSTraceSource.NewArgumentException(nameof(v1)); - return (v1.CompareTo(v2) <= 0); - } - - /// - /// Overloaded > operator - /// - public static bool operator >(SemanticVersion v1, SemanticVersion v2) - { - return (v2 < v1); - } - - /// - /// Overloaded >= operator - /// - public static bool operator >=(SemanticVersion v1, SemanticVersion v2) - { - return (v2 <= v1); - } - - internal enum ParseFailureKind - { - ArgumentException, - ArgumentOutOfRangeException, - FormatException - } - - internal struct VersionResult - { - internal SemanticVersion _parsedVersion; - internal ParseFailureKind _failure; - internal string _exceptionArgument; - internal bool _canThrow; - - internal void Init(bool canThrow) - { - _canThrow = canThrow; - } - - internal void SetFailure(ParseFailureKind failure) - { - SetFailure(failure, String.Empty); - } - - internal void SetFailure(ParseFailureKind failure, string argument) - { - _failure = failure; - _exceptionArgument = argument; - if (_canThrow) - { - throw GetVersionParseException(); - } - } - - internal Exception GetVersionParseException() - { - switch (_failure) - { - case ParseFailureKind.ArgumentException: - return PSTraceSource.NewArgumentException("version"); - case ParseFailureKind.ArgumentOutOfRangeException: - throw new ValidationMetadataException("ValidateRangeTooSmall", - null, Metadata.ValidateRangeSmallerThanMinRangeFailure, - _exceptionArgument, "0"); - case ParseFailureKind.FormatException: - // Regenerate the FormatException as would be thrown by Int32.Parse() - try - { - Int32.Parse(_exceptionArgument, CultureInfo.InvariantCulture); - } - catch (FormatException e) - { - return e; - } - catch (OverflowException e) - { - return e; - } - break; - } - return PSTraceSource.NewArgumentException("version"); - } - } - } } diff --git a/src/System.Management.Automation/engine/SecurityManagerBase.cs b/src/System.Management.Automation/engine/SecurityManagerBase.cs index 0d06b776e..0f594a7ff 100644 --- a/src/System.Management.Automation/engine/SecurityManagerBase.cs +++ b/src/System.Management.Automation/engine/SecurityManagerBase.cs @@ -87,16 +87,6 @@ namespace System.Management.Automation CommandOrigin origin, PSHost host) { -#if UNIX - // TODO:PSL this is a workaround since the exception below - // hides the internal issue of what's going on in terms of - // execution policy. - // On non-Windows platform Set/Get-ExecutionPolicy throw - // PlatformNotSupportedException - return; -#else - - #if DEBUG // If we are debugging, let the unit tests swap the file from beneath us if(commandInfo.CommandType == CommandTypes.ExternalScript) @@ -160,7 +150,6 @@ namespace System.Management.Automation throw new PSSecurityException(AuthorizationManagerBase.AuthorizationManagerDefaultFailureReason); } } -#endif } /// diff --git a/src/System.Management.Automation/engine/SessionStateContainer.cs b/src/System.Management.Automation/engine/SessionStateContainer.cs index 5cc6d8134..3dfd8464d 100644 --- a/src/System.Management.Automation/engine/SessionStateContainer.cs +++ b/src/System.Management.Automation/engine/SessionStateContainer.cs @@ -3712,8 +3712,6 @@ namespace System.Management.Automation } bool isSymbolicJunctionOrHardLink = false; - // Symbolic link targets are allowed to not exist on both Windows and Linux - bool allowNonexistingPath = false; if(type != null) { @@ -3722,7 +3720,6 @@ namespace System.Management.Automation if (typeEvaluator.IsMatch("symboliclink") || typeEvaluator.IsMatch("junction") || typeEvaluator.IsMatch("hardlink")) { isSymbolicJunctionOrHardLink = true; - allowNonexistingPath = typeEvaluator.IsMatch("symboliclink"); } } @@ -3745,7 +3742,7 @@ namespace System.Management.Automation var globbedTarget = Globber.GetGlobbedProviderPathsFromMonadPath( targetPath, - allowNonexistingPath, + false, context, out targetProvider, out targetProviderInstance); diff --git a/src/System.Management.Automation/engine/SessionStateDriveAPIs.cs b/src/System.Management.Automation/engine/SessionStateDriveAPIs.cs index 618189068..f25090481 100644 --- a/src/System.Management.Automation/engine/SessionStateDriveAPIs.cs +++ b/src/System.Management.Automation/engine/SessionStateDriveAPIs.cs @@ -1469,12 +1469,10 @@ namespace System.Management.Automation bool driveIsValid = true; // If the drive is auto-mounted, ensure that it still exists, or remove the drive. -#if !UNIX if (drive.IsAutoMounted || IsAStaleVhdMountedDrive(drive)) { driveIsValid = ValidateOrRemoveAutoMountedDrive(drive, lookupScope); } -#endif if(drive.Name.Length == 1) { if(!(driveNames.Contains(drive.Name))) diff --git a/src/System.Management.Automation/engine/SessionStateNavigation.cs b/src/System.Management.Automation/engine/SessionStateNavigation.cs index c6a51d0f5..78ea6401c 100644 --- a/src/System.Management.Automation/engine/SessionStateNavigation.cs +++ b/src/System.Management.Automation/engine/SessionStateNavigation.cs @@ -197,13 +197,13 @@ namespace System.Management.Automation bool isProviderQualified = false; bool isDriveQualified = false; string qualifier = null; - string pathNoQualifier = RemoveQualifier(path, provider, out qualifier, out isProviderQualified, out isDriveQualified); + string pathNoQualifier = RemoveQualifier(path, out qualifier, out isProviderQualified, out isDriveQualified); string result = GetParentPath(provider, pathNoQualifier, root, context); if (!String.IsNullOrEmpty(qualifier) && !String.IsNullOrEmpty(result)) { - result = AddQualifier(result, provider, qualifier, isProviderQualified, isDriveQualified); + result = AddQualifier(result, qualifier, isProviderQualified, isDriveQualified); } return result; @@ -214,7 +214,7 @@ namespace System.Management.Automation } } // GetParentPath - private string AddQualifier(string path, ProviderInfo provider, string qualifier, bool isProviderQualified, bool isDriveQualified) + private string AddQualifier(string path, string qualifier, bool isProviderQualified, bool isDriveQualified) { string result = path; @@ -225,15 +225,7 @@ namespace System.Management.Automation } else if (isDriveQualified) { - // Porting note: on non-windows filesystem paths, there should be no colon in the path - if (provider.VolumeSeparatedByColon) - { - formatString = "{0}:{1}"; - } - else - { - formatString = "{0}{1}"; - } + formatString = "{0}:{1}"; } result = @@ -254,10 +246,6 @@ namespace System.Management.Automation /// The path to strip the provider qualifier from. /// /// - /// - /// The provider that should handle the RemoveQualifier call. - /// - /// /// /// Returns the qualifier of the path. /// @@ -274,7 +262,7 @@ namespace System.Management.Automation /// The path without the qualifier. /// /// - private string RemoveQualifier(string path, ProviderInfo provider, out string qualifier, out bool isProviderQualified, out bool isDriveQualified) + private string RemoveQualifier(string path, out string qualifier, out bool isProviderQualified, out bool isDriveQualified) { Dbg.Diagnostics.Assert( path != null, @@ -303,17 +291,9 @@ namespace System.Management.Automation { isDriveQualified = true; - // Remove the drive name and colon, or just the drive name + // Remove the drive name and colon - // Porting note: on non-windows there is no colon for qualified paths - if (provider.VolumeSeparatedByColon) - { - result = path.Substring(qualifier.Length + 1); - } - else - { - result = path.Substring(qualifier.Length); - } + result = path.Substring(qualifier.Length + 1); } } diff --git a/src/System.Management.Automation/engine/SessionStateStrings.cs b/src/System.Management.Automation/engine/SessionStateStrings.cs index 93e40863c..cfde27930 100644 --- a/src/System.Management.Automation/engine/SessionStateStrings.cs +++ b/src/System.Management.Automation/engine/SessionStateStrings.cs @@ -26,25 +26,17 @@ namespace System.Management.Automation /// /// The default path separator used by the base implementation of the providers. - /// - /// Porting note: IO.Path.DirectorySeparatorChar is correct for all platforms. On Windows, - /// it is '\', and on Linux, it is '/', as expected. /// /// - internal static readonly char DefaultPathSeparator = System.IO.Path.DirectorySeparatorChar; - internal static readonly string DefaultPathSeparatorString = DefaultPathSeparator.ToString(); + internal const char DefaultPathSeparator = '\\'; + internal const string DefaultPathSeparatorString = "\\"; /// /// The alternate path separator used by the base implementation of the providers. - /// - /// Porting note: we do not use .NET's AlternatePathSeparatorChar here because it correctly - /// states that both the default and alternate are '/' on Linux. However, for PowerShell to - /// be "slash agnostic", we need to use the assumption that a '\' is the alternate path - /// separator on Linux. /// /// - internal static readonly char AlternatePathSeparator = Platform.IsWindows ? '/' : '\\'; - internal static readonly string AlternatePathSeparatorString = AlternatePathSeparator.ToString(); + internal const char AlternatePathSeparator = '/'; + internal const string AlternatePathSeparatorString = "/"; /// /// The default path prefix for remote paths. This is to mimic diff --git a/src/System.Management.Automation/engine/SpecialVariables.cs b/src/System.Management.Automation/engine/SpecialVariables.cs index 0fd56301c..2f6dd0a01 100644 --- a/src/System.Management.Automation/engine/SpecialVariables.cs +++ b/src/System.Management.Automation/engine/SpecialVariables.cs @@ -156,20 +156,6 @@ namespace System.Management.Automation internal const string PSModuleAutoLoading = "PSModuleAutoLoadingPreference"; internal static VariablePath PSModuleAutoLoadingPreferenceVarPath = new VariablePath("global:" + PSModuleAutoLoading); - #region Platform Variables - internal const string IsLinux = "IsLinux"; - internal static VariablePath IsLinuxPath = new VariablePath("IsLinux"); - - internal const string IsOSX = "IsOSX"; - internal static VariablePath IsOSXPath = new VariablePath("IsOSX"); - - internal const string IsWindows = "IsWindows"; - internal static VariablePath IsWindowsPath = new VariablePath("IsWindows"); - - internal const string IsCoreCLR = "IsCoreCLR"; - internal static VariablePath IsCoreCLRPath = new VariablePath("IsCoreCLR"); - - #endregion #region Preference Variables internal const string DebugPreference = "DebugPreference"; diff --git a/src/System.Management.Automation/engine/Utils.cs b/src/System.Management.Automation/engine/Utils.cs index ea1fbc3c5..91969c03c 100644 --- a/src/System.Management.Automation/engine/Utils.cs +++ b/src/System.Management.Automation/engine/Utils.cs @@ -71,7 +71,7 @@ namespace System.Management.Automation /// /// Allowed PowerShell Editions /// - internal static string[] AllowedEditionValues = { "WindowsPowerShell", "PowerShellCore" }; + internal static string[] AllowedEditionValues = { "Desktop", "Core" }; /// /// helper fn to check byte[] arg for null. @@ -170,7 +170,7 @@ namespace System.Management.Automation { if (p != IntPtr.Zero) { - Marshal.ZeroFreeCoTaskMemUnicode(p); + ClrFacade.ZeroFreeCoTaskMemUnicode(p); } } @@ -196,7 +196,16 @@ namespace System.Management.Automation private static string _pshome = null; - internal static string GetApplicationBaseFromRegistry(string shellId) + /// + /// Gets the application base for current monad version + /// + /// + /// applicationbase path for current monad version installation + /// + /// + /// if caller doesn't have permission to read the key + /// + internal static string GetApplicationBase(string shellId) { bool wantPsHome = (object) shellId == (object) DefaultPowerShellShellID; if (wantPsHome && _pshome != null) @@ -217,33 +226,6 @@ namespace System.Management.Automation } } - return null; - } - - /// - /// Gets the application base for current monad version - /// - /// - /// applicationbase path for current monad version installation - /// - /// - /// if caller doesn't have permission to read the key - /// - internal static string GetApplicationBase(string shellId) - { - // TODO: #1184 will resolve this work-around - // The application base cannot be resolved from the registry for side-by-side versions - // of PowerShell. -#if !CORECLR - // try to get the path from the registry first - string result = GetApplicationBaseFromRegistry(shellId); - if (result != null) - { - return result; - } -#endif - - #if CORECLR // Use the location of SMA.dll as the application base // Assembly.GetEntryAssembly is not in CoreCLR. GAC is not in CoreCLR. Assembly assembly = typeof(PSObject).GetTypeInfo().Assembly; @@ -298,24 +280,16 @@ namespace System.Management.Automation } // And built-in modules - string progFileDir; - // TODO: #1184 will resolve this work-around - // Side-by-side versions of PowerShell use modules from their application base, not - // the system installation path. -#if CORECLR - progFileDir = Path.Combine(appBase, "Modules"); -#else - progFileDir = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ProgramFiles), "WindowsPowerShell", "Modules"); -#endif - + string progFileDir = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ProgramFiles), "WindowsPowerShell", "Modules"); if (!string.IsNullOrEmpty(progFileDir)) { baseDirectories.Add(Path.Combine(progFileDir, "PackageManagement")); baseDirectories.Add(Path.Combine(progFileDir, "PowerShellGet")); baseDirectories.Add(Path.Combine(progFileDir, "Pester")); - baseDirectories.Add(Path.Combine(progFileDir, "PSReadLine")); #if CORECLR baseDirectories.Add(Path.Combine(progFileDir, "Json.Net")); +#else + baseDirectories.Add(Path.Combine(progFileDir, "PSReadline")); #endif // CORECLR } Interlocked.CompareExchange(ref _productFolderDirectories, baseDirectories.ToArray(), null); @@ -362,7 +336,6 @@ namespace System.Management.Automation /// internal static bool IsWinPEHost() { -#if !UNIX RegistryKey winPEKey = null; try @@ -383,7 +356,7 @@ namespace System.Management.Automation winPEKey.Dispose(); } } -#endif + return false; } @@ -573,8 +546,7 @@ namespace System.Management.Automation /// /// Profile uses this to control profile loading. /// - internal static string ProductNameForDirectory = - Platform.IsWindows ? "WindowsPowerShell" : Platform.SelectProductNameForDirectory(Platform.XDG_Type.CONFIG); + internal static string ProductNameForDirectory = "WindowsPowerShell"; /// /// The name of the subdirectory that contains packages. @@ -584,7 +556,7 @@ namespace System.Management.Automation /// /// The partial path to the DSC module directory /// - internal static string DscModuleDirectory = Path.Combine("WindowsPowerShell", "Modules"); + internal static string DscModuleDirectory = "WindowsPowerShell\\Modules"; internal static string GetRegistryConfigurationPrefix() { @@ -614,14 +586,8 @@ namespace System.Management.Automation return GetGroupPolicySetting(groupPolicyBase, settingName, preferenceOrder); } - // We use a static to avoid creating "extra garbage." - private static Dictionary _emptyDictionary = new Dictionary(StringComparer.OrdinalIgnoreCase); - internal static Dictionary GetGroupPolicySetting(string groupPolicyBase, string settingName, RegistryKey[] preferenceOrder) { -#if UNIX - return _emptyDictionary; -#else lock (cachedGroupPolicySettings) { // Return cached information, if we have it @@ -696,7 +662,6 @@ namespace System.Management.Automation return settings; } -#endif } static ConcurrentDictionary> cachedGroupPolicySettings = new ConcurrentDictionary>(); @@ -924,20 +889,10 @@ namespace System.Management.Automation internal static bool IsAdministrator() { - // Porting note: only Windows supports the SecurityPrincipal API of .NET. Due to - // advanced privilege models, the correct approach on Unix is to assume the user has - // permissions, attempt the task, and error gracefully if the task fails due to - // permissions. To fit into PowerShell's existing model of pre-emptively checking - // permissions (which cannot be assumed on Unix), we "assume" the user is an - // administrator by returning true, thus nullifying this check on Unix. -#if UNIX - return true; -#else System.Security.Principal.WindowsIdentity currentIdentity = System.Security.Principal.WindowsIdentity.GetCurrent(); System.Security.Principal.WindowsPrincipal principal = new System.Security.Principal.WindowsPrincipal(currentIdentity); return principal.IsInRole(System.Security.Principal.WindowsBuiltInRole.Administrator); -#endif } internal static bool NativeItemExists(string path) @@ -959,10 +914,6 @@ namespace System.Management.Automation isDirectory = false; return false; } -#if UNIX - isDirectory = Platform.NonWindowsIsDirectory(path); - return Platform.NonWindowsIsFile(path); -#else if (IsReservedDeviceName(path)) { @@ -996,7 +947,6 @@ namespace System.Management.Automation ((int)NativeMethods.FileAttributes.Directory); return true; -#endif } // This is done through P/Invoke since we pay 13% performance degradation @@ -1096,12 +1046,8 @@ namespace System.Management.Automation internal static bool PathIsUnc(string path) { -#if UNIX - return false; -#else Uri uri; return !string.IsNullOrEmpty(path) && Uri.TryCreate(path, UriKind.Absolute, out uri) && uri.IsUnc; -#endif } internal class NativeMethods diff --git a/src/System.Management.Automation/engine/hostifaces/History.cs b/src/System.Management.Automation/engine/hostifaces/History.cs index 65caf987e..167381725 100644 --- a/src/System.Management.Automation/engine/hostifaces/History.cs +++ b/src/System.Management.Automation/engine/hostifaces/History.cs @@ -1233,8 +1233,8 @@ namespace Microsoft.PowerShell.Commands { WriteObject(results, true); } - pipeline.RemoveFromInvokeHistoryEntryList(entry); - } + pipeline.RemoveFromInvokeHistoryEntryList(entry); + } finally { ps.Streams.Debug.DataAdded -= debugAdded; diff --git a/src/System.Management.Automation/engine/hostifaces/HostUtilities.cs b/src/System.Management.Automation/engine/hostifaces/HostUtilities.cs index 18d3a7a83..b6c01424c 100644 --- a/src/System.Management.Automation/engine/hostifaces/HostUtilities.cs +++ b/src/System.Management.Automation/engine/hostifaces/HostUtilities.cs @@ -198,6 +198,7 @@ namespace System.Management.Automation string profileName = useTestProfile ? "profile_test.ps1" : "profile.ps1"; + if (!string.IsNullOrEmpty(shellId)) { profileName = shellId + "_" + profileName; diff --git a/src/System.Management.Automation/engine/parser/PSType.cs b/src/System.Management.Automation/engine/parser/PSType.cs index 3d42739a2..c846f9bf8 100644 --- a/src/System.Management.Automation/engine/parser/PSType.cs +++ b/src/System.Management.Automation/engine/parser/PSType.cs @@ -1124,10 +1124,7 @@ namespace System.Management.Automation.Language // Two replaces at the end are for not-allowed characters. They are replaced by similar-looking chars. string assemblyName = ClrFacade.FIRST_CHAR_PSASSEMBLY_MARK + (string.IsNullOrWhiteSpace(rootAst.Extent.File) ? "powershell" - : rootAst.Extent.File - .Replace('\\', (char)0x29f9) - .Replace('/', (char)0x29f9) - .Replace(':', (char)0x0589)); + : rootAst.Extent.File.Replace('\\', (char)0x29f9).Replace(':', (char)0x0589)); var assembly = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName(assemblyName), AssemblyBuilderAccess.RunAndCollect, GetAssemblyAttributeBuilders()); diff --git a/src/System.Management.Automation/engine/remoting/commands/remotingcommandutil.cs b/src/System.Management.Automation/engine/remoting/commands/remotingcommandutil.cs index 854c80d1d..5d0c392bb 100644 --- a/src/System.Management.Automation/engine/remoting/commands/remotingcommandutil.cs +++ b/src/System.Management.Automation/engine/remoting/commands/remotingcommandutil.cs @@ -46,6 +46,15 @@ namespace Microsoft.PowerShell.Commands /// internal static string WinPEIdentificationRegKey = @"System\CurrentControlSet\Control\MiniNT"; + /// + /// IsWinPEHost indicates if the machine on which PowerShell is hosted is WinPE or not. + /// This is a helper variable used to kep track if the IsWinPE() helper method has + /// already checked for the WinPE specific registry key or not. + /// If the WinPE specific registry key has not yet been checked even + /// once then this variable will point to null. + /// + internal static bool? isWinPEHost = null; + internal static bool HasRepeatingRunspaces(PSSession[] runspaceInfos) { if (runspaceInfos == null) @@ -96,13 +105,9 @@ namespace Microsoft.PowerShell.Commands /// internal static void CheckRemotingCmdletPrerequisites() { -#if UNIX - // TODO: check that PSRP requirements are installed - return; -#else bool notSupported = true; String WSManKeyPath = "Software\\Microsoft\\Windows\\CurrentVersion\\WSMAN\\"; - + CheckHostRemotingPrerequisites(); try @@ -153,7 +158,46 @@ namespace Microsoft.PowerShell.Commands throw new InvalidOperationException( "Windows PowerShell remoting features are not enabled or not supported on this machine.\nThis may be because you do not have the correct version of WS-Management installed or this version of Windows does not support remoting currently.\n For more information, type 'get-help about_remote_requirements'."); } -#endif + } + + /// + /// IsWinPEHost is a helper method used to identify if the + /// PowerShell is hosted on a WinPE machine. + /// + internal static bool IsWinPEHost() + { + RegistryKey wsManKey = null; + + if (isWinPEHost == null) + { + try + { + // The existence of the following registry confirms that the host machine is a WinPE + // HKLM\System\CurrentControlSet\Control\MiniNT + wsManKey = Registry.LocalMachine.OpenSubKey(WinPEIdentificationRegKey); + + if (null != wsManKey) + { + isWinPEHost = true; + } + else + { + isWinPEHost = false; + } + } + catch (ArgumentException) { } + catch (System.Security.SecurityException) { } + catch (ObjectDisposedException) { } + finally + { + if (wsManKey != null) + { + wsManKey.Dispose(); + } + } + } + + return isWinPEHost== true? true: false; } /// @@ -169,7 +213,7 @@ namespace Microsoft.PowerShell.Commands { // A registry key indicates if the SKU is WINPE. If this turns out to be true, // then an InValidOperation exception is thrown. - bool isWinPEHost = Utils.IsWinPEHost(); + bool isWinPEHost = IsWinPEHost(); if (isWinPEHost) { // WSMan is not supported on this platform diff --git a/src/System.Management.Automation/engine/remoting/common/RemoteSessionNamedPipe.cs b/src/System.Management.Automation/engine/remoting/common/RemoteSessionNamedPipe.cs index cc9ed26d3..6417ee81e 100644 --- a/src/System.Management.Automation/engine/remoting/common/RemoteSessionNamedPipe.cs +++ b/src/System.Management.Automation/engine/remoting/common/RemoteSessionNamedPipe.cs @@ -533,12 +533,8 @@ namespace System.Management.Automation.Remoting SyncObject = new object(); // All PowerShell instances will start with the named pipe - // and listner created and running. - if (Platform.IsWindows) - { - IPCNamedPipeServerEnabled = true; - } - + // and listener created and running. + IPCNamedPipeServerEnabled = true; CreateIPCNamedPipeServerSingleton(); #if !CORECLR // There is only one AppDomain per application in CoreCLR, which would be the default CreateAppDomainUnloadHandler(); diff --git a/src/System.Management.Automation/engine/remoting/fanin/WSManNativeAPI.cs b/src/System.Management.Automation/engine/remoting/fanin/WSManNativeAPI.cs index 1d6686cee..625491cbb 100644 --- a/src/System.Management.Automation/engine/remoting/fanin/WSManNativeAPI.cs +++ b/src/System.Management.Automation/engine/remoting/fanin/WSManNativeAPI.cs @@ -379,7 +379,7 @@ namespace System.Management.Automation.Remoting.Client { if (cred.password != IntPtr.Zero) { - Marshal.ZeroFreeCoTaskMemUnicode(cred.password); + ClrFacade.ZeroFreeCoTaskMemUnicode(cred.password); cred.password = IntPtr.Zero; } @@ -2303,11 +2303,7 @@ namespace System.Management.Automation.Remoting.Client #region DllImports ClientAPI -#if !UNIX internal const string WSManApiDll = @"WsmSvc.dll"; -#else - internal const string WSManApiDll = @"libpsrpomiprov"; -#endif /// /// This API is used to initialize the WinRM client; @@ -2547,7 +2543,6 @@ namespace System.Management.Automation.Remoting.Client IntPtr asyncCallback, [In, Out] ref IntPtr shellOperationHandle); - /// /// /// @@ -2906,8 +2901,7 @@ namespace System.Management.Automation.Remoting.Client int flags, int errorCode, [MarshalAs(UnmanagedType.LPWStr)] string extendedInformation); - - + internal enum WSManFlagReceive : int { /// @@ -2971,20 +2965,7 @@ namespace System.Management.Automation.Remoting.Client IntPtr requestDetails, int flags, IntPtr context); -#if UNIX - /// - /// Registers the shutdown callback. - /// - /// Specifies the resource URI, options, locale, shutdown flag, and handle for the request. - /// Callback to be executed on shutdown - /// - /// - [DllImport(WSManNativeApi.WSManApiDll, SetLastError = false, CharSet = CharSet.Unicode)] - internal static extern void WSManPluginRegisterShutdownCallback( - IntPtr requestDetails, - IntPtr shutdownCallback, - IntPtr shutdownContext); -#endif + #endregion } @@ -3020,11 +3001,6 @@ namespace System.Management.Automation.Remoting.Client IntPtr requestDetails, int flags, IntPtr context); - - void WSManPluginRegisterShutdownCallback( - IntPtr requestDetails, - IntPtr shutdownCallback, - IntPtr shutdownContext); } /// @@ -3067,15 +3043,5 @@ namespace System.Management.Automation.Remoting.Client { return WSManNativeApi.WSManPluginReportContext(requestDetails, flags, context); } - - void IWSManNativeApiFacade.WSManPluginRegisterShutdownCallback( - IntPtr requestDetails, - IntPtr shutdownCallback, - IntPtr shutdownContext) - { -#if UNIX - WSManNativeApi.WSManPluginRegisterShutdownCallback(requestDetails, shutdownCallback, shutdownContext); -#endif - } } } diff --git a/src/System.Management.Automation/engine/remoting/fanin/WSManPlugin.cs b/src/System.Management.Automation/engine/remoting/fanin/WSManPlugin.cs index a5d9e3ed2..35199fad2 100644 --- a/src/System.Management.Automation/engine/remoting/fanin/WSManPlugin.cs +++ b/src/System.Management.Automation/engine/remoting/fanin/WSManPlugin.cs @@ -170,14 +170,14 @@ namespace System.Management.Automation.Remoting #if !CORECLR // Register our remoting handler for crashes AppDomain currentDomain = AppDomain.CurrentDomain; - currentDomain.UnhandledException += + currentDomain.UnhandledException += new UnhandledExceptionEventHandler(WSManPluginInstance.UnhandledExceptionHandler); // Register our Watson handler for crash reports in server mode System.Management.Automation.WindowsErrorReporting.RegisterWindowsErrorReporting(true); #endif } - + #endregion /// @@ -278,20 +278,10 @@ namespace System.Management.Automation.Remoting try { PSSenderInfo senderInfo = GetPSSenderInfo(requestDetails.senderDetails); - + // inbound shell information is already verified by pwrshplugin.dll.. so no need // to verify here. - WSManPluginServerTransportManager serverTransportMgr; - - if (Platform.IsWindows) - { - serverTransportMgr = new WSManPluginServerTransportManager(BaseTransportManager.DefaultFragmentSize, new PSRemotingCryptoHelperServer()); - } - - else - { - serverTransportMgr = new WSManPluginServerTransportManager(BaseTransportManager.DefaultFragmentSize, null); - } + WSManPluginServerTransportManager serverTransportMgr = new WSManPluginServerTransportManager(BaseTransportManager.DefaultFragmentSize, new PSRemotingCryptoHelperServer()); PSEtwLog.LogAnalyticInformational(PSEventId.ServerCreateRemoteSession, PSOpcode.Connect, PSTask.None, @@ -315,7 +305,7 @@ namespace System.Management.Automation.Remoting { ReportOperationComplete(requestDetails, WSManPluginErrorCodes.OutOfMemory); return; - } + } // Create a shell session wrapper to track and service future interacations. mgdShellSession = new WSManPluginShellSession(requestDetails, serverTransportMgr, remoteShellSession, context); @@ -381,53 +371,34 @@ namespace System.Management.Automation.Remoting } bool isRegisterWaitForSingleObjectSucceeded = true; - - //always synchronize calls to OperationComplete once notification handle is registered.. else duplicate OperationComplete calls are bound to happen - lock (mgdShellSession.shellSyncObject) - { + + //always synchronize calls to OperationComplete once notification handle is registered.. else duplicate OperationComplete calls are bound to happen + lock (mgdShellSession.shellSyncObject) + { mgdShellSession.registeredShutdownNotification = 1; // Wrap the provided handle so it can be passed to the registration function + SafeWaitHandle safeWaitHandle = new SafeWaitHandle(requestDetails.shutdownNotificationHandle, false); // Owned by WinRM EventWaitHandle eventWaitHandle = new EventWaitHandle(false, EventResetMode.AutoReset); - - if (Platform.IsWindows) - { - SafeWaitHandle safeWaitHandle = new SafeWaitHandle(requestDetails.shutdownNotificationHandle, false); // Owned by WinRM - ClrFacade.SetSafeWaitHandle(eventWaitHandle, safeWaitHandle); - } - else - { - //On non-windows platforms the shutdown notification is done through a callback instead of a windows event handle. - //Register the callback and this will then signal the event. Note, the gch object is deleted in the shell shutdown - //notification that will always come in to shut down the operation. - - GCHandle gch = GCHandle.Alloc(eventWaitHandle); - IntPtr p = GCHandle.ToIntPtr(gch); - - wsmanPinvokeStatic.WSManPluginRegisterShutdownCallback( - requestDetails.unmanagedHandle, - WSManPluginManagedEntryWrapper.workerPtrs.UnmanagedStruct.wsManPluginShutdownCallbackNative, - p); - } - + ClrFacade.SetSafeWaitHandle(eventWaitHandle, safeWaitHandle); mgdShellSession.registeredShutDownWaitHandle = ThreadPool.RegisterWaitForSingleObject( - eventWaitHandle, - new WaitOrTimerCallback(WSManPluginManagedEntryWrapper.PSPluginOperationShutdownCallback), - context, - -1, // INFINITE - true); // TODO: Do I need to worry not being able to set missing WT_TRANSFER_IMPERSONATION? + eventWaitHandle, + new WaitOrTimerCallback(WSManPluginManagedEntryWrapper.PSPluginOperationShutdownCallback), + context, + -1, // INFINITE + true); // TODO: Do I need to worry not being able to set missing WT_TRANSFER_IMPERSONATION? if (null == mgdShellSession.registeredShutDownWaitHandle) { isRegisterWaitForSingleObjectSucceeded = false; } } - + if (!isRegisterWaitForSingleObjectSucceeded) { mgdShellSession.registeredShutdownNotification = 0; WSManPluginInstance.ReportWSManOperationComplete( - requestDetails, + requestDetails, WSManPluginErrorCodes.ShutdownRegistrationFailed); DeleteFromActiveShellSessions(requestDetails.unmanagedHandle); return; @@ -439,7 +410,6 @@ namespace System.Management.Automation.Remoting { mgdShellSession.SendOneItemToSessionHelper(convertedBase64, WSManPluginConstants.SupportedInputStream); } - } catch(System.Exception e) { @@ -470,12 +440,12 @@ namespace System.Management.Automation.Remoting /// internal void CloseShellOperation( WSManPluginOperationShutdownContext context) - { + { PSEtwLog.LogAnalyticInformational(PSEventId.ServerCloseOperation, PSOpcode.Disconnect, PSTask.None, PSKeyword.ManagedPlugin | PSKeyword.UseAlwaysAnalytic, - ((IntPtr)context.shellContext).ToString(), - ((IntPtr)context.commandContext).ToString(), + ((IntPtr)context.shellContext).ToString(), + ((IntPtr)context.commandContext).ToString(), context.isReceiveOperation.ToString()); WSManPluginShellSession mgdShellSession = GetFromActiveShellSessions(context.shellContext); diff --git a/src/System.Management.Automation/engine/remoting/fanin/WSManPluginFacade.cs b/src/System.Management.Automation/engine/remoting/fanin/WSManPluginFacade.cs index b2143f8f6..0a5f8d517 100644 --- a/src/System.Management.Automation/engine/remoting/fanin/WSManPluginFacade.cs +++ b/src/System.Management.Automation/engine/remoting/fanin/WSManPluginFacade.cs @@ -97,13 +97,6 @@ namespace System.Management.Automation.Remoting [MarshalAs(UnmanagedType.LPWStr)] string commandLine, IntPtr arguments); - /// - /// Delegate that is passed to native layer for callback on operation shutdown notifications - /// - /// IntPtr - delegate void WSMPluginOperationShutdownDelegate( - IntPtr shutdownContext); - /// /// /// @@ -178,27 +171,27 @@ namespace System.Management.Automation.Remoting bool timedOut); /// - /// + /// /// /// PVOID delegate void WSMShutdownPluginDelegate( IntPtr pluginContext); /// - /// + /// /// internal sealed class WSManPluginEntryDelegates : IDisposable { #region Private Members - // Holds the delegate pointers in a structure that has identical layout to the native structure. + // Holds the delegate pointers in a structure that has identical layout to the native structure. private WSManPluginEntryDelegatesInternal unmanagedStruct = new WSManPluginEntryDelegatesInternal(); internal WSManPluginEntryDelegatesInternal UnmanagedStruct { get { return unmanagedStruct; } } - // Flag: Has Dispose already been called? + // Flag: Has Dispose already been called? private bool disposed = false; /// @@ -213,7 +206,6 @@ namespace System.Management.Automation.Remoting private GCHandle pluginSignalGCHandle; private GCHandle pluginConnectGCHandle; private GCHandle shutdownPluginGCHandle; - private GCHandle WSMPluginOperationShutdownGCHandle; #endregion @@ -326,16 +318,10 @@ namespace System.Management.Automation.Remoting this.shutdownPluginGCHandle = GCHandle.Alloc(shutdownPlugin); unmanagedStruct.wsManPluginShutdownPluginCallbackNative = Marshal.GetFunctionPointerForDelegate(shutdownPlugin); } - if(!Platform.IsWindows) - { - WSMPluginOperationShutdownDelegate pluginShutDownDelegate = new WSMPluginOperationShutdownDelegate(WSManPluginManagedEntryWrapper.WSManPSShutdown); - this.WSMPluginOperationShutdownGCHandle = GCHandle.Alloc(pluginShutDownDelegate); - unmanagedStruct.wsManPluginShutdownCallbackNative = Marshal.GetFunctionPointerForDelegate(pluginShutDownDelegate); - } } /// - /// + /// /// private void CleanUpDelegates() { @@ -351,10 +337,6 @@ namespace System.Management.Automation.Remoting this.pluginSignalGCHandle.Free(); this.pluginConnectGCHandle.Free(); this.shutdownPluginGCHandle.Free(); - if(!Platform.IsWindows) - { - this.WSMPluginOperationShutdownGCHandle.Free(); - } } } @@ -414,18 +396,11 @@ namespace System.Management.Automation.Remoting internal IntPtr wsManPluginSignalCallbackNative; /// - /// WSManPluginConnectCallbackNative + /// WSManPluginConnectCallbackNative /// [SuppressMessage("Microsoft.Reliability", "CA2006:UseSafeHandleToEncapsulateNativeResources")] internal IntPtr wsManPluginConnectCallbackNative; - - /// - /// WSManPluginCommandCallbackNative - /// - [SuppressMessage("Microsoft.Reliability", "CA2006:UseSafeHandleToEncapsulateNativeResources")] - internal IntPtr wsManPluginShutdownCallbackNative; - - } + } } /// @@ -442,7 +417,7 @@ namespace System.Management.Automation.Remoting /// /// Immutable container that holds the delegates and their unmanaged pointers. /// - internal static WSManPluginEntryDelegates workerPtrs = new WSManPluginEntryDelegates(); + private static WSManPluginEntryDelegates workerPtrs = new WSManPluginEntryDelegates(); #region Managed Entry Points @@ -624,19 +599,6 @@ namespace System.Management.Automation.Remoting WSManPluginInstance.PerformWSManPluginCommand(pluginContext, requestDetails, flags, shellContext, commandLine, arguments); } - /// - /// Operation shutdown notification that was registered with the native layer for each of the shellCreate operations. - /// - /// IntPtr - public static void WSManPSShutdown( - IntPtr shutdownContext) - { - GCHandle gch = GCHandle.FromIntPtr(shutdownContext); - EventWaitHandle eventHandle = (EventWaitHandle) gch.Target; - eventHandle.Set(); - gch.Free(); - } - /// /// /// @@ -752,9 +714,9 @@ namespace System.Management.Automation.Remoting WSManPluginInstance.PerformWSManPluginSignal(pluginContext, requestDetails, flags, shellContext, commandContext, code); } - + /// - /// Callback used to register with thread pool to notify when a plugin operation shuts down. + /// Callback used to register with thread pool to notify when a plugin operation shutsdown. /// Conforms to: /// public delegate void WaitOrTimerCallback( Object state, bool timedOut ) /// @@ -775,7 +737,7 @@ namespace System.Management.Automation.Remoting WSManPluginInstance.PerformCloseOperation(context); } - + #endregion } diff --git a/src/System.Management.Automation/engine/remoting/fanin/WSManPluginShellSession.cs b/src/System.Management.Automation/engine/remoting/fanin/WSManPluginShellSession.cs index 41913739b..8a21e1adf 100644 --- a/src/System.Management.Automation/engine/remoting/fanin/WSManPluginShellSession.cs +++ b/src/System.Management.Automation/engine/remoting/fanin/WSManPluginShellSession.cs @@ -265,7 +265,7 @@ namespace System.Management.Automation.Remoting //RACE TO BE FIXED - As soon as this API is called, WinRM service will send CommandResponse back and Signal is expected anytime // If Signal comes and executes before registering the notification handle, cleanup will be messed result = WSManNativeApi.WSManPluginReportContext(creationRequestDetails.unmanagedHandle, 0, creationRequestDetails.unmanagedHandle); - if (Platform.IsWindows && (WSManPluginConstants.ExitCodeSuccess == result)) + if (WSManPluginConstants.ExitCodeSuccess == result) { registeredShutdownNotification = 1; diff --git a/src/System.Management.Automation/engine/remoting/fanin/WSManPluginTransportManager.cs b/src/System.Management.Automation/engine/remoting/fanin/WSManPluginTransportManager.cs index 7c49a68bd..757d774a5 100644 --- a/src/System.Management.Automation/engine/remoting/fanin/WSManPluginTransportManager.cs +++ b/src/System.Management.Automation/engine/remoting/fanin/WSManPluginTransportManager.cs @@ -332,24 +332,22 @@ namespace System.Management.Automation.Remoting isRequestPending = true; this.requestDetails = requestDetails; - if (Platform.IsWindows) - { - // Wrap the provided handle so it can be passed to the registration function - SafeWaitHandle safeWaitHandle = new SafeWaitHandle(requestDetails.shutdownNotificationHandle, false); // Owned by WinRM - EventWaitHandle eventWaitHandle = new EventWaitHandle(false, EventResetMode.AutoReset); - ClrFacade.SetSafeWaitHandle(eventWaitHandle, safeWaitHandle); + // Wrap the provided handle so it can be passed to the registration function + SafeWaitHandle safeWaitHandle = new SafeWaitHandle(requestDetails.shutdownNotificationHandle, false); // Owned by WinRM + EventWaitHandle eventWaitHandle = new EventWaitHandle(false, EventResetMode.AutoReset); + ClrFacade.SetSafeWaitHandle(eventWaitHandle, safeWaitHandle); - this.registeredShutDownWaitHandle = ThreadPool.RegisterWaitForSingleObject( - eventWaitHandle, - new WaitOrTimerCallback(WSManPluginManagedEntryWrapper.PSPluginOperationShutdownCallback), - shutDownContext, - -1, // INFINITE - true); // TODO: Do I need to worry not being able to set missing WT_TRANSFER_IMPERSONATION? - if (null == this.registeredShutDownWaitHandle) - { - isRegisterWaitForSingleObjectSucceeded = false; - } + this.registeredShutDownWaitHandle = ThreadPool.RegisterWaitForSingleObject( + eventWaitHandle, + new WaitOrTimerCallback(WSManPluginManagedEntryWrapper.PSPluginOperationShutdownCallback), + shutDownContext, + -1, // INFINITE + true); // TODO: Do I need to worry not being able to set missing WT_TRANSFER_IMPERSONATION? + if (null == this.registeredShutDownWaitHandle) + { + isRegisterWaitForSingleObjectSucceeded = false; } + // release thread waiting to send data to the client. waitHandle.Set(); } diff --git a/src/System.Management.Automation/engine/remoting/server/ServerPowerShellDriver.cs b/src/System.Management.Automation/engine/remoting/server/ServerPowerShellDriver.cs index 0f1e57ede..efc2c3658 100644 --- a/src/System.Management.Automation/engine/remoting/server/ServerPowerShellDriver.cs +++ b/src/System.Management.Automation/engine/remoting/server/ServerPowerShellDriver.cs @@ -336,24 +336,17 @@ namespace System.Management.Automation // Flow the impersonation policy to pipeline execution thread // only if the current thread is impersonated (Delegation is // also a kind of impersonation). - if (Platform.IsWindows) + WindowsIdentity currentThreadIdentity = WindowsIdentity.GetCurrent(); + switch (currentThreadIdentity.ImpersonationLevel) { - WindowsIdentity currentThreadIdentity = WindowsIdentity.GetCurrent(); - switch (currentThreadIdentity.ImpersonationLevel) - { - case TokenImpersonationLevel.Impersonation: - case TokenImpersonationLevel.Delegation: - settings.FlowImpersonationPolicy = true; - break; - default: - settings.FlowImpersonationPolicy = false; - break; - } - } - else - { - settings.FlowImpersonationPolicy = false; + case TokenImpersonationLevel.Impersonation: + case TokenImpersonationLevel.Delegation: + settings.FlowImpersonationPolicy = true; + break; + default: + settings.FlowImpersonationPolicy = false; + break; } settings.AddToHistory = addToHistory; diff --git a/src/System.Management.Automation/engine/remoting/server/serverremotesession.cs b/src/System.Management.Automation/engine/remoting/server/serverremotesession.cs index 7fd08b9ec..616e7f485 100644 --- a/src/System.Management.Automation/engine/remoting/server/serverremotesession.cs +++ b/src/System.Management.Automation/engine/remoting/server/serverremotesession.cs @@ -170,11 +170,8 @@ namespace System.Management.Automation.Remoting _senderInfo = senderInfo; _configProviderId = configurationProviderId; _initParameters = initializationParameters; - if (Platform.IsWindows) - { - _cryptoHelper = (PSRemotingCryptoHelperServer)transportManager.CryptoHelper; - _cryptoHelper.Session = this; - } + _cryptoHelper = (PSRemotingCryptoHelperServer)transportManager.CryptoHelper; + _cryptoHelper.Session = this; _context = new ServerRemoteSessionContext(); _sessionDSHandler = new ServerRemoteSessionDSHandlerlImpl(this, transportManager); diff --git a/src/System.Management.Automation/engine/runtime/Binding/Binders.cs b/src/System.Management.Automation/engine/runtime/Binding/Binders.cs index 08d2f8e97..6ac4d4f55 100644 --- a/src/System.Management.Automation/engine/runtime/Binding/Binders.cs +++ b/src/System.Management.Automation/engine/runtime/Binding/Binders.cs @@ -554,7 +554,6 @@ namespace System.Management.Automation.Language { return (errorSuggestion ?? NullResult(target)).WriteToDebugLog(this); } - #if !CORECLR // In CORECLR System.Data.DataTable does not have the DataRowCollection IEnumerable, so disabling code. if (targetValue is DataTable) @@ -584,7 +583,6 @@ namespace System.Management.Automation.Language GetRestrictions(target))).WriteToDebugLog(this); } #endif - if (IsComObject(targetValue)) { // Pretend that all com objects are enumerable, even if they aren't. We do this because it's technically impossible @@ -672,23 +670,13 @@ namespace System.Management.Automation.Language return (result == DynamicMetaObjectExtensions.FakeError) ? null : result; } - // This is to reduce the runtime overhead of the feature query - private static readonly TypeInfo ComObjectTypeInfo = GetComObjectType(); - - private static TypeInfo GetComObjectType() - { -#if UNIX - return null; -#else - return typeof(object).GetTypeInfo().Assembly.GetType("System.__ComObject").GetTypeInfo(); -#endif - } + private static readonly TypeInfo ComObjectTypeInfo = typeof(object).GetTypeInfo().Assembly.GetType("System.__ComObject").GetTypeInfo(); internal static bool IsComObject(object obj) { // we can't use System.Runtime.InteropServices.Marshal.IsComObject(obj) since it doesn't work in partial trust obj = PSObject.Base(obj); - return obj != null && ComObjectTypeInfo != null && ComObjectTypeInfo.IsAssignableFrom(obj.GetType().GetTypeInfo()); + return obj != null && ComObjectTypeInfo.IsAssignableFrom(obj.GetType().GetTypeInfo()); } private static IEnumerator AutomationNullRule(CallSite site, object obj) diff --git a/src/System.Management.Automation/help/HelpCommands.cs b/src/System.Management.Automation/help/HelpCommands.cs index a78657c2b..a9c2d18a6 100644 --- a/src/System.Management.Automation/help/HelpCommands.cs +++ b/src/System.Management.Automation/help/HelpCommands.cs @@ -699,17 +699,9 @@ namespace Microsoft.PowerShell.Commands { this.WriteVerbose(string.Format(CultureInfo.InvariantCulture, HelpDisplayStrings.OnlineHelpUri, uriToLaunch.OriginalString)); System.Diagnostics.Process browserProcess = new System.Diagnostics.Process(); - -#if UNIX - browserProcess.StartInfo.FileName = Platform.IsLinux ? "xdg-open" : /* OS X */ "open"; - browserProcess.StartInfo.Arguments = uriToLaunch.OriginalString; - browserProcess.Start(); -#elif CORECLR - throw new PlatformNotSupportedException(); -#else + browserProcess.StartInfo.UseShellExecute = true; browserProcess.StartInfo.FileName = uriToLaunch.OriginalString; browserProcess.Start(); -#endif } catch (InvalidOperationException ioe) { diff --git a/src/System.Management.Automation/help/HelpNotFoundException.cs b/src/System.Management.Automation/help/HelpNotFoundException.cs index 3cf3a2b19..5b8771886 100644 --- a/src/System.Management.Automation/help/HelpNotFoundException.cs +++ b/src/System.Management.Automation/help/HelpNotFoundException.cs @@ -62,11 +62,7 @@ namespace Microsoft.PowerShell.Commands /// private void CreateErrorRecord() { - string errMessage = string.Format(HelpErrors.HelpNotFound, _helpTopic); - - // Don't do ParentContainsErrorRecordException(this), as this causes recursion, and creates a - // segmentation fault on Linux - _errorRecord = new ErrorRecord(new ParentContainsErrorRecordException(errMessage), "HelpNotFound", ErrorCategory.ResourceUnavailable, null); + _errorRecord = new ErrorRecord(new ParentContainsErrorRecordException(this), "HelpNotFound", ErrorCategory.ResourceUnavailable, null); _errorRecord.ErrorDetails = new ErrorDetails(typeof(HelpNotFoundException).GetTypeInfo().Assembly, "HelpErrors", "HelpNotFound", _helpTopic); } diff --git a/src/System.Management.Automation/logging/MshLog.cs b/src/System.Management.Automation/logging/MshLog.cs index 52279d855..cd2c5c1f2 100644 --- a/src/System.Management.Automation/logging/MshLog.cs +++ b/src/System.Management.Automation/logging/MshLog.cs @@ -171,8 +171,6 @@ namespace System.Management.Automation } #endif Collection providers = new Collection(); - // Porting note: Linux does not support ETW -#if !UNIX try { #if !CORECLR //TODO:CORECLR EventLogLogProvider not handled yet @@ -197,7 +195,7 @@ namespace System.Management.Automation // when running as non-admin user. In that case, we will default // to dummy log. } -#endif + providers.Add(new DummyLogProvider()); return providers; } diff --git a/src/System.Management.Automation/logging/eventlog/EventLogLogProvider.cs b/src/System.Management.Automation/logging/eventlog/EventLogLogProvider.cs index 90ffa6e21..ccd27ac50 100644 --- a/src/System.Management.Automation/logging/eventlog/EventLogLogProvider.cs +++ b/src/System.Management.Automation/logging/eventlog/EventLogLogProvider.cs @@ -40,7 +40,7 @@ namespace System.Management.Automation _eventLog = new EventLog(); _eventLog.Source = source; - _resourceManager = new ResourceManager("System.Management.Automation.resources.Logging", System.Reflection.Assembly.GetExecutingAssembly()); + _resourceManager = new ResourceManager("Logging", System.Reflection.Assembly.GetExecutingAssembly()); } internal string SetupEventSource(string shellId) diff --git a/src/System.Management.Automation/namespaces/EnvironmentProvider.cs b/src/System.Management.Automation/namespaces/EnvironmentProvider.cs index 7ad67c3b3..9a03e76ae 100644 --- a/src/System.Management.Automation/namespaces/EnvironmentProvider.cs +++ b/src/System.Management.Automation/namespaces/EnvironmentProvider.cs @@ -190,15 +190,8 @@ namespace Microsoft.PowerShell.Commands /// internal override IDictionary GetSessionStateTable () { - // Environment variables are case-sensitive on Unix and - // case-insensitive on Windows -#if UNIX - Dictionary providerTable = - new Dictionary(StringComparer.Ordinal); -#else Dictionary providerTable = new Dictionary(StringComparer.OrdinalIgnoreCase); -#endif // The environment variables returns a dictionary of keys and values that are // both strings. We want to return a dictionary with the key as a string and diff --git a/src/System.Management.Automation/namespaces/FileSystemContentStream.cs b/src/System.Management.Automation/namespaces/FileSystemContentStream.cs index 8539cb77e..97cf6ddb1 100644 --- a/src/System.Management.Automation/namespaces/FileSystemContentStream.cs +++ b/src/System.Management.Automation/namespaces/FileSystemContentStream.cs @@ -1192,10 +1192,8 @@ namespace Microsoft.PowerShell.Commands if (_singleByteCharSet != null) return (bool)_singleByteCharSet; - // Porting note: only UTF-8 is supported on Linux, which is not an SBCS - if ((_currentEncoding.Equals(_oemEncoding) || - _currentEncoding.Equals(_defaultAnsiEncoding)) - && Platform.IsWindows) + if (_currentEncoding.Equals(_oemEncoding) || + _currentEncoding.Equals(_defaultAnsiEncoding)) { NativeMethods.CPINFO cpInfo; if (NativeMethods.GetCPInfo((uint)_currentEncoding.CodePage, out cpInfo) && diff --git a/src/System.Management.Automation/namespaces/FileSystemProvider.cs b/src/System.Management.Automation/namespaces/FileSystemProvider.cs index 9b8120510..a3c067d3a 100644 --- a/src/System.Management.Automation/namespaces/FileSystemProvider.cs +++ b/src/System.Management.Automation/namespaces/FileSystemProvider.cs @@ -405,7 +405,7 @@ namespace Microsoft.PowerShell.Commands } // -Persist switch parameter is supported only for Network paths. - if (drive.Persist && !PathIsNetworkPath(drive.Root)) + if (drive.Persist && !NativeMethods.PathIsNetworkPath(drive.Root)) { ErrorRecord er = new ErrorRecord(new NotSupportedException(FileSystemProviderStrings.PersistNotSupported), "DriveRootNotNetworkPath", ErrorCategory.InvalidArgument, drive); ThrowTerminatingError(er); @@ -488,19 +488,6 @@ namespace Microsoft.PowerShell.Commands /// /// The PSDrive infor that would be used to create a new PS drive. private void MapNetworkDrive(PSDriveInfo drive) - { - // Porting note: mapped network drives are only supported on Windows - if (Platform.IsWindows) - { - WinMapNetworkDrive(drive); - } - else - { - throw new PlatformNotSupportedException(); - } - } - - private void WinMapNetworkDrive(PSDriveInfo drive) { if (drive != null && !string.IsNullOrEmpty(drive.Root)) { @@ -591,7 +578,7 @@ namespace Microsoft.PowerShell.Commands /// private bool IsNetworkMappedDrive(PSDriveInfo drive) { - bool shouldMapNetworkDrive = (drive != null && !string.IsNullOrEmpty(drive.Root) && PathIsNetworkPath(drive.Root)) && + bool shouldMapNetworkDrive = (drive != null && !string.IsNullOrEmpty(drive.Root) && NativeMethods.PathIsNetworkPath(drive.Root)) && (drive.Persist || (drive.Credential != null && !drive.Credential.Equals(PSCredential.Empty))); return shouldMapNetworkDrive; @@ -607,15 +594,6 @@ namespace Microsoft.PowerShell.Commands /// protected override PSDriveInfo RemoveDrive(PSDriveInfo drive) { -#if UNIX - return drive; -#else - return WinRemoveDrive(drive); -#endif - } - - private PSDriveInfo WinRemoveDrive(PSDriveInfo drive) - { if (IsNetworkMappedDrive(drive)) { const int CONNECT_UPDATE_PROFILE = 0x00000001; @@ -681,15 +659,6 @@ namespace Microsoft.PowerShell.Commands /// internal static string GetUNCForNetworkDrive(string driveName) { -#if UNIX - return driveName; -#else - return WinGetUNCForNetworkDrive(driveName); -#endif - } - - private static string WinGetUNCForNetworkDrive(string driveName) - { string uncPath = null; if (!string.IsNullOrEmpty(driveName) && driveName.Length == 1) { @@ -739,15 +708,6 @@ namespace Microsoft.PowerShell.Commands /// internal static string GetSubstitutedPathForNetworkDosDevice(string driveName) { -#if UNIX - throw new PlatformNotSupportedException(); -#else - return WinGetSubstitutedPathForNetworkDosDevice(driveName); -#endif - } - - private static string WinGetSubstitutedPathForNetworkDosDevice(string driveName) - { string associatedPath = null; if (!string.IsNullOrEmpty(driveName) && driveName.Length == 1) { @@ -882,50 +842,39 @@ namespace Microsoft.PowerShell.Commands break; } - // cover everything by the try-catch block, because some of the - // DriveInfo properties may throw exceptions + string newDriveName = newDrive.Name.Substring(0, 1); + + string description = String.Empty; + string root = newDrive.Name; + string displayRoot = null; + + if (newDrive.DriveType == DriveType.Fixed) + { + try + { + description = newDrive.VolumeLabel; + } + // trying to read the volume label may cause an + // IOException or SecurityException. Just default + // to an empty description. + catch (IOException) + { + } + catch (System.Security.SecurityException) + { + } + catch (System.UnauthorizedAccessException) + { + } + } + + if (newDrive.DriveType == DriveType.Network) + { + displayRoot = GetRootPathForNetworkDriveOrDosDevice(newDrive); + } + try { - string newDriveName = newDrive.Name.Substring(0, 1); - - string description = String.Empty; - string root = newDrive.Name; - string displayRoot = null; - - if (newDrive.DriveType == DriveType.Fixed) - { - try - { - description = newDrive.VolumeLabel; - } - // trying to read the volume label may cause an - // IOException or SecurityException. Just default - // to an empty description. - catch (IOException) - { - } - catch (System.Security.SecurityException) - { - } - catch (System.UnauthorizedAccessException) - { - } - } - - if (newDrive.DriveType == DriveType.Network) - { - // Platform notes: This is important because certain mount - // points on non-Windows are enumerated as drives by .NET, but - // the platform itself then has no real network drive support - // as required by this context. Solution: check for network - // drive support before using it. -#if UNIX - continue; -#else - displayRoot = GetRootPathForNetworkDriveOrDosDevice(newDrive); -#endif - } - if (newDrive.DriveType == DriveType.Fixed) { if (!newDrive.RootDirectory.Exists) @@ -936,29 +885,6 @@ namespace Microsoft.PowerShell.Commands root = newDrive.RootDirectory.FullName; } -#if UNIX - // Porting notes: On platforms with single root filesystems, only - // add the filesystem with the root "/" to the initial drive list, - // otherwise path handling will not work correctly because there - // is no : available to separate the filesystems from each other - if (root != StringLiterals.DefaultPathSeparatorString) - continue; -#endif - - // Porting notes: On non-windows platforms .net can report two - // drives with the same root, make sure to only add one of those - bool skipDuplicate = false; - foreach (PSDriveInfo driveInfo in results) - { - if (driveInfo.Root == root) - { - skipDuplicate = true; - break; - } - } - if (skipDuplicate) - continue; - // Create a new VirtualDrive for each logical drive PSDriveInfo newPSDriveInfo = new PSDriveInfo( @@ -980,18 +906,9 @@ namespace Microsoft.PowerShell.Commands { newPSDriveInfo.IsAutoMounted = true; } - - // Porting notes: on the non-Windows platforms, the drive never - // uses : as a separator between drive and path - if (!Platform.IsWindows) - { - newPSDriveInfo.VolumeSeparatedByColon = false; - } - results.Add(newPSDriveInfo); } - // If there are issues accessing properties of the DriveInfo, do - // not add the drive + // If we can't access the root itself, don't add the drive catch (IOException) { } @@ -1322,18 +1239,7 @@ namespace Microsoft.PowerShell.Commands if (ShouldProcess(resource, action)) { - System.Diagnostics.Process invokeProcess = new System.Diagnostics.Process(); - -#if UNIX - invokeProcess.StartInfo.FileName = Platform.IsLinux ? "xdg-open" : /* OS X */ "open"; - invokeProcess.StartInfo.Arguments = path; - invokeProcess.Start(); -#elif CORECLR - throw new PlatformNotSupportedException(); -#else - invokeProcess.StartInfo.FileName = path; - invokeProcess.Start(); -#endif + System.Diagnostics.Process.Start(path); } } // InvokeDefaultAction @@ -1507,13 +1413,6 @@ namespace Microsoft.PowerShell.Commands { DirectoryInfo directory = new DirectoryInfo(path); - if (!Platform.IsWindows && Platform.NonWindowsIsSymLink(directory)) - { - // For Linux, treat symlink to directories like a file - WriteItemObject(directory, path, false); - return; - } - // Enumerate the directory Dir(directory, recurse, depth, nameOnly, returnContainers); } @@ -1641,10 +1540,7 @@ namespace Microsoft.PowerShell.Commands // Write out the items foreach (IEnumerable childList in target) { - // On some systems, this is already sorted. For consistency, always sort again. - IEnumerable sortedChildList = childList.OrderBy(c => c.Name, StringComparer.CurrentCultureIgnoreCase); - - foreach(FileSystemInfo filesystemInfo in sortedChildList) + foreach(FileSystemInfo filesystemInfo in childList) { // Making sure to obey the StopProcessing. if (Stopping) @@ -1827,10 +1723,7 @@ namespace Microsoft.PowerShell.Commands mode[3] = (fileInfo.Attributes & FileAttributes.Hidden) == FileAttributes.Hidden ? 'h' : '-'; mode[4] = (fileInfo.Attributes & FileAttributes.System) == FileAttributes.System ? 's' : '-'; // Mark the last bit as a "l" if it's a reparsepoint (symbolic link or junction) - // Porting note: these need to be handled specially - bool isReparsePoint = InternalSymbolicLinkLinkCodeMethods.IsReparsePoint(fileInfo); - bool isHardLink = InternalSymbolicLinkLinkCodeMethods.IsHardLink(fileInfo); - mode[5] = isReparsePoint || isHardLink ? 'l' : '-'; + mode[5] = (fileInfo.Attributes & FileAttributes.ReparsePoint) == FileAttributes.ReparsePoint ? 'l' : '-'; return new string(mode); } @@ -2124,14 +2017,9 @@ namespace Microsoft.PowerShell.Commands bool exists = false; - // It is legal to create symbolic links to non-existing targets on - // both Windows and Linux. It is not legal to create hard links to - // non-existing targets on either Windows or Linux. try { - exists = (itemType == ItemType.SymbolicLink) - ? true // pretend it exists if we're making a symbolic link - : CheckItemExists(strTargetPath, out isDirectory); + exists = CheckItemExists(strTargetPath, out isDirectory); } catch (Exception e) { @@ -2214,25 +2102,12 @@ namespace Microsoft.PowerShell.Commands if(itemType == ItemType.SymbolicLink) { - if (Platform.IsWindows) - { - success = WinCreateSymbolicLink(path,strTargetPath,isDirectory); - } - else - { - success = Platform.NonWindowsCreateSymbolicLink(path,strTargetPath); - } + int created = NativeMethods.CreateSymbolicLink(path, strTargetPath, (isDirectory ? 1 : 0)); + success = (created == 1) ? true : false; } else if(itemType == ItemType.HardLink) { - if (Platform.IsWindows) - { - success = WinCreateHardLink(path,strTargetPath); - } - else - { - success = Platform.NonWindowsCreateHardLink(path,strTargetPath); - } + success = NativeMethods.CreateHardLink(path, strTargetPath, IntPtr.Zero); } if (!success) @@ -2375,7 +2250,7 @@ namespace Microsoft.PowerShell.Commands try { - bool junctionCreated = WinCreateJunction(path, strTargetPath); + bool junctionCreated = InternalSymbolicLinkLinkCodeMethods.CreateJunction(path, strTargetPath); if (junctionCreated) { @@ -2421,25 +2296,6 @@ namespace Microsoft.PowerShell.Commands } } // NewItem - private static bool WinCreateSymbolicLink(string path, string strTargetPath, bool isDirectory) - { - int created = NativeMethods.CreateSymbolicLink(path, strTargetPath, (isDirectory ? 1 : 0)); - bool success = (created == 1) ? true : false; - return success; - } - - private static bool WinCreateHardLink(string path, string strTargetPath) - { - bool success = NativeMethods.CreateHardLink(path, strTargetPath, IntPtr.Zero); - return success; - } - - private static bool WinCreateJunction(string path, string strTargetPath) - { - bool junctionCreated = InternalSymbolicLinkLinkCodeMethods.CreateJunction(path, strTargetPath); - return junctionCreated; - } - /// /// Checks if the item exists and throws exception on access. /// @@ -2857,7 +2713,7 @@ namespace Microsoft.PowerShell.Commands } //if this is a reparse point and force is not specified then warn user but dont remove the directory. - if (Platform.IsWindows && ((directory.Attributes & FileAttributes.ReparsePoint) != 0) && !Force) + if (((directory.Attributes & FileAttributes.ReparsePoint) != 0) && !Force) { String error = StringUtil.Format(FileSystemProviderStrings.DirectoryReparsePoint, directory.FullName); Exception e = new IOException(error); @@ -4767,17 +4623,10 @@ namespace Microsoft.PowerShell.Commands return parentPath; } // GetParentPath - // Note: we don't use IO.Path.IsPathRooted as this deals with "invalid" i.e. unnormalized paths private static bool IsAbsolutePath(string path) { bool result = false; - // check if we're on a single root filesystem and it's an absolute path - if (LocationGlobber.IsSingleFileSystemAbsolutePath(path)) - { - return true; - } - // Find the drive separator int index = path.IndexOf(':'); @@ -6962,51 +6811,6 @@ namespace Microsoft.PowerShell.Commands internal static int SafeGetFileAttributes(string path) { -#if UNIX - System.IO.FileAttributes attr = System.IO.File.GetAttributes(path); - - int result = 0; - if ((attr & FileAttributes.Archive) == FileAttributes.Archive) - result |= 0x20; - if ((attr & FileAttributes.Compressed) == FileAttributes.Compressed) - result |= 0x800; - if ((attr & FileAttributes.Device) == FileAttributes.Device) - result |= 0x40; - if ((attr & FileAttributes.Directory) == FileAttributes.Directory) - result |= 0x10; - if ((attr & FileAttributes.Encrypted) == FileAttributes.Encrypted) - result |= 0x4000; - if ((attr & FileAttributes.Hidden) == FileAttributes.Hidden) - result |= 0x2; - if ((attr & FileAttributes.IntegrityStream) == FileAttributes.IntegrityStream) - result |= 0x8000; - if ((attr & FileAttributes.Normal) == FileAttributes.Normal) - result |= 0x80; - if ((attr & FileAttributes.NoScrubData) == FileAttributes.NoScrubData) - result |= 0x20000; - if ((attr & FileAttributes.NotContentIndexed) == FileAttributes.NotContentIndexed) - result |= 0x2000; - if ((attr & FileAttributes.Offline) == FileAttributes.Offline) - result |= 0x1000; - if ((attr & FileAttributes.ReadOnly) == FileAttributes.ReadOnly) - result |= 0x1; - if ((attr & FileAttributes.ReparsePoint) == FileAttributes.ReparsePoint) - result |= 0x400; - if ((attr & FileAttributes.SparseFile) == FileAttributes.SparseFile) - result |= 0x200; - if ((attr & FileAttributes.System) == FileAttributes.System) - result |= 0x4; - if ((attr & FileAttributes.Temporary) == FileAttributes.Temporary) - result |= 0x100; - - return result; -#else - return WinSafeGetFileAttributes(path); -#endif - } - - internal static int WinSafeGetFileAttributes(string path) - { int result = Utils.NativeMethods.GetFileAttributes(path); if (result == -1) { @@ -7056,26 +6860,6 @@ namespace Microsoft.PowerShell.Commands } } - /// - /// The API 'PathIsNetworkPath' is not available in CoreSystem. - /// This implementation is based on the 'PathIsNetworkPath' API. - /// - /// - /// - internal static bool PathIsNetworkPath(string path) - { -#if UNIX - return false; -#else - return WinPathIsNetworkPath(path); -#endif - } - - internal static bool WinPathIsNetworkPath(string path) - { - return NativeMethods.PathIsNetworkPath(path); // call the native method - } - static class NativeMethods { /// @@ -7785,7 +7569,7 @@ namespace Microsoft.PowerShell.Commands private bool wait; /// - /// When the Raw switch is present, we don't do any breaks on newlines, + /// When the Raw switch is present, we dont do any breaks on newlines, /// and only emit one object to the pipeline: all of the content. /// [Parameter] @@ -8066,17 +7850,15 @@ namespace Microsoft.PowerShell.Commands if (fileSysInfo != null) { - if (Platform.IsWindows) + using (SafeFileHandle handle = OpenReparsePoint(fileSysInfo.FullName, FileDesiredAccess.GenericRead)) { - using (SafeFileHandle handle = OpenReparsePoint(fileSysInfo.FullName, FileDesiredAccess.GenericRead)) - { - string linkTarget = InternalGetTarget(handle); + string linkTarget = InternalGetTarget(handle); - if (linkTarget != null) - return (new string[] { linkTarget }); - } + if (linkTarget != null) + return (new string[] { linkTarget }); } + //return InternalGetTarget(fileSysInfo.FullName).ToArray(); return InternalGetTarget(fileSysInfo.FullName); } else @@ -8094,7 +7876,7 @@ namespace Microsoft.PowerShell.Commands if (fileSysInfo != null) { - return InternalGetLinkType(fileSysInfo); + return InternalGetLinkType(fileSysInfo.FullName); } else return null; @@ -8103,15 +7885,6 @@ namespace Microsoft.PowerShell.Commands private static List InternalGetTarget(string filePath) { var links = new List(); - if (!Platform.IsWindows) - { - string link = Platform.NonWindowsInternalGetTarget(filePath); - if (!String.IsNullOrEmpty(link)) - { - links.Add(link); - } - return links; - } #if !CORECLR //FindFirstFileName, FindNextFileName and FindClose are not available on Core Clr UInt32 linkStringLength = 0; @@ -8175,26 +7948,9 @@ namespace Microsoft.PowerShell.Commands return links; } - private static string InternalGetLinkType(FileSystemInfo fileInfo) - { - if (Platform.IsWindows) - { - return WinInternalGetLinkType(fileInfo.FullName); - } - else - { - return Platform.NonWindowsInternalGetLinkType(fileInfo); - } - } - [System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Reliability", "CA2001:AvoidCallingProblematicMethods")] - private static string WinInternalGetLinkType(string filePath) + private static string InternalGetLinkType(string filePath) { - if (!Platform.IsWindows) - { - throw new PlatformNotSupportedException(); - } - using (SafeFileHandle handle = OpenReparsePoint(filePath, FileDesiredAccess.GenericRead)) { int outBufferSize = ClrFacade.SizeOf(); @@ -8252,75 +8008,8 @@ namespace Microsoft.PowerShell.Commands } } - internal static bool IsHardLink(FileSystemInfo fileInfo) - { - if (Platform.IsWindows) - return WinIsHardLink(fileInfo); - else - return Platform.NonWindowsIsHardLink(fileInfo); - } - - internal static bool IsReparsePoint(FileSystemInfo fileInfo) - { - if (Platform.IsWindows) - { - // Note that this class also has a enum called FileAttributes, so use fully qualified name - return (fileInfo.Attributes & System.IO.FileAttributes.ReparsePoint) - == System.IO.FileAttributes.ReparsePoint; - } - else - { - return Platform.NonWindowsIsSymLink(fileInfo); - } - } - - internal static bool WinIsHardLink(FileSystemInfo fileInfo) - { - bool isHardLink = false; - - // only check for hard link if the item is not directory - if (!((fileInfo.Attributes & System.IO.FileAttributes.Directory) == System.IO.FileAttributes.Directory)) - { - IntPtr nativeHandle = InternalSymbolicLinkLinkCodeMethods.CreateFile( - fileInfo.FullName, - InternalSymbolicLinkLinkCodeMethods.FileDesiredAccess.GenericRead, - InternalSymbolicLinkLinkCodeMethods.FileShareMode.Read, - IntPtr.Zero, - InternalSymbolicLinkLinkCodeMethods.FileCreationDisposition.OpenExisting, - InternalSymbolicLinkLinkCodeMethods.FileAttributes.Normal, - IntPtr.Zero); - - using (SafeFileHandle handle = new SafeFileHandle(nativeHandle, true)) - { - bool success = false; - - try - { - handle.DangerousAddRef(ref success); - IntPtr dangerousHandle = handle.DangerousGetHandle(); - isHardLink = InternalSymbolicLinkLinkCodeMethods.IsHardLink(ref dangerousHandle); - } - finally - { - if (success) - handle.DangerousRelease(); - } - } - } - - return isHardLink; - } - - internal static bool IsHardLink(ref IntPtr handle) - { - if (Platform.IsWindows) - return WinIsHardLink(ref handle); - else - return Platform.NonWindowsIsHardLink(ref handle); - } - [System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Reliability", "CA2001:AvoidCallingProblematicMethods")] - internal static bool WinIsHardLink(ref IntPtr handle) + internal static bool IsHardLink(ref IntPtr handle) { BY_HANDLE_FILE_INFORMATION handleInfo; bool succeeded = InternalSymbolicLinkLinkCodeMethods.GetFileInformationByHandle(handle, out handleInfo); @@ -8339,20 +8028,8 @@ namespace Microsoft.PowerShell.Commands return false; } - private static string InternalGetTarget(SafeFileHandle handle) - { - if (Platform.IsWindows) - { - return WinInternalGetTarget(handle); - } - else - { - return Platform.NonWindowsInternalGetTarget(handle); - } - } - [System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Reliability", "CA2001:AvoidCallingProblematicMethods")] - private static string WinInternalGetTarget(SafeFileHandle handle) + private static string InternalGetTarget(SafeFileHandle handle) { int outBufferSize = ClrFacade.SizeOf(); @@ -8417,22 +8094,8 @@ namespace Microsoft.PowerShell.Commands } } - internal static bool CreateJunction(string path, string target) - { - // this is a purely Windows specific feature, no feature flag - // used for that reason - if (Platform.IsWindows) - { - return WinCreateJunction(path,target); - } - else - { - return false; - } - } - [System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Reliability", "CA2001:AvoidCallingProblematicMethods")] - private static bool WinCreateJunction(string path, string target) + internal static bool CreateJunction(string path, string target) { if (!String.IsNullOrEmpty(path)) { @@ -8505,20 +8168,6 @@ namespace Microsoft.PowerShell.Commands if (!String.IsNullOrEmpty(junctionPath)) { - if (!Platform.IsWindows) - { - // For non-Windows platform, treat it as a file. Just delete it. - try - { - File.Delete(junctionPath); - return true; - } - catch - { - return false; - } - } - using (SafeHandle handle = OpenReparsePoint(junctionPath, FileDesiredAccess.GenericWrite)) { bool success = false; @@ -8532,24 +8181,10 @@ namespace Microsoft.PowerShell.Commands IntPtr dangerousHandle = handle.DangerousGetHandle(); int bytesReturned; - // Do a FSCTL_GET_REPARSE_POINT first because the ReparseTag could be - // IO_REPARSE_TAG_MOUNT_POINT or IO_REPARSE_TAG_SYMLINK. - // Using the wrong one results in mismatched-tag error. - REPARSE_GUID_DATA_BUFFER junctionData = new REPARSE_GUID_DATA_BUFFER(); - ClrFacade.StructureToPtr(junctionData, outBuffer, false); - - result = DeviceIoControl(dangerousHandle, FSCTL_GET_REPARSE_POINT, IntPtr.Zero, 0, - outBuffer, inOutBufferSize, out bytesReturned, IntPtr.Zero); - if (!result) - { - int lastError = Marshal.GetLastWin32Error(); - throw new Win32Exception(lastError); - } - - junctionData = ClrFacade.PtrToStructure(outBuffer); junctionData.ReparseDataLength = 0; junctionData.DataBuffer = new char[MAX_REPARSE_SIZE]; + junctionData.ReparseTag = IO_REPARSE_TAG_MOUNT_POINT; ClrFacade.StructureToPtr(junctionData, inBuffer, false); @@ -8585,15 +8220,6 @@ namespace Microsoft.PowerShell.Commands private static SafeFileHandle OpenReparsePoint(string reparsePoint, FileDesiredAccess accessMode) { -#if UNIX - throw new PlatformNotSupportedException(); -#else - return WinOpenReparsePoint(reparsePoint,accessMode); -#endif - } - - private static SafeFileHandle WinOpenReparsePoint(string reparsePoint, FileDesiredAccess accessMode) - { IntPtr nativeHandle = CreateFile(reparsePoint, accessMode, FileShareMode.Read | FileShareMode.Write | FileShareMode.Delete, IntPtr.Zero, FileCreationDisposition.OpenExisting, diff --git a/src/System.Management.Automation/namespaces/LocationGlobber.cs b/src/System.Management.Automation/namespaces/LocationGlobber.cs index 7b09022e9..5e3ba3591 100644 --- a/src/System.Management.Automation/namespaces/LocationGlobber.cs +++ b/src/System.Management.Automation/namespaces/LocationGlobber.cs @@ -1570,33 +1570,6 @@ namespace System.Management.Automation return result; } // IsProviderQualifiedPath - /// - /// Determines if the given path is absolute while on a single root filesystem. - /// - /// - /// - /// Porting notes: absolute paths on non-Windows filesystems start with a '/' (no "C:" drive - /// prefix, the slash is the prefix). We compare against both '/' and '\' (default and - /// alternate path separator) in order for PowerShell to be slash agnostic. - /// - /// - /// - /// The path used in the determination - /// - /// - /// - /// Returns true if we're on a single root filesystem and the path is absolute. - /// - internal static bool IsSingleFileSystemAbsolutePath(string path) - { -#if UNIX - return path.StartsWith(StringLiterals.DefaultPathSeparatorString, StringComparison.Ordinal) - || path.StartsWith(StringLiterals.AlternatePathSeparatorString, StringComparison.Ordinal); -#else - return false; -#endif - } // IsSingleFileSystemAbsolutePath - /// /// Determines if the given path is relative or absolute /// @@ -1634,9 +1607,7 @@ namespace System.Management.Automation break; } - // compare both to \ and / here - if (path.StartsWith(@".\", StringComparison.Ordinal) || - path.StartsWith(@"./", StringComparison.Ordinal)) + if (path.StartsWith(@".\", StringComparison.Ordinal)) { // The .\ prefix basically escapes anything that follows // so treat it as a relative path no matter what comes @@ -1646,13 +1617,6 @@ namespace System.Management.Automation break; } - // check if we're on a single root filesystem and it's an absolute path - if (IsSingleFileSystemAbsolutePath(path)) - { - result = true; - break; - } - int index = path.IndexOf(":", StringComparison.Ordinal); if (index == -1) @@ -1740,14 +1704,6 @@ namespace System.Management.Automation break; } - // check if we're on a single root filesystem and it's an absolute path - if (IsSingleFileSystemAbsolutePath(path)) - { - driveName = StringLiterals.DefaultPathSeparatorString; - result = true; - break; - } - int index = path.IndexOf(":", StringComparison.CurrentCulture); if (index == -1) @@ -2060,20 +2016,7 @@ namespace System.Management.Automation // Now hack off the drive component of the path if (!isPathForCurrentDrive) { - // This functionality needs to respect if a drive uses a colon to separate the path - // - // what happens here is this: - // - path is assumed to be drive root relative, so on Windows it would start with a - // \ - // - on Linux, there is no difference between drive root relative, and absolute, they - // are both the same, so we have to preserve the drive here in order to make - // sure the path will continue being drive root relative - if (workingDriveForPath.VolumeSeparatedByColon) - { - // this is the default behavior for all windows drives, and all non-filesystem - // drives on non-windows - path = path.Substring(driveName.Length + 1); - } + path = path.Substring(driveName.Length + 1); } } else @@ -2281,10 +2224,6 @@ namespace System.Management.Automation { // The root relative path was given so empty the current working path. - // Porting notes: This can happen on non-Windows, because the assumption - // is that for file paths a path that is already relative to the drive - // root is the same thing as an absolute path (both start with /). - driveRootRelativeWorkingPath = String.Empty; // Remove the \ or / from the drive relative @@ -3153,12 +3092,6 @@ namespace System.Management.Automation } } - // Porting note: if the volume is not separated by a colon (non-Windows filesystems), don't add it. - if (!drive.VolumeSeparatedByColon) - { - formatString = "{0}{1}"; - } - string resolvedPath = String.Format( System.Globalization.CultureInfo.InvariantCulture, @@ -3326,53 +3259,35 @@ namespace System.Management.Automation string result = path; bool treatAsRelative = true; - if (drive.VolumeSeparatedByColon) + // Ensure the drive name is the same as the portion of the path before + // :. If not add the drive name and colon as if it was a relative path + + int index = path.IndexOf(':'); + + if (index != -1) { - // Ensure the drive name is the same as the portion of the path before - // :. If not add the drive name and colon as if it was a relative path - - int index = path.IndexOf(':'); - - if (index != -1) + if (drive.Hidden) { - if (drive.Hidden) + treatAsRelative = false; + } + else + { + string possibleDriveName = path.Substring(0, index); + if (String.Equals(possibleDriveName, drive.Name, StringComparison.OrdinalIgnoreCase)) { treatAsRelative = false; } - else - { - string possibleDriveName = path.Substring(0, index); - if (String.Equals(possibleDriveName, drive.Name, StringComparison.OrdinalIgnoreCase)) - { - treatAsRelative = false; - } - } - } - } - else - { - if (IsAbsolutePath(path)) - { - treatAsRelative = false; } } if (treatAsRelative) { - string formatString; - if (drive.VolumeSeparatedByColon) - { - formatString = "{0}:" + StringLiterals.DefaultPathSeparator + "{1}"; - if (path.StartsWith(StringLiterals.DefaultPathSeparatorString, StringComparison.Ordinal)) - { - formatString = "{0}:{1}"; - } - } - else - { - formatString = "{0}{1}"; - } + string formatString = "{0}:" + StringLiterals.DefaultPathSeparator + "{1}"; + if (path.StartsWith(StringLiterals.DefaultPathSeparatorString, StringComparison.Ordinal)) + { + formatString = "{0}:{1}"; + } result = String.Format( System.Globalization.CultureInfo.InvariantCulture, @@ -5089,4 +5004,4 @@ namespace System.Management.Automation #endregion internal methods } // class LocationGlobber -} // namespace System.Management.Automation +} // namespace System.Management.Automation \ No newline at end of file diff --git a/src/System.Management.Automation/namespaces/NavigationProviderBase.cs b/src/System.Management.Automation/namespaces/NavigationProviderBase.cs index beeb0d80d..b234acd09 100644 --- a/src/System.Management.Automation/namespaces/NavigationProviderBase.cs +++ b/src/System.Management.Automation/namespaces/NavigationProviderBase.cs @@ -416,8 +416,8 @@ namespace System.Management.Automation.Provider } else { - // Normalize the path so that only the default path separator is used as a - // separator even if the user types the alternate slash. + // Normalize the path so that only the backslash is used as a separator even if the + // user types a forward slash. parent = parent.Replace(StringLiterals.AlternatePathSeparator, StringLiterals.DefaultPathSeparator); child = child.Replace(StringLiterals.AlternatePathSeparator, StringLiterals.DefaultPathSeparator); diff --git a/src/System.Management.Automation/namespaces/RegistryProvider.cs b/src/System.Management.Automation/namespaces/RegistryProvider.cs index 63c1d7ef8..8b3a75847 100644 --- a/src/System.Management.Automation/namespaces/RegistryProvider.cs +++ b/src/System.Management.Automation/namespaces/RegistryProvider.cs @@ -135,8 +135,6 @@ namespace Microsoft.PowerShell.Commands protected override Collection InitializeDefaultDrives() { Collection drives = new Collection(); - -#if !UNIX drives.Add( new PSDriveInfo( "HKLM", @@ -152,7 +150,6 @@ namespace Microsoft.PowerShell.Commands "HKEY_CURRENT_USER", RegistryProviderStrings.HKCUDriveDescription, null)); -#endif return drives; } // InitializeDefaultDrives @@ -3885,7 +3882,7 @@ namespace Microsoft.PowerShell.Commands if (!String.IsNullOrEmpty(path)) { - result = path.Replace(StringLiterals.AlternatePathSeparator, StringLiterals.DefaultPathSeparator); + result = path.Replace('/', '\\'); // Remove relative path tokens if (HasRelativePathTokens(path)) diff --git a/src/System.Management.Automation/namespaces/SafeRegistryHandle.cs b/src/System.Management.Automation/namespaces/SafeRegistryHandle.cs index 006714766..119cf9724 100644 --- a/src/System.Management.Automation/namespaces/SafeRegistryHandle.cs +++ b/src/System.Management.Automation/namespaces/SafeRegistryHandle.cs @@ -58,13 +58,9 @@ namespace Microsoft.PowerShell.Commands.Internal override protected bool ReleaseHandle() { -#if UNIX - return true; -#else // Returns a Win32 error code, 0 for success int r = RegCloseKey(handle); return r == 0; -#endif } } } diff --git a/src/System.Management.Automation/namespaces/SafeTransactionHandle.cs b/src/System.Management.Automation/namespaces/SafeTransactionHandle.cs index 797193cc6..ad5af91bd 100644 --- a/src/System.Management.Automation/namespaces/SafeTransactionHandle.cs +++ b/src/System.Management.Automation/namespaces/SafeTransactionHandle.cs @@ -45,7 +45,7 @@ namespace Microsoft.PowerShell.Commands.Internal // KTM is kernel Transaction Manager to handle file, registry etc and MSDTC provides an integration support // with KTM to handle transaction across kernel resources and MSDTC resources like SQL, MSMQ etc. // We need KTMRM service as well. WinPE doesnt have these services installed - if (Utils.IsWinPEHost() || PsUtils.IsRunningOnProcessorArchitectureARM()) + if (RemotingCommandUtil.IsWinPEHost() || PsUtils.IsRunningOnProcessorArchitectureARM()) { throw new NotSupportedException(RegistryProviderStrings.NotSupported_KernelTransactions); } diff --git a/src/System.Management.Automation/resources/ParserStrings.resx b/src/System.Management.Automation/resources/ParserStrings.resx index 45c808cb5..74847d052 100644 --- a/src/System.Management.Automation/resources/ParserStrings.resx +++ b/src/System.Management.Automation/resources/ParserStrings.resx @@ -1351,8 +1351,8 @@ ModuleVersion : Version of module to import. If used, ModuleName must represent Cannot run a document in PowerShell Core: {0}. - - 'PowerShellAssemblyLoadContext' is not initialized. + + The default AssemblyLoadContext in use is invalid. The default AssemblyLoadContext for PowerShell Core should be of type 'PowerShellAssemblyLoadContext'. Multiple type constraints are not allowed on a method parameter. diff --git a/src/System.Management.Automation/security/CatalogHelper.cs b/src/System.Management.Automation/security/CatalogHelper.cs index 66649901b..f052cbe48 100644 --- a/src/System.Management.Automation/security/CatalogHelper.cs +++ b/src/System.Management.Automation/security/CatalogHelper.cs @@ -1,4 +1,3 @@ -#if !UNIX /********************************************************************++ Copyright (c) Microsoft Corporation. All rights reserved. @@ -845,4 +844,3 @@ namespace System.Management.Automation } } -#endif diff --git a/src/System.Management.Automation/security/SecureStringHelper.cs b/src/System.Management.Automation/security/SecureStringHelper.cs index 89f777ce7..50948e91f 100644 --- a/src/System.Management.Automation/security/SecureStringHelper.cs +++ b/src/System.Management.Automation/security/SecureStringHelper.cs @@ -94,7 +94,7 @@ namespace Microsoft.PowerShell } finally { - Marshal.ZeroFreeCoTaskMemUnicode(ptr); + ClrFacade.ZeroFreeCoTaskMemUnicode(ptr); } } diff --git a/src/System.Management.Automation/security/SecurityManager.cs b/src/System.Management.Automation/security/SecurityManager.cs index 80446a297..7dd6d46f2 100644 --- a/src/System.Management.Automation/security/SecurityManager.cs +++ b/src/System.Management.Automation/security/SecurityManager.cs @@ -117,13 +117,12 @@ namespace Microsoft.PowerShell string path = script.Path; string reasonMessage; - // path is assumed to be fully qualified here - if (path.IndexOf(System.IO.Path.DirectorySeparatorChar) < 0) + if (path.IndexOf('\\') < 0) { throw PSTraceSource.NewArgumentException("path"); } - if (path.LastIndexOf(System.IO.Path.DirectorySeparatorChar) == (path.Length - 1)) + if (path.LastIndexOf('\\') == (path.Length - 1)) { throw PSTraceSource.NewArgumentException("path"); } diff --git a/src/System.Management.Automation/security/SecuritySupport.cs b/src/System.Management.Automation/security/SecuritySupport.cs index bb4174863..08f529927 100644 --- a/src/System.Management.Automation/security/SecuritySupport.cs +++ b/src/System.Management.Automation/security/SecuritySupport.cs @@ -141,9 +141,6 @@ namespace System.Management.Automation.Internal internal static void SetExecutionPolicy(ExecutionPolicyScope scope, ExecutionPolicy policy, string shellId) { -#if UNIX - throw new PlatformNotSupportedException(); -#else string executionPolicy = "Restricted"; string preferenceKey = Utils.GetRegistryConfigurationPath(shellId); const string PolicyKeyValueName = "ExecutionPolicy"; @@ -228,7 +225,6 @@ namespace System.Management.Automation.Internal break; } } -#endif } // Clean up the parents of a registry key as long as they @@ -285,9 +281,6 @@ namespace System.Management.Automation.Internal internal static ExecutionPolicy GetExecutionPolicy(string shellId, ExecutionPolicyScope scope) { -#if UNIX - return ExecutionPolicy.Unrestricted; -#else switch (scope) { case ExecutionPolicyScope.Process: @@ -368,7 +361,6 @@ namespace System.Management.Automation.Internal } return ExecutionPolicy.Restricted; -#endif } internal static ExecutionPolicy ParseExecutionPolicy(string policy) @@ -437,11 +429,6 @@ namespace System.Management.Automation.Internal return false; } -#if UNIX - // There is no signature support on non-Windows platforms (yet), when - // execution reaches here, we are sure the file is under product folder - return true; -#else // Check the file signature Signature fileSignature = SignatureHelper.GetSignature(file, null); if ((fileSignature != null) && (fileSignature.IsOSBinary)) @@ -461,7 +448,6 @@ namespace System.Management.Automation.Internal } return false; -#endif } #if !CORECLR @@ -1639,15 +1625,6 @@ namespace System.Management.Automation /// AMSI_RESULT_DETECTED if malware was detected in the sample. internal static AmsiNativeMethods.AMSI_RESULT ScanContent(string content, string sourceMetadata) { -#if UNIX - return AmsiNativeMethods.AMSI_RESULT.AMSI_RESULT_NOT_DETECTED; -#else - return WinScanContent(content,sourceMetadata); -#endif - } - - internal static AmsiNativeMethods.AMSI_RESULT WinScanContent(string content, string sourceMetadata) - { if (String.IsNullOrEmpty(sourceMetadata)) { sourceMetadata = String.Empty; @@ -1731,11 +1708,9 @@ namespace System.Management.Automation } } - internal static void CurrentDomain_ProcessExit(object sender, EventArgs e) + static void CurrentDomain_ProcessExit(object sender, EventArgs e) { -#if !UNIX VerifyAmsiUninitializeCalled(); -#endif } [SuppressMessage("Microsoft.Reliability", "CA2006:UseSafeHandleToEncapsulateNativeResources")] @@ -1751,13 +1726,6 @@ namespace System.Management.Automation /// internal static void CloseSession() { -#if !UNIX - WinCloseSession(); -#endif - } - - internal static void WinCloseSession() - { if (!amsiInitFailed) { if ((amsiContext != IntPtr.Zero) && (amsiSession != IntPtr.Zero)) @@ -1780,13 +1748,6 @@ namespace System.Management.Automation /// internal static void Uninitialize() { -#if !UNIX - WinUninitialize(); -#endif - } - - internal static void WinUninitialize() - { AmsiUninitializeCalled = true; if (!amsiInitFailed) { diff --git a/src/System.Management.Automation/security/wldpNativeMethods.cs b/src/System.Management.Automation/security/wldpNativeMethods.cs index 1bc416616..5261cd863 100644 --- a/src/System.Management.Automation/security/wldpNativeMethods.cs +++ b/src/System.Management.Automation/security/wldpNativeMethods.cs @@ -190,7 +190,8 @@ namespace System.Management.Automation.Security // Temp path can sometimes be deleted. While many places in PowerShell depend on its existence, // this one can crash PowerShell. // A less sensitive implementation will be possible once AppLocker allows validation of files that - // don't exist. + // don't exist: + // https://microsoft.visualstudio.com/DefaultCollection/WSSC/_workitems#_a=edit&id=1908704 // string testPathScript = null; diff --git a/src/System.Management.Automation/singleshell/config/MshConsoleLoadException.cs b/src/System.Management.Automation/singleshell/config/MshConsoleLoadException.cs index eb8b8c9ab..f9e081815 100644 --- a/src/System.Management.Automation/singleshell/config/MshConsoleLoadException.cs +++ b/src/System.Management.Automation/singleshell/config/MshConsoleLoadException.cs @@ -94,7 +94,7 @@ namespace System.Management.Automation.Runspaces } _errorRecord = new ErrorRecord(new ParentContainsErrorRecordException(this), "ConsoleLoadFailure", ErrorCategory.ResourceUnavailable, null); - _errorRecord.ErrorDetails = new ErrorDetails(String.Format(ConsoleInfoErrorStrings.ConsoleLoadFailure, _consoleFileName, sb.ToString())); + _errorRecord.ErrorDetails = new ErrorDetails(typeof(PSConsoleLoadException).GetTypeInfo().Assembly, "ConsoleInfoErrorStrings", "ConsoleLoadFailure", _consoleFileName, sb.ToString()); } private ErrorRecord _errorRecord; diff --git a/src/System.Management.Automation/singleshell/config/MshSnapinInfo.cs b/src/System.Management.Automation/singleshell/config/MshSnapinInfo.cs index dd0209b66..e6b052cba 100644 --- a/src/System.Management.Automation/singleshell/config/MshSnapinInfo.cs +++ b/src/System.Management.Automation/singleshell/config/MshSnapinInfo.cs @@ -994,7 +994,7 @@ namespace System.Management.Automation return v; } - internal static void ReadRegistryInfo(out Version assemblyVersion, out string publicKeyToken, out string culture, out string architecture, out string applicationBase, out Version psVersion) + private static void ReadRegistryInfo(out Version assemblyVersion, out string publicKeyToken, out string culture, out string architecture, out string applicationBase, out Version psVersion) { applicationBase = Utils.GetApplicationBase(Utils.DefaultPowerShellShellID); Dbg.Assert(!string.IsNullOrEmpty(applicationBase), @@ -1130,7 +1130,7 @@ namespace System.Management.Automation StringComparison.OrdinalIgnoreCase)) { types = new Collection(new string[] { "GetEvent.types.ps1xml" }); - formats = new Collection(new string[] { "Event.format.ps1xml","Diagnostics.format.ps1xml" }); + formats = new Collection(new string[] { "Event.Format.ps1xml","Diagnostics.Format.ps1xml" }); } else if (defaultMshSnapinInfo.AssemblyName.Equals("Microsoft.WSMan.Management", StringComparison.OrdinalIgnoreCase)) { @@ -1390,10 +1390,9 @@ namespace System.Management.Automation { defaultMshSnapins = new List() { -#if !PORTABLE // Microsoft.PowerShell.Commands.Diagnostics.dll needs to be ported new DefaultPSSnapInInformation("Microsoft.PowerShell.Diagnostics", "Microsoft.PowerShell.Commands.Diagnostics", null, "GetEventResources,Description", "GetEventResources,Vendor"), -#endif + new DefaultPSSnapInInformation("Microsoft.PowerShell.Host", "Microsoft.PowerShell.ConsoleHost", null, "HostMshSnapInResources,Description","HostMshSnapInResources,Vendor"), @@ -1409,13 +1408,11 @@ namespace System.Management.Automation "SecurityMshSnapInResources,Description","SecurityMshSnapInResources,Vendor") }; -#if !PORTABLE - if (!Utils.IsWinPEHost()) + if (!RemotingCommandUtil.IsWinPEHost()) { defaultMshSnapins.Add(new DefaultPSSnapInInformation("Microsoft.WSMan.Management", "Microsoft.WSMan.Management", null, "WsManResources,Description", "WsManResources,Vendor")); } -#endif } } } diff --git a/src/System.Management.Automation/singleshell/config/MshSnapinLoadException.cs b/src/System.Management.Automation/singleshell/config/MshSnapinLoadException.cs index 02f939759..dd1346a83 100644 --- a/src/System.Management.Automation/singleshell/config/MshSnapinLoadException.cs +++ b/src/System.Management.Automation/singleshell/config/MshSnapinLoadException.cs @@ -113,12 +113,12 @@ namespace System.Management.Automation.Runspaces if (_warning) { _errorRecord = new ErrorRecord(new ParentContainsErrorRecordException(this), "PSSnapInLoadWarning", ErrorCategory.ResourceUnavailable, null); - _errorRecord.ErrorDetails = new ErrorDetails(String.Format(ConsoleInfoErrorStrings.PSSnapInLoadWarning, _PSSnapin, _reason)); + _errorRecord.ErrorDetails = new ErrorDetails(currentAssembly, "ConsoleInfoErrorStrings", "PSSnapInLoadWarning", _PSSnapin, _reason); } else { _errorRecord = new ErrorRecord(new ParentContainsErrorRecordException(this), "PSSnapInLoadFailure", ErrorCategory.ResourceUnavailable, null); - _errorRecord.ErrorDetails = new ErrorDetails(String.Format(ConsoleInfoErrorStrings.PSSnapInLoadFailure, _PSSnapin, _reason)); + _errorRecord.ErrorDetails = new ErrorDetails(currentAssembly, "ConsoleInfoErrorStrings", "PSSnapInLoadFailure", _PSSnapin, _reason); } } } diff --git a/src/System.Management.Automation/singleshell/config/RunspaceConfigForSingleShell.cs b/src/System.Management.Automation/singleshell/config/RunspaceConfigForSingleShell.cs index 28b00731e..e3e89faf2 100644 --- a/src/System.Management.Automation/singleshell/config/RunspaceConfigForSingleShell.cs +++ b/src/System.Management.Automation/singleshell/config/RunspaceConfigForSingleShell.cs @@ -617,7 +617,6 @@ namespace System.Management.Automation.Runspaces try { - // WARNING: DUPLICATE CODE see InitialSessionState assembly = Assembly.Load(new AssemblyName(mshsnapinInfo.AssemblyName)); } catch (FileLoadException e) diff --git a/src/System.Management.Automation/utils/ClrFacade.cs b/src/System.Management.Automation/utils/ClrFacade.cs index f9cd78eb4..ab61c8d7c 100644 --- a/src/System.Management.Automation/utils/ClrFacade.cs +++ b/src/System.Management.Automation/utils/ClrFacade.cs @@ -148,7 +148,7 @@ namespace System.Management.Automation { if (unmanagedMemory != IntPtr.Zero) { - Marshal.ZeroFreeCoTaskMemUnicode(unmanagedMemory); + ZeroFreeCoTaskMemUnicode(unmanagedMemory); } } return passwordInClearText; @@ -213,6 +213,19 @@ namespace System.Management.Automation #endif } + /// + /// Needed to pair with the SecureStringToCoTaskMemUnicode method which is member of + /// 'SecureStringMarshal' on CORE CLR, and member of 'Marshal' on Full CLR. + /// + internal static void ZeroFreeCoTaskMemUnicode(IntPtr unmanagedStr) + { +#if CORECLR + SecureStringMarshal.ZeroFreeCoTaskMemUnicode(unmanagedStr); +#else + Marshal.ZeroFreeCoTaskMemUnicode(unmanagedStr); +#endif + } + /// /// Facade for SecureStringToCoTaskMemUnicode /// @@ -228,6 +241,7 @@ namespace System.Management.Automation #endregion Marshal #region Assembly + /// /// Facade for AssemblyName.GetAssemblyName(string) /// @@ -311,7 +325,7 @@ namespace System.Management.Automation { throw new ArgumentNullException("assemblyShortName"); } - + return PSAssemblyLoadContext.ProbeAssemblyFileForMetadataAnalysis(assemblyShortName, additionalSearchPath); } @@ -340,15 +354,20 @@ namespace System.Management.Automation PSAssemblyLoadContext.AssemblyLoad += handler; } + private static volatile PowerShellAssemblyLoadContext _psLoadContext; private static PowerShellAssemblyLoadContext PSAssemblyLoadContext { get { - if (PowerShellAssemblyLoadContext.Instance == null) + if (_psLoadContext == null) { - throw new InvalidOperationException(ParserStrings.LoadContextNotInitialized); + _psLoadContext = AssemblyLoadContext.Default as PowerShellAssemblyLoadContext; + if (_psLoadContext == null) + { + throw new InvalidOperationException(ParserStrings.InvalidAssemblyLoadContextInUse); + } } - return PowerShellAssemblyLoadContext.Instance; + return _psLoadContext; } } #endif @@ -516,6 +535,27 @@ namespace System.Management.Automation #endif } + /// + /// Facade for Directory.GetParent(string) + /// + internal static DirectoryInfo GetParent(string path) + { +#if CORECLR + // Implementation copied from .NET source code. + if (string.IsNullOrEmpty(path)) + throw new ArgumentNullException("path"); + + string fullPath = Path.GetFullPath(path); + + string s = Path.GetDirectoryName(fullPath); + if (s == null) + return null; + return new DirectoryInfo(s); +#else + return Directory.GetParent(path); +#endif + } + /// /// Facade for ManagementDateTimeConverter.ToDmtfDateTime(DateTime) /// @@ -656,7 +696,7 @@ namespace System.Management.Automation internal static void SetProfileOptimizationRoot(string directoryPath) { #if CORECLR - PSAssemblyLoadContext.SetProfileOptimizationRootImpl(directoryPath); + System.Runtime.Loader.AssemblyLoadContext.Default.SetProfileOptimizationRoot(directoryPath); #else System.Runtime.ProfileOptimization.SetProfileRoot(directoryPath); #endif @@ -669,7 +709,7 @@ namespace System.Management.Automation internal static void StartProfileOptimization(string profile) { #if CORECLR - PSAssemblyLoadContext.StartProfileOptimizationImpl(profile); + System.Runtime.Loader.AssemblyLoadContext.Default.StartProfileOptimization(profile); #else System.Runtime.ProfileOptimization.StartProfile(profile); #endif diff --git a/src/System.Management.Automation/utils/CryptoUtils.cs b/src/System.Management.Automation/utils/CryptoUtils.cs index bc794d99b..51fb8edf0 100644 --- a/src/System.Management.Automation/utils/CryptoUtils.cs +++ b/src/System.Management.Automation/utils/CryptoUtils.cs @@ -1023,7 +1023,7 @@ namespace System.Management.Automation.Internal { data[i] = Marshal.ReadByte(ptr, i); } - Marshal.ZeroFreeCoTaskMemUnicode(ptr); + ClrFacade.ZeroFreeCoTaskMemUnicode(ptr); try { diff --git a/src/System.Management.Automation/utils/ExtensionMethods.cs b/src/System.Management.Automation/utils/ExtensionMethods.cs index 70bc32ea7..d2d0dd577 100644 --- a/src/System.Management.Automation/utils/ExtensionMethods.cs +++ b/src/System.Management.Automation/utils/ExtensionMethods.cs @@ -130,9 +130,7 @@ namespace System.Management.Automation [MethodImpl(MethodImplOptions.AggressiveInlining)] internal static bool IsComObject(this Type type) { -#if UNIX - return false; -#elif CORECLR // Type.IsComObject(Type) is not in CoreCLR +#if CORECLR // Type.IsComObject(Type) is not in CoreCLR return ComObjectType.IsAssignableFrom(type); #else return type.IsCOMObject; diff --git a/src/System.Management.Automation/utils/PSTelemetryWrapper.cs b/src/System.Management.Automation/utils/PSTelemetryWrapper.cs index f8c7b1b16..74ecb2ad9 100644 --- a/src/System.Management.Automation/utils/PSTelemetryWrapper.cs +++ b/src/System.Management.Automation/utils/PSTelemetryWrapper.cs @@ -56,6 +56,7 @@ namespace System.Management.Automation.Internal // Initialize EventSourceOptions for Writing informational messages // WdiContext will ensure Universal Telemetry Client [UTC] will upload telemetry messages to Cosmos/xPert pipeline + // https://microsoft.sharepoint.com/teams/osg_core_fun/idt/OSGInstrument/SitePages/How%20to%20upload%20EventSource%20events.aspx // MeasuresKeyword is to indicate that event is for understanding measures and reporting scenarios. // This keyword results in the generation of Asimov compatible events for telemetry @@ -89,7 +90,8 @@ namespace System.Management.Automation.Internal /// // EventSource data gets raised on the Client containing OS Environment information and supplied arguments as "data" - // Events are queued and uploaded to Cosmos/xPert. + // Events are queued and uploaded to Cosmos/xPert. Here is a way of accessing the telemetry data: + // http://xpert/osg/?view=Search&source=PROD&start=3.06.2015-19.41&end=3.06.2015-21.41 // Format of data generated on the Client: // { // "ver": "2.1", diff --git a/src/System.Management.Automation/utils/PowerShellETWTracer.cs b/src/System.Management.Automation/utils/PowerShellETWTracer.cs index 3b58a2fc8..53bc633e9 100644 --- a/src/System.Management.Automation/utils/PowerShellETWTracer.cs +++ b/src/System.Management.Automation/utils/PowerShellETWTracer.cs @@ -1,8 +1,7 @@ -#if !UNIX // // Copyright (C) Microsoft. All rights reserved. // -using System; +using System; using System.Collections.Generic; using System.Globalization; using System.Linq; @@ -1596,6 +1595,4 @@ namespace System.Management.Automation.Tracing } } //pragma warning restore 16001,16003 -} - -#endif +} \ No newline at end of file diff --git a/src/System.Management.Automation/utils/PsUtils.cs b/src/System.Management.Automation/utils/PsUtils.cs index f27825042..ae9c2fd6b 100644 --- a/src/System.Management.Automation/utils/PsUtils.cs +++ b/src/System.Management.Automation/utils/PsUtils.cs @@ -584,19 +584,6 @@ namespace System.Management.Automation } internal static string GetHostName() - { - // Note: non-windows CoreCLR does not support System.Net yet - if (Platform.IsWindows) - { - return WinGetHostName(); - } - else - { - return Platform.NonWindowsGetHostName(); - } - } - - internal static string WinGetHostName() { System.Net.NetworkInformation.IPGlobalProperties ipProperties = System.Net.NetworkInformation.IPGlobalProperties.GetIPGlobalProperties(); @@ -611,18 +598,6 @@ namespace System.Management.Automation } internal static uint GetNativeThreadId() - { - if (Platform.IsWindows) - { - return WinGetNativeThreadId(); - } - else - { - return Platform.NonWindowsGetThreadId(); - } - } - - internal static uint WinGetNativeThreadId() { return NativeMethods.GetCurrentThreadId(); } diff --git a/src/System.Management.Automation/utils/tracing/EtwActivity.cs b/src/System.Management.Automation/utils/tracing/EtwActivity.cs index 5352749db..6abd12063 100644 --- a/src/System.Management.Automation/utils/tracing/EtwActivity.cs +++ b/src/System.Management.Automation/utils/tracing/EtwActivity.cs @@ -1,4 +1,3 @@ -#if !UNIX // // Copyright (C) Microsoft. All rights reserved. // @@ -548,6 +547,3 @@ namespace System.Management.Automation.Tracing } } } - - -#endif diff --git a/src/System.Management.Automation/utils/tracing/EtwActivityReverter.cs b/src/System.Management.Automation/utils/tracing/EtwActivityReverter.cs index ad79f6160..21e1236a7 100644 --- a/src/System.Management.Automation/utils/tracing/EtwActivityReverter.cs +++ b/src/System.Management.Automation/utils/tracing/EtwActivityReverter.cs @@ -1,5 +1,4 @@ -#if !UNIX -//----------------------------------------------------------------------- +//----------------------------------------------------------------------- // // Copyright (c) Microsoft Corporation. All rights reserved. // @@ -59,6 +58,3 @@ namespace System.Management.Automation.Tracing } } } - - -#endif diff --git a/src/System.Management.Automation/utils/tracing/EtwActivityReverterMethodInvoker.cs b/src/System.Management.Automation/utils/tracing/EtwActivityReverterMethodInvoker.cs index 3a3c48463..722ff6a11 100644 --- a/src/System.Management.Automation/utils/tracing/EtwActivityReverterMethodInvoker.cs +++ b/src/System.Management.Automation/utils/tracing/EtwActivityReverterMethodInvoker.cs @@ -1,5 +1,4 @@ -#if !UNIX -//----------------------------------------------------------------------- +//----------------------------------------------------------------------- // // Copyright (c) Microsoft Corporation. All rights reserved. // @@ -69,6 +68,3 @@ namespace System.Management.Automation.Tracing #endregion } } - - -#endif diff --git a/src/System.Management.Automation/utils/tracing/EtwEventCorrelator.cs b/src/System.Management.Automation/utils/tracing/EtwEventCorrelator.cs index b08cc7586..4dc1221d8 100644 --- a/src/System.Management.Automation/utils/tracing/EtwEventCorrelator.cs +++ b/src/System.Management.Automation/utils/tracing/EtwEventCorrelator.cs @@ -1,5 +1,4 @@ -#if !UNIX -//----------------------------------------------------------------------- +//----------------------------------------------------------------------- // // Copyright (c) Microsoft Corporation. All rights reserved. // @@ -116,6 +115,3 @@ namespace System.Management.Automation.Tracing } } } - - -#endif diff --git a/src/System.Management.Automation/utils/tracing/IMethodInvoker.cs b/src/System.Management.Automation/utils/tracing/IMethodInvoker.cs index 3f1ebf579..37570678d 100644 --- a/src/System.Management.Automation/utils/tracing/IMethodInvoker.cs +++ b/src/System.Management.Automation/utils/tracing/IMethodInvoker.cs @@ -1,5 +1,4 @@ -#if !UNIX -//----------------------------------------------------------------------- +//----------------------------------------------------------------------- // // Copyright (c) Microsoft Corporation. All rights reserved. // @@ -15,6 +14,3 @@ namespace System.Management.Automation.Tracing object[] CreateInvokerArgs(Delegate methodToInvoke, object[] methodToInvokeArgs); } } - - -#endif diff --git a/src/System.Management.Automation/utils/tracing/PSEtwLog.cs b/src/System.Management.Automation/utils/tracing/PSEtwLog.cs index 7e3030b0d..d2d1b058a 100644 --- a/src/System.Management.Automation/utils/tracing/PSEtwLog.cs +++ b/src/System.Management.Automation/utils/tracing/PSEtwLog.cs @@ -1,4 +1,3 @@ -#if !UNIX // // Copyright (C) Microsoft. All rights reserved. // @@ -311,6 +310,3 @@ namespace System.Management.Automation.Tracing } } } - - -#endif diff --git a/src/System.Management.Automation/utils/tracing/PSEtwLogProvider.cs b/src/System.Management.Automation/utils/tracing/PSEtwLogProvider.cs index 8fd0d9612..32bd8baa4 100644 --- a/src/System.Management.Automation/utils/tracing/PSEtwLogProvider.cs +++ b/src/System.Management.Automation/utils/tracing/PSEtwLogProvider.cs @@ -1,4 +1,3 @@ -#if !UNIX // // Copyright (C) Microsoft. All rights reserved. // @@ -463,6 +462,4 @@ namespace System.Management.Automation.Tracing EventProvider.SetActivityId(ref result); } } -} - -#endif +} \ No newline at end of file diff --git a/src/System.Management.Automation/utils/tracing/Tracing.cs b/src/System.Management.Automation/utils/tracing/Tracing.cs index b7360ca09..301d9ac98 100644 --- a/src/System.Management.Automation/utils/tracing/Tracing.cs +++ b/src/System.Management.Automation/utils/tracing/Tracing.cs @@ -1,4 +1,3 @@ -#if !UNIX // // Copyright (C) Microsoft. All rights reserved. // @@ -53,6 +52,4 @@ namespace System.Management.Automation.Tracing { return true; } } -} - -#endif +} \ No newline at end of file diff --git a/src/System.Management.Automation/utils/tracing/TracingGen.cs b/src/System.Management.Automation/utils/tracing/TracingGen.cs index 3cff0e265..35ff735ff 100644 --- a/src/System.Management.Automation/utils/tracing/TracingGen.cs +++ b/src/System.Management.Automation/utils/tracing/TracingGen.cs @@ -1,4 +1,3 @@ -#if !UNIX using System; using System.Collections; using System.Diagnostics.Eventing; @@ -988,5 +987,3 @@ namespace System.Management.Automation.Tracing { } // This code was generated on 02/01/2012 19:52:32 - -#endif diff --git a/src/TypeCatalogGen/TypeCatalogGen.cs b/src/TypeCatalogGen/TypeCatalogGen.cs index b93cac070..3bc70e07d 100644 --- a/src/TypeCatalogGen/TypeCatalogGen.cs +++ b/src/TypeCatalogGen/TypeCatalogGen.cs @@ -14,7 +14,6 @@ */ using System; using System.Collections.Generic; -using System.Diagnostics; using System.Globalization; using System.IO; using System.Reflection; @@ -91,16 +90,7 @@ Usage: TypeCatalogGen.exe <{0}> <{1}> } string fullName = GetTypeFullName(metadataReader, typeDefinition); - - // Only add unique types - if (!typeNameToAssemblyMap.ContainsKey(fullName)) - { - typeNameToAssemblyMap.Add(fullName, strongAssemblyName); - } - else - { - Debug.WriteLine($"Not adding duplicate key {fullName}!"); - } + typeNameToAssemblyMap.Add(fullName, strongAssemblyName); } } } @@ -128,19 +118,19 @@ Usage: TypeCatalogGen.exe <{0}> <{1}> switch (hashAlgorithm) { case AssemblyHashAlgorithm.Sha1: - hashImpl = SHA1.Create(); + hashImpl = HashAlgorithm.Create("SHA1"); break; case AssemblyHashAlgorithm.MD5: - hashImpl = MD5.Create(); + hashImpl = HashAlgorithm.Create("MD5"); break; case AssemblyHashAlgorithm.Sha256: - hashImpl = SHA256.Create(); + hashImpl = HashAlgorithm.Create("SHA256"); break; case AssemblyHashAlgorithm.Sha384: - hashImpl = SHA384.Create(); + hashImpl = HashAlgorithm.Create("SHA384"); break; case AssemblyHashAlgorithm.Sha512: - hashImpl = SHA512.Create(); + hashImpl = HashAlgorithm.Create("SHA512"); break; default: throw new NotSupportedException(); @@ -284,11 +274,10 @@ Usage: TypeCatalogGen.exe <{0}> <{1}> // catalog based on the reference assemblies of .NET Core. // using System.Collections.Generic; -using System.Runtime.Loader; namespace System.Management.Automation {{ - internal partial class PowerShellAssemblyLoadContext : AssemblyLoadContext + internal partial class PowerShellAssemblyLoadContext {{ private Dictionary InitializeTypeCatalog() {{ diff --git a/src/powershell-native/nativemsh/pwrshcommon/ClrHostWrapper.h b/src/powershell-native/nativemsh/pwrshcommon/ClrHostWrapper.h index cb1b870cc..b1c3b7cfb 100644 --- a/src/powershell-native/nativemsh/pwrshcommon/ClrHostWrapper.h +++ b/src/powershell-native/nativemsh/pwrshcommon/ClrHostWrapper.h @@ -12,6 +12,7 @@ #pragma once #include +#include #include "NativeMshConstants.h" namespace NativeMsh @@ -31,413 +32,322 @@ namespace NativeMsh virtual bool IsInitialized() { return false; } + // For setting a host ptr since it is not known at container creation time. + // TODO: Can I make it immutable? + virtual void SetClrHost( + void* hostPtr) = 0; + // Graceful clean up of the object to prevent leaks virtual unsigned int CleanUpHostWrapper() = 0; + void SetAppDomainId(DWORD id) + { + m_appDomainId = id; + } + + DWORD GetAppDomainId() + { + return m_appDomainId; + } + // // The following methods are direct thin wrappers for the host calls. // - virtual unsigned int SetupWrapper(LPCSTR coreClrPathPtr) = 0; + virtual HRESULT STDMETHODCALLTYPE CreateAppDomainWithManager( + /* [in] */ LPCWSTR wszFriendlyName, + /* [in] */ DWORD dwFlags, + /* [in] */ LPCWSTR wszAppDomainManagerAssemblyName, + /* [in] */ LPCWSTR wszAppDomainManagerTypeName, + /* [in] */ int nProperties, + /* [in] */ LPCWSTR *pPropertyNames, + /* [in] */ LPCWSTR *pPropertyValues, + /* [out] */ DWORD *pAppDomainID) = 0; - virtual int InitializeClr( - const char* exePath, - const char* appDomainFriendlyName, - int propertyCount, - const char** propertyKeys, - const char** propertyValues) = 0; + virtual HRESULT STDMETHODCALLTYPE UnloadAppDomain( + /* [in] */ DWORD dwAppDomainId, + /* [in] */ BOOL fWaitUntilDone) = 0; - virtual int CreateDelegate( - const char* entryPointAssemblyName, - const char* entryPointTypeName, - const char* entryPointMethodName, - void** delegate) = 0; + virtual HRESULT STDMETHODCALLTYPE CreateDelegate( + /* [in] */ DWORD appDomainID, + /* [in] */ LPCWSTR wszAssemblyName, + /* [in] */ LPCWSTR wszClassName, + /* [in] */ LPCWSTR wszMethodName, + /* [out] */ INT_PTR *fnPtr) = 0; - // TODO: This probably isn't needed - virtual int ShutdownClr() = 0; + virtual HRESULT STDMETHODCALLTYPE Authenticate( + /* [in] */ ULONGLONG authKey) = 0; + + virtual HRESULT STDMETHODCALLTYPE SetStartupFlags( + /* [in] */ STARTUP_FLAGS dwFlags) = 0; + + virtual HRESULT STDMETHODCALLTYPE Start() = 0; + + virtual HRESULT STDMETHODCALLTYPE Stop() = 0; + + virtual HRESULT STDMETHODCALLTYPE Release() = 0; }; +#if CORECLR // - // Concrete implementation of the wrapper for CoreClr.dll's - // Platform-Agnostic hosting interface. + // Concrete implementation of the wrapper for the ICLRRuntimeHost2 interface. // - class CoreClrHostingApiWrapper : public ClrHostWrapper + class ICLRRuntimeHost2Wrapper : public ClrHostWrapper { private: - // Handle of CoreClr.dll - HMODULE coreClrHandle; - HMODULE pinnedModuleHandle; - - // CoreCLR.dll API values that are hidden from the user and kept internal. - void* hostHandle; - unsigned int domainId; - - // The name of the CoreCLR native runtime DLL. - PCSTR coreClrDllName = "CoreCLR.dll"; - - // - // Function Pointer Definitions for the function pointers to load from CoreCLR.dll - // - typedef int (STDMETHODCALLTYPE *coreclr_initialize_ptr)( - const char* exePath, - const char* appDomainFriendlyName, - int propertyCount, - const char** propertyKeys, - const char** propertyValues, - void** hostHandle, - unsigned int* domainId); - - typedef int (STDMETHODCALLTYPE *coreclr_shutdown_ptr)( - void* hostHandle, - unsigned int domainId); - - typedef int (STDMETHODCALLTYPE *coreclr_create_delegate_ptr)( - void* hostHandle, - unsigned int domainId, - const char* entryPointAssemblyName, - const char* entryPointTypeName, - const char* entryPointMethodName, - void** delegate); - - // Pointers to exported functions of CoreClr.dll - coreclr_initialize_ptr initPtr; - coreclr_shutdown_ptr shutdownPtr; - coreclr_create_delegate_ptr createDelegatePtr; + ICLRRuntimeHost2* pHost; public: - CoreClrHostingApiWrapper() - : coreClrHandle(NULL), - pinnedModuleHandle(NULL), - hostHandle(NULL), - domainId(0), - initPtr(NULL), - shutdownPtr(NULL), - createDelegatePtr(NULL) - {} - - virtual ~CoreClrHostingApiWrapper() + ICLRRuntimeHost2Wrapper() : pHost(NULL) {} + virtual ~ICLRRuntimeHost2Wrapper() { - this->CleanUpHostWrapper(); + CleanUpHostWrapper(); } - virtual bool IsInitialized() - { - return (NULL != coreClrHandle); - } - - // - // Attempts to load CoreCLR.dll from the specified directory. - // On success pins the dll, sets coreCLRDirectoryPath and returns the HMODULE. - // On failure returns NULL. - // - virtual unsigned int SetupWrapper(LPCSTR coreClrPathPtr) + virtual bool IsInitialized() { return (pHost != NULL); } + + // For setting a host ptr since it is not known at container creation time. + virtual void SetClrHost(void* hostPtr) { - std::string coreClrPath(coreClrPathPtr); - coreClrPath += coreClrDllName; - - HMODULE result = LoadLibraryExA(coreClrPath.c_str(), NULL, 0); - if (!result) - { - return EXIT_CODE_INIT_FAILURE; - } - - // Pin the module - CoreCLR.dll does not support being unloaded. - if (!GetModuleHandleExA(GET_MODULE_HANDLE_EX_FLAG_PIN, coreClrPath.c_str(), &pinnedModuleHandle)) - { - return EXIT_CODE_INIT_FAILURE; - } - - initPtr = (coreclr_initialize_ptr)GetProcAddress(result, "coreclr_initialize"); - shutdownPtr = (coreclr_shutdown_ptr)GetProcAddress(result, "coreclr_shutdown"); - createDelegatePtr = (coreclr_create_delegate_ptr)GetProcAddress(result, "coreclr_create_delegate"); - - if (NULL == initPtr || - NULL == shutdownPtr || - NULL == createDelegatePtr) - { - return EXIT_CODE_INIT_FAILURE; - } - - // Initialization succeeded. Save the handle and return success; - coreClrHandle = result; - return EXIT_CODE_SUCCESS; + pHost = (ICLRRuntimeHost2*)hostPtr; } virtual unsigned int CleanUpHostWrapper() { if (this->IsInitialized()) { - HRESULT status = this->ShutdownClr(); - if (FAILED(status)) + if (FAILED(this->UnloadAppDomain(this->GetAppDomainId(), true))) + { + return g_UNLOAD_APPDOMAIN_FAILED; + } + + if (FAILED(this->Stop())) { return g_STOP_CLR_HOST_FAILED; } - - if (this->coreClrHandle) + + // Release the reference to the host + if (FAILED(this->Release())) { - // TODO: Is this comment still relevant with the new hosting API? - // - // Free the module. This is done for completeness, but in fact CoreCLR.dll - // was pinned earlier so this call won't actually free it. The pinning is - // done because CoreCLR does not support unloading. - ::FreeLibrary(this->coreClrHandle); - this->coreClrHandle = NULL; + return g_RELEASE_CLR_HOST_FAILED; } + this->SetClrHost(NULL); } return EXIT_CODE_SUCCESS; } - virtual int InitializeClr( - const char* exePath, - const char* appDomainFriendlyName, - int propertyCount, - const char** propertyKeys, - const char** propertyValues) + virtual HRESULT STDMETHODCALLTYPE CreateAppDomainWithManager( + /* [in] */ LPCWSTR wszFriendlyName, + /* [in] */ DWORD dwFlags, + /* [in] */ LPCWSTR wszAppDomainManagerAssemblyName, + /* [in] */ LPCWSTR wszAppDomainManagerTypeName, + /* [in] */ int nProperties, + /* [in] */ LPCWSTR *pPropertyNames, + /* [in] */ LPCWSTR *pPropertyValues, + /* [out] */ DWORD *pAppDomainID) { - if (initPtr) + if (pHost) { - return initPtr( - exePath, - appDomainFriendlyName, - propertyCount, - propertyKeys, - propertyValues, - &(this->hostHandle), - &(this->domainId)); + return pHost->CreateAppDomainWithManager( + wszFriendlyName, + dwFlags, + wszAppDomainManagerAssemblyName, + wszAppDomainManagerTypeName, + nProperties, + pPropertyNames, + pPropertyValues, + pAppDomainID); } return E_FAIL; } - virtual int CreateDelegate( - const char* entryPointAssemblyName, - const char* entryPointTypeName, - const char* entryPointMethodName, - void** delegate) + virtual HRESULT STDMETHODCALLTYPE UnloadAppDomain( + /* [in] */ DWORD dwAppDomainId, + /* [in] */ BOOL fWaitUntilDone) { - if (createDelegatePtr) + if (pHost) { - return createDelegatePtr( - this->hostHandle, - this->domainId, - entryPointAssemblyName, - entryPointTypeName, - entryPointMethodName, - delegate); + return pHost->UnloadAppDomain( + dwAppDomainId, + fWaitUntilDone); } return E_FAIL; } - virtual int ShutdownClr() + virtual HRESULT STDMETHODCALLTYPE CreateDelegate( + /* [in] */ DWORD appDomainID, + /* [in] */ LPCWSTR wszAssemblyName, + /* [in] */ LPCWSTR wszClassName, + /* [in] */ LPCWSTR wszMethodName, + /* [out] */ INT_PTR *fnPtr) { - if (shutdownPtr) + if (pHost) { - return shutdownPtr( - this->hostHandle, - this->domainId); + return pHost->CreateDelegate( + appDomainID, + wszAssemblyName, + wszClassName, + wszMethodName, + fnPtr); + } + return E_FAIL; + } + + virtual HRESULT STDMETHODCALLTYPE Authenticate( + /* [in] */ ULONGLONG authKey) + { + if (pHost) + { + return pHost->Authenticate( + authKey); + } + return E_FAIL; + } + + virtual HRESULT STDMETHODCALLTYPE SetStartupFlags( + /* [in] */ STARTUP_FLAGS dwFlags) + { + if (pHost) + { + return pHost->SetStartupFlags( + dwFlags); + } + return E_FAIL; + } + + virtual HRESULT STDMETHODCALLTYPE Start() + { + if (pHost) + { + return pHost->Start(); + } + return E_FAIL; + } + + virtual HRESULT STDMETHODCALLTYPE Stop() + { + if (pHost) + { + return pHost->Stop(); + } + return E_FAIL; + } + + virtual HRESULT STDMETHODCALLTYPE Release() + { + if (pHost) + { + return pHost->Release(); } return E_FAIL; } }; +#endif // Encapsulates the environment that CoreCLR will run in, including the TPALIST class HostEnvironment { private: // The path to this module - char m_hostPath[MAX_PATH]; - wchar_t m_hostPathW[MAX_PATH]; + wchar_t m_hostPath[MAX_PATH]; // The path to the directory containing this module - char m_hostDirectoryPath[MAX_PATH]; - wchar_t m_hostDirectoryPathW[MAX_PATH]; + wchar_t m_hostDirectoryPath[MAX_PATH]; // The name of this module, without the path - std::string m_hostBinaryName; - std::wstring m_hostBinaryNameW; + std::wstring m_hostBinaryName; // The path to the directory that CoreCLR is in - char m_coreCLRDirectoryPath[MAX_PATH]; - wchar_t m_coreCLRDirectoryPathW[MAX_PATH]; + wchar_t m_coreCLRDirectoryPath[MAX_PATH]; - void convertAnsiToWide(char* ansiArray, wchar_t* wideArray) - { - // Generate the wide version of the string and save its value; - // - // This is a two call function. The first call is to get the necessary length. - // The second call is to perform the actual operation. - int length = ::MultiByteToWideChar(CP_UTF8, 0, ansiArray, -1, NULL, 0); - if (0 < length) - { - LPWSTR result = new wchar_t[length]; - if (NULL != result) - { - length = ::MultiByteToWideChar(CP_UTF8, 0, ansiArray, -1, result, length); - if (0 < length) - { - wcscpy_s(wideArray, MAX_PATH, result); - } - delete[] result; // Free the allocated string to avoid a memory leak - } - } - } - - void convertWideToAnsi(wchar_t* wideArray, char* ansiArray) - { - // Generate the ansi version of the string and save its value; - // - // This is a two call function. The first call is to get the necessary length. - // The second call is to perform the actual operation. - int length = ::WideCharToMultiByte(CP_ACP, 0, wideArray, -1, NULL, 0, NULL, NULL); - if (0 < length) - { - LPSTR result = new char[length]; - if (NULL != result) - { - length = ::WideCharToMultiByte(CP_ACP, 0, wideArray, -1, result, length, NULL, NULL); - if (0 < length) - { - strcpy_s(ansiArray, MAX_PATH, result); - } - delete[] result; // Free the allocated string to avoid a memory leak - } - } - } + HMODULE m_coreCLRModule; public: HostEnvironment() + : m_coreCLRModule(0) { memset(m_hostPath, 0, sizeof(m_hostPath)); memset(m_hostDirectoryPath, 0, sizeof(m_hostDirectoryPath)); memset(m_coreCLRDirectoryPath, 0, sizeof(m_coreCLRDirectoryPath)); } - ~HostEnvironment() {} - - // Safely copies in a host path - void SetHostPath(PCSTR hostPath) + ~HostEnvironment() { - if (hostPath) + if (m_coreCLRModule) { - ::ExpandEnvironmentStringsA(hostPath, m_hostPath, MAX_PATH); - - convertAnsiToWide(m_hostPath, m_hostPathW); + // Free the module. This is done for completeness, but in fact CoreCLR.dll + // was pinned earlier so this call won't actually free it. The pinning is + // done because CoreCLR does not support unloading. + ::FreeLibrary(m_coreCLRModule); } } - void SetHostPathW(PCWSTR hostPath) + + // Safely copies in a host path + void SetHostPath(PCWSTR hostPath) { if (hostPath) { - ::ExpandEnvironmentStringsW(hostPath, m_hostPathW, MAX_PATH); - - convertWideToAnsi(m_hostPathW, m_hostPath); + ::ExpandEnvironmentStringsW(hostPath, m_hostPath, MAX_PATH); + //::wcsncpy_s(m_hostPath, hostPath, _TRUNCATE); } } // Returns the path to the host module - PCSTR GetHostPath() + PCWSTR GetHostPath() { return m_hostPath; } - PCWSTR GetHostPathW() - { - return m_hostPathW; - } - // Safely copies in a host binary name - void SetHostBinaryName(PCSTR hostBinaryName) + void SetHostBinaryName(PCWSTR hostBinaryName) { if (hostBinaryName) { - m_hostBinaryName = std::string(hostBinaryName); - } - } - - void SetHostBinaryNameW(PCWSTR hostBinaryName) - { - if (hostBinaryName) - { - m_hostBinaryNameW = std::wstring(hostBinaryName); + m_hostBinaryName = std::wstring(hostBinaryName); } } // Returns the name of the host module - PCSTR GetHostBinaryName() + PCWSTR GetHostBinaryName() { return m_hostBinaryName.c_str(); } - PCWSTR GetHostBinaryNameW() - { - return m_hostBinaryNameW.c_str(); - } - // Safely copies in a host directory path - void SetHostDirectoryPath(PCSTR hostDirPath) + void SetHostDirectoryPath(PCWSTR hostDirPath) { if (hostDirPath) { - ::ExpandEnvironmentStringsA(hostDirPath, m_hostDirectoryPath, MAX_PATH); - - convertAnsiToWide(m_hostDirectoryPath, m_hostDirectoryPathW); - } - } - - void SetHostDirectoryPathW(PCWSTR hostDirPath) - { - if (hostDirPath) - { - ::ExpandEnvironmentStringsW(hostDirPath, m_hostDirectoryPathW, MAX_PATH); - - convertWideToAnsi(m_hostDirectoryPathW, m_hostDirectoryPath); + ::ExpandEnvironmentStringsW(hostDirPath, m_hostDirectoryPath, MAX_PATH); + //::wcsncpy_s(m_hostDirectoryPath, hostDirPath, _TRUNCATE); } } // Returns the directory path of the host module - PCSTR GetHostDirectoryPath() + PCWSTR GetHostDirectoryPath() { return m_hostDirectoryPath; } - // Returns the directory path of the host module as a wide char string - PCWSTR GetHostDirectoryPathW() - { - return m_hostDirectoryPathW; - } - // Safely copies in a core clr directory path - void SetCoreCLRDirectoryPath(PCSTR hostClrPath) + void SetCoreCLRDirectoryPath(PCWSTR hostClrPath) { if (hostClrPath) { - ::ExpandEnvironmentStringsA(hostClrPath, m_coreCLRDirectoryPath, MAX_PATH); - - convertAnsiToWide(m_coreCLRDirectoryPath, m_coreCLRDirectoryPathW); - } - } - - void SetCoreCLRDirectoryPathW(PCWSTR hostClrPath) - { - if (hostClrPath) - { - ::ExpandEnvironmentStringsW(hostClrPath, m_coreCLRDirectoryPathW, MAX_PATH); - - convertWideToAnsi(m_coreCLRDirectoryPathW, m_coreCLRDirectoryPath); + ::ExpandEnvironmentStringsW(hostClrPath, m_coreCLRDirectoryPath, MAX_PATH); + //::wcsncpy_s(m_coreCLRDirectoryPath, hostClrPath, _TRUNCATE); } } // Returns the directory path of the host module - PCSTR GetCoreCLRDirectoryPath() + PCWSTR GetCoreCLRDirectoryPath() { return m_coreCLRDirectoryPath; } - // Returns the directory path of the host module - PCWSTR GetCoreCLRDirectoryPathW() + void SetCoreCLRModule(HMODULE module) { - return m_coreCLRDirectoryPathW; + m_coreCLRModule = module; } - - }; -} // namespace NativeMsh +} // namespace NativeMsh \ No newline at end of file diff --git a/src/powershell-native/nativemsh/pwrshcommon/NativeMsh.h b/src/powershell-native/nativemsh/pwrshcommon/NativeMsh.h index 924fc5e34..df477f4cc 100644 --- a/src/powershell-native/nativemsh/pwrshcommon/NativeMsh.h +++ b/src/powershell-native/nativemsh/pwrshcommon/NativeMsh.h @@ -17,20 +17,14 @@ #include "NativeMshConstants.h" #include "ClrHostWrapper.h" #include "SystemCallFacade.h" -#include "ConfigFileReader.h" #include "IPwrshCommonOutput.h" -#if !CORECLR -#include -#endif - namespace NativeMsh { class PwrshCommon { private: IPwrshCommonOutput* output; - ConfigFileReader* reader; SystemCallFacade* sysCalls; public: @@ -43,7 +37,6 @@ namespace NativeMsh // allocate them with "new". PwrshCommon( IPwrshCommonOutput* outObj, // Enables clients to specify how error messages are displayed or suppressed - ConfigFileReader* rdr, // Enables specification of how the config file is read. SystemCallFacade* systemCalls); // Wraps all calls to Windows APIs to allow for dependency injection via unit test ~PwrshCommon(); @@ -98,12 +91,17 @@ namespace NativeMsh __deref_out_opt PWSTR * pwszRuntimeVersion, __deref_out_opt PWSTR * pwszConsoleHostAssemblyName); +#if CORECLR unsigned int LaunchCoreCLR( ClrHostWrapper* hostWrapper, - HostEnvironment& hostEnvironment, - PCSTR friendlyName); + HostEnvironment& hostEnvironment); -#if !CORECLR + unsigned int CreateAppDomain( + ClrHostWrapper* hostWrapper, + PCWSTR friendlyName, + HostEnvironment& hostEnvironment); + +#else // !CORECLR // NOTE: // This must be ifdef'd out of the CoreCLR build because it uses .NET 1.0 // types that have been deprecated and removed from mscoree.h. @@ -115,6 +113,7 @@ namespace NativeMsh LPCWSTR wszMonadVersion, LPCWSTR wszRuntimeVersion, __in_ecount(1) ICorRuntimeHost** pCLR); + #endif // !CORECLR protected: @@ -171,21 +170,28 @@ namespace NativeMsh __out_ecount(1) int * lpMinorVersion); virtual bool DoesAssemblyExist( - std::string& fileToTest); + std::wstring& fileToTest); virtual void ProbeAssembly( - _In_z_ PCSTR directoryPath, - _In_z_ PCSTR assemblyName, - std::string& result); + _In_z_ PCWSTR directoryPath, + _In_z_ PCWSTR assemblyName, + std::wstring& result); virtual void GetTrustedAssemblyList( - PCSTR coreCLRDirectoryPath, - std::stringstream& assemblyList, + PCWSTR coreCLRDirectoryPath, + std::wstringstream& assemblyList, bool& listEmpty); virtual unsigned int IdentifyHostDirectory( HostEnvironment& hostEnvironment); + virtual HMODULE TryLoadCoreCLR( + _In_ PCWSTR directoryPath); + + virtual unsigned int InitializeClr( + _In_ ClrHostWrapper* hostWrapper, + _In_ HMODULE coreClrModule); + private: // Explicitly disallow copy construction and assignment PwrshCommon(const PwrshCommon&); diff --git a/src/powershell-native/nativemsh/pwrshcommon/SystemCallFacade.h b/src/powershell-native/nativemsh/pwrshcommon/SystemCallFacade.h index c44d6a314..877f3d2b0 100644 --- a/src/powershell-native/nativemsh/pwrshcommon/SystemCallFacade.h +++ b/src/powershell-native/nativemsh/pwrshcommon/SystemCallFacade.h @@ -32,13 +32,18 @@ namespace NativeMsh _Reserved_ HANDLE hFile, _In_ DWORD dwFlags) = 0; - virtual DWORD WINAPI GetModuleFileNameA( + virtual DWORD WINAPI GetModuleFileNameW( _In_opt_ HMODULE hModule, - _Out_ LPSTR lpFilename, + _Out_ PWSTR lpFilename, _In_ DWORD nSize) = 0; - virtual HMODULE WINAPI GetModuleHandleA( - _In_opt_ PCSTR lpModuleName) = 0; + virtual HMODULE WINAPI GetModuleHandleW( + _In_opt_ PCWSTR lpModuleName) = 0; + + virtual BOOL WINAPI GetModuleHandleExW( + _In_ DWORD dwFlags, + _In_opt_ PCWSTR lpModuleName, + _Out_ HMODULE *phModule) = 0; virtual FARPROC WINAPI GetProcAddress( _In_ HMODULE hModule, @@ -48,13 +53,12 @@ namespace NativeMsh _In_ HMODULE hModule) = 0; // File Manipulation Wrappers - virtual errno_t fopen_s( - FILE** file, - const char *filename, - const char *mode) = 0; + virtual FILE* _wfopen( + const wchar_t *filename, + const wchar_t *mode) = 0; virtual int fclose( FILE *stream) = 0; }; -} // namespace NativeMsh +} // namespace NativeMsh \ No newline at end of file diff --git a/src/powershell-native/nativemsh/pwrshcommon/WinSystemCallFacade.cpp b/src/powershell-native/nativemsh/pwrshcommon/WinSystemCallFacade.cpp index 0c61d5bf6..8ccfb2b25 100644 --- a/src/powershell-native/nativemsh/pwrshcommon/WinSystemCallFacade.cpp +++ b/src/powershell-native/nativemsh/pwrshcommon/WinSystemCallFacade.cpp @@ -14,7 +14,7 @@ namespace NativeMsh { HMODULE WINAPI WinSystemCallFacade::LoadLibraryExW( - _In_ LPCWSTR lpFileName, + _In_ LPCTSTR lpFileName, _Reserved_ HANDLE hFile, _In_ DWORD dwFlags) { @@ -24,20 +24,28 @@ namespace NativeMsh #pragma prefast(push) #pragma prefast (disable: 26006) // Possibly incorrect single element annotation on string buffer - This is a thin wrapper around a system call, so it's behavior is not controllable. - DWORD WINAPI WinSystemCallFacade::GetModuleFileNameA( + DWORD WINAPI WinSystemCallFacade::GetModuleFileNameW( _In_opt_ HMODULE hModule, - _Out_ LPSTR lpFilename, // _Out_writes_to_(nSize, return +1) OR __out_ecount_part(nSize, return + 1)? __out_ecount(nSize) + _Out_ LPTSTR lpFilename, // _Out_writes_to_(nSize, return +1) OR __out_ecount_part(nSize, return + 1)? __out_ecount(nSize) _In_ DWORD nSize) { - return ::GetModuleFileNameA(hModule, lpFilename, nSize); + return ::GetModuleFileNameW(hModule, lpFilename, nSize); } #pragma prefast(pop) - HMODULE WINAPI WinSystemCallFacade::GetModuleHandleA( - _In_opt_ LPCSTR lpModuleName) + HMODULE WINAPI WinSystemCallFacade::GetModuleHandleW( + _In_opt_ LPCTSTR lpModuleName) { - return ::GetModuleHandleA(lpModuleName); + return ::GetModuleHandleW(lpModuleName); + } + + BOOL WINAPI WinSystemCallFacade::GetModuleHandleExW( + _In_ DWORD dwFlags, + _In_opt_ LPCTSTR lpModuleName, + _Out_ HMODULE *phModule) + { + return ::GetModuleHandleExW(dwFlags, lpModuleName, phModule); } FARPROC WINAPI WinSystemCallFacade::GetProcAddress( @@ -53,12 +61,11 @@ namespace NativeMsh return ::FreeLibrary(hModule); } - errno_t WinSystemCallFacade::fopen_s( - FILE** file, - const char *filename, - const char *mode) + FILE* WinSystemCallFacade::_wfopen( + const wchar_t *filename, + const wchar_t *mode) { - return ::fopen_s(file, filename, mode); + return ::_wfopen(filename, mode); } int WinSystemCallFacade::fclose( @@ -67,4 +74,4 @@ namespace NativeMsh return ::fclose(stream); } -} // namespace NativeMsh +} // namespace NativeMsh \ No newline at end of file diff --git a/src/powershell-native/nativemsh/pwrshcommon/WinSystemCallFacade.h b/src/powershell-native/nativemsh/pwrshcommon/WinSystemCallFacade.h index 76ecf01f3..bdaa3a116 100644 --- a/src/powershell-native/nativemsh/pwrshcommon/WinSystemCallFacade.h +++ b/src/powershell-native/nativemsh/pwrshcommon/WinSystemCallFacade.h @@ -30,13 +30,18 @@ namespace NativeMsh _Reserved_ HANDLE hFile, _In_ DWORD dwFlags); - virtual DWORD WINAPI GetModuleFileNameA( + virtual DWORD WINAPI GetModuleFileNameW( _In_opt_ HMODULE hModule, - _Out_ LPSTR lpFilename, + _Out_ PWSTR lpFilename, _In_ DWORD nSize); - virtual HMODULE WINAPI GetModuleHandleA( - _In_opt_ LPCSTR lpModuleName); + virtual HMODULE WINAPI GetModuleHandleW( + _In_opt_ PCWSTR lpModuleName); + + virtual BOOL WINAPI GetModuleHandleExW( + _In_ DWORD dwFlags, + _In_opt_ PCWSTR lpModuleName, + _Out_ HMODULE *phModule); virtual FARPROC WINAPI GetProcAddress( _In_ HMODULE hModule, @@ -46,13 +51,12 @@ namespace NativeMsh _In_ HMODULE hModule); // File Manipulation Wrappers - virtual errno_t fopen_s( - FILE** file, - const char *filename, - const char *mode); + virtual FILE* _wfopen( + const wchar_t *filename, + const wchar_t *mode); virtual int fclose( FILE *stream); }; -} // namespace NativeMsh +} // namespace NativeMsh \ No newline at end of file diff --git a/src/powershell-native/nativemsh/pwrshcommon/pwrshcommon.cpp b/src/powershell-native/nativemsh/pwrshcommon/pwrshcommon.cpp index fef838058..0f9deb37e 100644 --- a/src/powershell-native/nativemsh/pwrshcommon/pwrshcommon.cpp +++ b/src/powershell-native/nativemsh/pwrshcommon/pwrshcommon.cpp @@ -667,193 +667,182 @@ namespace NativeMsh // System.Management.Automation must not be listed here. I should exist on the APP_PATH. // // NOTE: The names must not include the .dll extension because it will be added programmatically. - static PCSTR trustedAssemblies[] = + static PCWSTR trustedAssemblies[] = { - "Microsoft.CSharp", - "Microsoft.VisualBasic", - "Microsoft.Win32.Primitives", - "Microsoft.Win32.Registry.AccessControl", - "Microsoft.Win32.Registry", - "mscorlib", - "System.AppContext", - "System.Buffers", - "System.Collections.Concurrent", - "System.Collections", - "System.Collections.Immutable", - "System.Collections.NonGeneric", - "System.Collections.Specialized", - "System.ComponentModel.Annotations", - "System.ComponentModel.DataAnnotations", - "System.ComponentModel", - "System.ComponentModel.EventBasedAsync", - "System.ComponentModel.Primitives", - "System.ComponentModel.TypeConverter", - "System.Console", - "System.Core", - "System.Data.Common", - "System.Diagnostics.Contracts", - "System.Diagnostics.Debug", - "System.Diagnostics.DiagnosticSource", - "System.Diagnostics.FileVersionInfo", - "System.Diagnostics.Process", - "System.Diagnostics.StackTrace", - "System.Diagnostics.TextWriterTraceListener", - "System.Diagnostics.Tools", - "System.Diagnostics.TraceSource", - "System.Diagnostics.Tracing", - "System", - "System.Dynamic.Runtime", - "System.Globalization.Calendars", - "System.Globalization", - "System.Globalization.Extensions", - "System.IO.Compression", - "System.IO.Compression.ZipFile", - "System.IO", - "System.IO.FileSystem.AccessControl", - "System.IO.FileSystem", - "System.IO.FileSystem.DriveInfo", - "System.IO.FileSystem.Primitives", - "System.IO.FileSystem.Watcher", - "System.IO.MemoryMappedFiles", - "System.IO.Packaging", - "System.IO.Pipes", - "System.IO.UnmanagedMemoryStream", - "System.Linq", - "System.Linq.Expressions", - "System.Linq.Parallel", - "System.Linq.Queryable", - "System.Net", - "System.Net.Http", - "System.Net.Http.WinHttpHandler", - "System.Net.NameResolution", - "System.Net.NetworkInformation", - "System.Net.Ping", - "System.Net.Primitives", - "System.Net.Requests", - "System.Net.Security", - "System.Net.Sockets", - "System.Net.WebHeaderCollection", - "System.Net.WebSockets.Client", - "System.Net.WebSockets", - "System.Numerics", - "System.Numerics.Vectors", - "System.ObjectModel", - "System.Private.DataContractSerialization", - "System.Private.ServiceModel", - "System.Private.Uri", - "System.Reflection.DispatchProxy", - "System.Reflection", - "System.Reflection.Emit", - "System.Reflection.Emit.ILGeneration", - "System.Reflection.Emit.Lightweight", - "System.Reflection.Extensions", - "System.Reflection.Metadata", - "System.Reflection.Primitives", - "System.Reflection.TypeExtensions", - "System.Resources.ReaderWriter", - "System.Resources.ResourceManager", - "System.Runtime.CompilerServices.VisualC", - "System.Runtime", - "System.Runtime.Extensions", - "System.Runtime.Handles", - "System.Runtime.InteropServices", - "System.Runtime.InteropServices.PInvoke", - "System.Runtime.InteropServices.RuntimeInformation", - "System.Runtime.Loader", - "System.Runtime.Numerics", - "System.Runtime.Serialization", - "System.Runtime.Serialization.Json", - "System.Runtime.Serialization.Primitives", - "System.Runtime.Serialization.Xml", - "System.Security.AccessControl", - "System.Security.Claims", - "System.Security.Cryptography.Algorithms", - "System.Security.Cryptography.Cng", - "System.Security.Cryptography.Csp", - "System.Security.Cryptography.Encoding", - "System.Security.Cryptography.OpenSsl", - "System.Security.Cryptography.Primitives", - "System.Security.Cryptography.X509Certificates", - "System.Security.Principal", - "System.Security.Principal.Windows", - "System.Security.SecureString", - "System.ServiceModel", - "System.ServiceModel.Duplex", - "System.ServiceModel.Http", - "System.ServiceModel.NetTcp", - "System.ServiceModel.Primitives", - "System.ServiceModel.Security", - "System.ServiceModel.Web", - "System.ServiceProcess.ServiceController", - "System.Text.Encoding.CodePages", - "System.Text.Encoding", - "System.Text.Encoding.Extensions", - "System.Text.Encodings.Web", - "System.Text.RegularExpressions", - "System.Threading.AccessControl", - "System.Threading", - "System.Threading.Overlapped", - "System.Threading.Tasks.Dataflow", - "System.Threading.Tasks", - "System.Threading.Tasks.Extensions", - "System.Threading.Tasks.Parallel", - "System.Threading.Thread", - "System.Threading.ThreadPool", - "System.Threading.Timer", - "System.Windows", - "System.Xml", - "System.Xml.Linq", - "System.Xml.ReaderWriter", - "System.Xml.Serialization", - "System.Xml.XDocument", - "System.Xml.XmlDocument", - "System.Xml.XmlSerializer", - "System.Xml.XPath", - "System.Xml.XPath.XDocument", - "System.Xml.XPath.XmlDocument", - "Microsoft.PowerShell.CoreCLR.AssemblyLoadContext" + L"Microsoft.CSharp", + L"Microsoft.VisualBasic", + L"Microsoft.Win32.Primitives", + L"Microsoft.Win32.Registry.AccessControl", + L"Microsoft.Win32.Registry", + L"mscorlib", + L"System.AppContext", + L"System.Buffers", + L"System.Collections.Concurrent", + L"System.Collections", + L"System.Collections.Immutable", + L"System.Collections.NonGeneric", + L"System.Collections.Specialized", + L"System.ComponentModel.Annotations", + L"System.ComponentModel.DataAnnotations", + L"System.ComponentModel", + L"System.ComponentModel.EventBasedAsync", + L"System.ComponentModel.Primitives", + L"System.ComponentModel.TypeConverter", + L"System.Console", + L"System.Core", + L"System.Data.Common", + L"System.Diagnostics.Contracts", + L"System.Diagnostics.Debug", + L"System.Diagnostics.DiagnosticSource", + L"System.Diagnostics.FileVersionInfo", + L"System.Diagnostics.Process", + L"System.Diagnostics.StackTrace", + L"System.Diagnostics.TextWriterTraceListener", + L"System.Diagnostics.Tools", + L"System.Diagnostics.TraceSource", + L"System.Diagnostics.Tracing", + L"System", + L"System.Dynamic.Runtime", + L"System.Globalization.Calendars", + L"System.Globalization", + L"System.Globalization.Extensions", + L"System.IO.Compression", + L"System.IO.Compression.ZipFile", + L"System.IO", + L"System.IO.FileSystem.AccessControl", + L"System.IO.FileSystem", + L"System.IO.FileSystem.DriveInfo", + L"System.IO.FileSystem.Primitives", + L"System.IO.FileSystem.Watcher", + L"System.IO.MemoryMappedFiles", + L"System.IO.Packaging", + L"System.IO.Pipes", + L"System.IO.UnmanagedMemoryStream", + L"System.Linq", + L"System.Linq.Expressions", + L"System.Linq.Parallel", + L"System.Linq.Queryable", + L"System.Net", + L"System.Net.Http", + L"System.Net.Http.WinHttpHandler", + L"System.Net.NameResolution", + L"System.Net.NetworkInformation", + L"System.Net.Ping", + L"System.Net.Primitives", + L"System.Net.Requests", + L"System.Net.Security", + L"System.Net.Sockets", + L"System.Net.WebHeaderCollection", + L"System.Net.WebSockets.Client", + L"System.Net.WebSockets", + L"System.Numerics", + L"System.Numerics.Vectors", + L"System.ObjectModel", + L"System.Private.DataContractSerialization", + L"System.Private.ServiceModel", + L"System.Private.Uri", + L"System.Reflection.DispatchProxy", + L"System.Reflection", + L"System.Reflection.Emit", + L"System.Reflection.Emit.ILGeneration", + L"System.Reflection.Emit.Lightweight", + L"System.Reflection.Extensions", + L"System.Reflection.Metadata", + L"System.Reflection.Primitives", + L"System.Reflection.TypeExtensions", + L"System.Resources.ReaderWriter", + L"System.Resources.ResourceManager", + L"System.Runtime.CompilerServices.VisualC", + L"System.Runtime", + L"System.Runtime.Extensions", + L"System.Runtime.Handles", + L"System.Runtime.InteropServices", + L"System.Runtime.InteropServices.PInvoke", + L"System.Runtime.InteropServices.RuntimeInformation", + L"System.Runtime.Loader", + L"System.Runtime.Numerics", + L"System.Runtime.Serialization", + L"System.Runtime.Serialization.Json", + L"System.Runtime.Serialization.Primitives", + L"System.Runtime.Serialization.Xml", + L"System.Security.AccessControl", + L"System.Security.Claims", + L"System.Security.Cryptography.Algorithms", + L"System.Security.Cryptography.Cng", + L"System.Security.Cryptography.Csp", + L"System.Security.Cryptography.Encoding", + L"System.Security.Cryptography.OpenSsl", + L"System.Security.Cryptography.Primitives", + L"System.Security.Cryptography.X509Certificates", + L"System.Security.Principal", + L"System.Security.Principal.Windows", + L"System.Security.SecureString", + L"System.ServiceModel", + L"System.ServiceModel.Duplex", + L"System.ServiceModel.Http", + L"System.ServiceModel.NetTcp", + L"System.ServiceModel.Primitives", + L"System.ServiceModel.Security", + L"System.ServiceModel.Web", + L"System.ServiceProcess.ServiceController", + L"System.Text.Encoding.CodePages", + L"System.Text.Encoding", + L"System.Text.Encoding.Extensions", + L"System.Text.Encodings.Web", + L"System.Text.RegularExpressions", + L"System.Threading.AccessControl", + L"System.Threading", + L"System.Threading.Overlapped", + L"System.Threading.Tasks.Dataflow", + L"System.Threading.Tasks", + L"System.Threading.Tasks.Extensions", + L"System.Threading.Tasks.Parallel", + L"System.Threading.Thread", + L"System.Threading.ThreadPool", + L"System.Threading.Timer", + L"System.Windows", + L"System.Xml", + L"System.Xml.Linq", + L"System.Xml.ReaderWriter", + L"System.Xml.Serialization", + L"System.Xml.XDocument", + L"System.Xml.XmlDocument", + L"System.Xml.XmlSerializer", + L"System.Xml.XPath", + L"System.Xml.XPath.XDocument", + L"System.Xml.XPath.XmlDocument", + L"Microsoft.PowerShell.CoreCLR.AssemblyLoadContext" }; // Define the function pointer for the CLR entry point typedef HRESULT(STDAPICALLTYPE *GetCLRRuntimeHostFp)(REFIID riid, IUnknown** pUnk); // The name of the CoreCLR native runtime DLL. - static PCSTR coreClrDll = "CoreCLR.dll"; + static PCWSTR coreClrDll = L"CoreCLR.dll"; - // The location where CoreCLR is expected to be installed for inbox PowerShell. If CoreCLR.dll isn't + // The location where CoreCLR is expected to be installed. If CoreCLR.dll isn't // found in the same directory as the host, it will be looked for here. - static PCSTR coreCLRInstallDirectory = "%windir%\\system32\\DotNetCore\\v1.0\\"; + static PCWSTR coreCLRInstallDirectory = L"%windir%\\system32\\DotNetCore\\v1.0\\"; - // The location where CoreCLR PowerShell Ext binaries are expected to be installed for inbox PowerShell. - static PCSTR coreCLRPowerShellExtInstallDirectory = "%windir%\\system32\\CoreClrPowerShellExt\\v1.0\\"; + // The location where CoreCLR PowerShell Ext binaries are expected to be installed. + static PCWSTR coreCLRPowerShellExtInstallDirectory = L"%windir%\\system32\\CoreClrPowerShellExt\\v1.0\\"; - // The default PowerShell install directory for inbox PowerShell. - // This location may be overridden by placing a config file in the same directory as the PowerShell host. - static PCSTR powerShellInstallPath = "%windir%\\System32\\WindowsPowerShell\\v1.0\\"; + // The default PowerShell install directory. This location may be overridden through a config file in %windir%\System32. + static PCWSTR powerShellInstallPath = L"%windir%\\System32\\WindowsPowerShell\\v1.0\\"; unsigned int PwrshCommon::IdentifyHostDirectory( HostEnvironment& hostEnvironment) { - // Discover the path to the plugin or the executable (pwrshplugin.dll or powershell.exe). - // For PowerShell Core, the plugin no longer resides in %windir%\\system32 (it is in a sub-directory). - // If pwrshplugin.dll is not loaded, it means that this is running via powershell.exe. + // Discover the path to the exe's module (powershell.exe or wsmprovhost.exe). + // For remoting, this is expected to be %windir%\system32 since that is the location of wsmprovhost.exe. wchar_t hostPath[MAX_PATH]; - DWORD thisModuleLength; + DWORD thisModuleLength = sysCalls->GetModuleFileNameW(sysCalls->GetModuleHandleW(NULL), hostPath, MAX_PATH); - if (GetModuleHandleW(L"pwrshplugin.dll")) - { - thisModuleLength = GetModuleFileNameW(GetModuleHandleW(L"pwrshplugin.dll"), hostPath, MAX_PATH); - } - else - { - thisModuleLength = GetModuleFileNameW(GetModuleHandleW(NULL), hostPath, MAX_PATH); - } - if (0 == thisModuleLength) // Greater than zero means it is the length of the fully qualified path (without the NULL character) + if (0 == thisModuleLength) { // TODO: Use GetLastError() to find the specific error # return EXIT_CODE_INIT_FAILURE; } - // Search for the last backslash in the host path. int lastBackslashIndex; for (lastBackslashIndex = thisModuleLength - 1; lastBackslashIndex >= 0; lastBackslashIndex--) @@ -865,62 +854,106 @@ namespace NativeMsh } // The remaining part of the path after the last '\' is the binary name. - hostEnvironment.SetHostBinaryNameW(hostPath + lastBackslashIndex + 1); + hostEnvironment.SetHostBinaryName(hostPath + lastBackslashIndex + 1); // Copy the directory path portion of the path hostPath[lastBackslashIndex + 1] = '\0'; - hostEnvironment.SetHostPathW(hostPath); + hostEnvironment.SetHostPath(hostPath); - // Read the config file to determine the appropriate host path and CoreCLR path to use. - unsigned int result = reader->Read(hostPath); - if (EXIT_CODE_SUCCESS == result) + hostEnvironment.SetHostDirectoryPath(powerShellInstallPath); + + return EXIT_CODE_SUCCESS; + } + + // Attempts to load CoreCLR.dll from the specified directory. + // On success pins the dll, sets coreCLRDirectoryPath and returns the HMODULE. + // On failure returns NULL. + HMODULE PwrshCommon::TryLoadCoreCLR( + _In_ PCWSTR directoryPath) + { + std::wstring coreCLRPath(directoryPath); + coreCLRPath += coreClrDll; + + HMODULE result = sysCalls->LoadLibraryExW(coreCLRPath.c_str(), NULL, 0); + if (!result) { - // The config file was successfully parsed. Use those directories. - hostEnvironment.SetHostDirectoryPathW(reader->GetPathToPowerShell().c_str()); - hostEnvironment.SetCoreCLRDirectoryPathW(reader->GetPathToCoreClr().c_str()); + return NULL; } - else + + // Pin the module - CoreCLR.dll does not support being unloaded. + HMODULE dummy_coreCLRModule; + if (!sysCalls->GetModuleHandleExW(GET_MODULE_HANDLE_EX_FLAG_PIN, coreCLRPath.c_str(), &dummy_coreCLRModule)) { - // There was an issue accessing or parsing the config file OR - // we are working for the EXE. - // - // TODO: This should not be the fallback for inbox PowerShell.exe. - // It should use coreCLRInstallDirectory and coreCLRPowerShellExtInstallDirectory. - // - // Use the directory detected via GetModuleFileName + GetModuleHandle - hostEnvironment.SetHostDirectoryPathW(hostPath); - // At the moment, CoreCLR is in the same directory as PowerShell Core. - // This path must be modified if we decide to use a different directory. - hostEnvironment.SetCoreCLRDirectoryPathW(hostPath); + return NULL; } + + return result; + } + + unsigned int PwrshCommon::InitializeClr( + _In_ ClrHostWrapper* hostWrapper, + _In_ HMODULE coreClrModule) + { +#if CORECLR + // Get the function pointer for "GetCLRRuntimeHost" + GetCLRRuntimeHostFp getCLRRuntimeHostfp = (GetCLRRuntimeHostFp)sysCalls->GetProcAddress(coreClrModule, "GetCLRRuntimeHost"); + if (getCLRRuntimeHostfp == NULL) + { + return EXIT_CODE_INIT_FAILURE; + } + + // Get the CLR runtime host + ICLRRuntimeHost2* pHost = NULL; + HRESULT hResult = getCLRRuntimeHostfp(IID_ICLRRuntimeHost2, (IUnknown**)&pHost); + if (FAILED(hResult)) + { + return EXIT_CODE_INIT_FAILURE; + } + + hostWrapper->SetClrHost(pHost); + // Authenticate with either + // CORECLR_HOST_AUTHENTICATION_KEY or + // CORECLR_HOST_AUTHENTICATION_KEY_NONGEN + hResult = hostWrapper->Authenticate(CORECLR_HOST_AUTHENTICATION_KEY); + if (FAILED(hResult)) + { + return EXIT_CODE_INIT_FAILURE; + } + + hostWrapper->SetStartupFlags((STARTUP_FLAGS)(STARTUP_SINGLE_APPDOMAIN | STARTUP_LOADER_OPTIMIZATION_SINGLE_DOMAIN)); + + hResult = hostWrapper->Start(); + if (FAILED(hResult)) + { + return EXIT_CODE_INIT_FAILURE; + } +#endif return EXIT_CODE_SUCCESS; } bool PwrshCommon::DoesAssemblyExist( - std::string& fileToTest) + std::wstring& fileToTest) { - //FILE *file = sysCalls->fopen(fileToTest.c_str(), "r"); // TODO: Use fopen_s? - FILE *file = NULL; - errno_t status = sysCalls->fopen_s(&file, fileToTest.c_str(), "r"); + FILE *file = sysCalls->_wfopen(fileToTest.c_str(), L"r"); if (file != NULL) { sysCalls->fclose(file); - return (status == 0); + return true; } return false; } // This assumes that directoryPath already includes a trailing "\\" void PwrshCommon::ProbeAssembly( - _In_z_ PCSTR directoryPath, - _In_z_ PCSTR assemblyName, - std::string& result) + _In_z_ PCWSTR directoryPath, + _In_z_ PCWSTR assemblyName, + std::wstring& result) { - PCSTR niExtension = ".ni.dll"; - PCSTR ilExtension = ".dll"; + PCWSTR niExtension = L".ni.dll"; + PCWSTR ilExtension = L".dll"; // Test NI extension first because it is preferable to IL - std::string fileToTest(directoryPath); + std::wstring fileToTest(directoryPath); fileToTest += assemblyName; fileToTest += niExtension; if (DoesAssemblyExist(fileToTest)) { @@ -940,13 +973,13 @@ namespace NativeMsh // Returns the semicolon-separated list of paths to runtime dlls that are considered trusted. // Do not put powershell assemblies in the TPA list as it will cause 'Security Transparent V.S. Security Critical' error. void PwrshCommon::GetTrustedAssemblyList( - PCSTR coreCLRDirectoryPath, - std::stringstream& assemblyList, + PCWSTR coreCLRDirectoryPath, + std::wstringstream& assemblyList, bool& listEmpty) { - for (const char* &assembly : trustedAssemblies) + for (const wchar_t * &assembly : trustedAssemblies) { - std::string assemblyPath; + std::wstring assemblyPath; ProbeAssembly(coreCLRDirectoryPath, assembly, assemblyPath); if (assemblyPath.length() > 0) @@ -954,7 +987,7 @@ namespace NativeMsh if (listEmpty) listEmpty = false; else - assemblyList << ";"; + assemblyList << L";"; assemblyList << assemblyPath; } } @@ -990,26 +1023,20 @@ namespace NativeMsh // PwrshCommon::PwrshCommon() - : output(new PwrshCommonOutputDefault()), reader(new ConfigFileReader()), sysCalls(new WinSystemCallFacade()) + : output(new PwrshCommonOutputDefault()), sysCalls(new WinSystemCallFacade()) { } PwrshCommon::PwrshCommon( IPwrshCommonOutput* outObj, - ConfigFileReader* rdr, SystemCallFacade* systemCalls) - : output(outObj), reader(rdr), sysCalls(systemCalls) + : output(outObj), sysCalls(systemCalls) { if (NULL == output) { output = new PwrshCommonOutputDefault(); } - if (NULL == reader) - { - reader = new ConfigFileReader(); - } - if (NULL == sysCalls) { sysCalls = new WinSystemCallFacade(); @@ -1024,12 +1051,6 @@ namespace NativeMsh output = NULL; } - if (reader) - { - delete reader; - reader = NULL; - } - if (sysCalls) { delete sysCalls; @@ -1330,10 +1351,10 @@ namespace NativeMsh pwszRuntimeVersion, L"ConsoleHostAssemblyName", pwszConsoleHostAssemblyName); } + #if CORECLR unsigned int PwrshCommon::LaunchCoreCLR( ClrHostWrapper* hostWrapper, - HostEnvironment& hostEnvironment, - PCSTR friendlyName) + HostEnvironment& hostEnvironment) { unsigned int exitCode = this->IdentifyHostDirectory(hostEnvironment); if (EXIT_CODE_SUCCESS != exitCode) @@ -1342,57 +1363,131 @@ namespace NativeMsh return exitCode; } - exitCode = hostWrapper->SetupWrapper(hostEnvironment.GetCoreCLRDirectoryPath()); - if (EXIT_CODE_SUCCESS != exitCode) - { - this->output->DisplayMessage(false, g_STARTING_CLR_FAILED, GetLastError()); - return exitCode; - } - - const int nMaxProps = 8; - LPCSTR props[nMaxProps]; - LPCSTR vals[nMaxProps]; - int nProps = 0; - - // If I do not include my managed enload point dll in this list, I get a security error. - std::stringstream assemblyList; - bool listEmpty = true; - this->GetTrustedAssemblyList(hostEnvironment.GetCoreCLRDirectoryPath(), assemblyList, listEmpty); - - char coreCLRPowerShellExtInstallPath[MAX_PATH]; - ::ExpandEnvironmentStringsA(coreCLRPowerShellExtInstallDirectory, coreCLRPowerShellExtInstallPath, MAX_PATH); - this->GetTrustedAssemblyList(coreCLRPowerShellExtInstallPath, assemblyList, listEmpty); - - props[nProps] = "TRUSTED_PLATFORM_ASSEMBLIES"; - std::string tempStr = assemblyList.str(); - vals[nProps] = tempStr.c_str(); - nProps++; - - props[nProps] = "APP_PATHS"; - vals[nProps] = ""; // Used to be hostEnvironment.GetHostDirectoryPath() - nProps++; - - props[nProps] = "APP_NI_PATHS"; - vals[nProps] = ""; // Used to be hostEnvironment.GetHostDirectoryPath() - nProps++; - - int hr = hostWrapper->InitializeClr( - hostEnvironment.GetHostDirectoryPath(), - friendlyName, - nProps, - props, - vals); - - if (FAILED(hr)) + // Try to load from the well-known location. + wchar_t coreCLRInstallPath[MAX_PATH]; + exitCode = ::ExpandEnvironmentStringsW(coreCLRInstallDirectory, coreCLRInstallPath, MAX_PATH); + if (0 == exitCode || _countof(coreCLRInstallPath) <= exitCode) { this->output->DisplayMessage(false, g_STARTING_CLR_FAILED, GetLastError()); return EXIT_CODE_INIT_FAILURE; } + HMODULE coreClrModule = this->TryLoadCoreCLR(coreCLRInstallPath); + + if (coreClrModule) + { + // Save the directory that CoreCLR was found in + WCHAR coreCLRDirectoryPath[MAX_PATH]; + DWORD modulePathLength = sysCalls->GetModuleFileNameW(coreClrModule, coreCLRDirectoryPath, MAX_PATH); + + // Search for the last backslash and terminate it there to keep just the directory path with trailing slash + for (int lastBackslashIndex = modulePathLength - 1; lastBackslashIndex >= 0; lastBackslashIndex--) + { + if (coreCLRDirectoryPath[lastBackslashIndex] == L'\\') + { + coreCLRDirectoryPath[lastBackslashIndex + 1] = L'\0'; + break; + } + } + hostEnvironment.SetCoreCLRDirectoryPath(coreCLRDirectoryPath); + } + else + { + this->output->DisplayMessage(false, g_STARTING_CLR_FAILED, GetLastError()); + return EXIT_CODE_INIT_FAILURE; + } + + exitCode = this->InitializeClr(hostWrapper, coreClrModule); + if (EXIT_CODE_SUCCESS != exitCode) + { + this->output->DisplayMessage(false, g_STARTING_CLR_FAILED, GetLastError()); + return exitCode; + } + + hostEnvironment.SetCoreCLRModule(coreClrModule); + + return exitCode; + } + + unsigned int PwrshCommon::CreateAppDomain( + ClrHostWrapper* hostWrapper, + PCWSTR friendlyName, + HostEnvironment& hostEnvironment) + { + const int nMaxProps = 8; + LPCWSTR props[nMaxProps]; + LPCWSTR vals[nMaxProps]; + + if (!hostWrapper->IsInitialized()) + { + return EXIT_CODE_INIT_FAILURE; + } + + //PAL_LeaveHolder holder; + DWORD dwDomainFlags = 0; + dwDomainFlags = APPDOMAIN_SECURITY_DEFAULT; + dwDomainFlags |= APPDOMAIN_ENABLE_ASSEMBLY_LOADFILE; + dwDomainFlags |= APPDOMAIN_DISABLE_TRANSPARENCY_ENFORCEMENT; + + // By default CoreCLR only allows platform neutral assembly to be run. To allow + // assemblies marked as platform specific, include this flag + dwDomainFlags |= APPDOMAIN_ENABLE_PLATFORM_SPECIFIC_APPS; + // Enable PInvoke + dwDomainFlags |= APPDOMAIN_ENABLE_PINVOKE_AND_CLASSIC_COMINTEROP; + // This will not tear down an application if a managed exception goes unhandled + dwDomainFlags |= APPDOMAIN_IGNORE_UNHANDLED_EXCEPTIONS; + + int nProps = 0; + props[nProps] = L"APPBASE"; + vals[nProps] = hostEnvironment.GetHostDirectoryPath(); + nProps++; + + // If I do not include my managed enload point dll in this list, I get a security error. + std::wstringstream assemblyList; + bool listEmpty = true; + this->GetTrustedAssemblyList(hostEnvironment.GetCoreCLRDirectoryPath(), assemblyList, listEmpty); + + wchar_t coreCLRPowerShellExtInstallPath[MAX_PATH]; + ::ExpandEnvironmentStringsW(coreCLRPowerShellExtInstallDirectory, coreCLRPowerShellExtInstallPath, MAX_PATH); + this->GetTrustedAssemblyList(coreCLRPowerShellExtInstallPath, assemblyList, listEmpty); + + props[nProps] = L"TRUSTED_PLATFORM_ASSEMBLIES"; + std::wstring tempStr = assemblyList.str(); + vals[nProps] = tempStr.c_str(); + nProps++; + + props[nProps] = L"APP_PATHS"; + vals[nProps] = hostEnvironment.GetHostDirectoryPath(); + nProps++; + + props[nProps] = L"APP_NI_PATHS"; + vals[nProps] = hostEnvironment.GetHostDirectoryPath(); + nProps++; + + // Create the customized AppDomainManager out of the SandboxHelper class + DWORD appDomainId = INVALID_APPDOMAIN_ID; + HRESULT hr = hostWrapper->CreateAppDomainWithManager( + friendlyName, + dwDomainFlags, + NULL, // AppDomainManager is no longer required now that we can use AssemblyLoadContext to access arbitrary assemblies from within SMA.dll + NULL, + nProps, + props, + vals, + &appDomainId); + if (FAILED(hr)) + { + //LONG systemErrorCode = GetLastError(); + this->output->DisplayMessage(false, g_GETTING_DEFAULT_DOMAIN_FAILED, hr); + + return EXIT_CODE_INIT_FAILURE; + } + hostWrapper->SetAppDomainId(appDomainId); return EXIT_CODE_SUCCESS; } -#if !CORECLR + #else // !CORECLR + // NOTE: // This must be ifdef'd out of the CoreCLR build because it uses .NET 1.0 // types that have been deprecated and removed from mscoree.h. @@ -1455,7 +1550,7 @@ namespace NativeMsh return exitCode; } -#endif // !CORECLR + #endif // !CORECLR #pragma prefast(pop) diff --git a/src/powershell-native/nativemsh/pwrshexe/CssMainEntry.cpp b/src/powershell-native/nativemsh/pwrshexe/CssMainEntry.cpp index c8a201760..038ca0299 100644 --- a/src/powershell-native/nativemsh/pwrshexe/CssMainEntry.cpp +++ b/src/powershell-native/nativemsh/pwrshexe/CssMainEntry.cpp @@ -12,13 +12,10 @@ #include #include #include -#if !CORECLR - #include "mscoree.h" -#endif +#include "mscoree.h" #include "NativeMsh.h" #include "ClrHostWrapper.h" #include "OutputWriter.h" -#include "ConfigFileReader.h" #include "WinSystemCallFacade.h" namespace NativeMsh @@ -36,10 +33,10 @@ namespace NativeMsh // All these objects will be destroyed when commonFuncs goes out of scope. PwrshExeOutput* output = new PwrshExeOutput(); - PwrshCommon commonFuncs(output, new ConfigFileReader(), new WinSystemCallFacade()); - CoreClrHostingApiWrapper hostWrapper; + PwrshCommon commonFuncs(output, new WinSystemCallFacade()); + ICLRRuntimeHost2Wrapper hostWrapper; - exitCode = commonFuncs.LaunchCoreCLR(&hostWrapper, hostEnvironment, "powershell"); + exitCode = commonFuncs.LaunchCoreCLR(&hostWrapper, hostEnvironment); if (EXIT_CODE_SUCCESS != exitCode) { if (verbose) @@ -54,14 +51,23 @@ namespace NativeMsh return false; } + exitCode = commonFuncs.CreateAppDomain(&hostWrapper, hostEnvironment.GetHostBinaryName(), hostEnvironment); + if (EXIT_CODE_SUCCESS != exitCode) + { + if (verbose) + ::wprintf(L"Unable to create app domain\n"); + return false; + } + //------------------------------------------------------------- // Set the powershell custom assembly loader to be the default LoaderRunHelperFp initDelegate = NULL; HRESULT hr = hostWrapper.CreateDelegate( - "Microsoft.PowerShell.CoreCLR.AssemblyLoadContext, Version=3.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35", - "System.Management.Automation.PowerShellAssemblyLoadContextInitializer", - "SetPowerShellAssemblyLoadContext", - (void**)&initDelegate); + hostWrapper.GetAppDomainId(), + L"Microsoft.PowerShell.CoreCLR.AssemblyLoadContext, Version=3.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35", + L"System.Management.Automation.PowerShellAssemblyLoadContextInitializer", + L"SetPowerShellAssemblyLoadContext", + (INT_PTR*)&initDelegate); if (FAILED(hr)) { @@ -69,17 +75,18 @@ namespace NativeMsh } else { - initDelegate(hostEnvironment.GetHostDirectoryPathW()); + initDelegate(hostEnvironment.GetHostDirectoryPath()); } //------------------------------------------------------------- // Start the assembly MonadRunHelperFp pfnDelegate = NULL; hr = hostWrapper.CreateDelegate( - "Microsoft.PowerShell.ConsoleHost, Version=3.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35", - "Microsoft.PowerShell.UnmanagedPSEntry", - "Start", - (void**)&pfnDelegate); + hostWrapper.GetAppDomainId(), + L"Microsoft.PowerShell.ConsoleHost, Version=3.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35", + L"Microsoft.PowerShell.UnmanagedPSEntry", + L"Start", + (INT_PTR*)&pfnDelegate); if (FAILED(hr)) { diff --git a/src/powershell-native/nativemsh/pwrshexe/MainEntry.cpp b/src/powershell-native/nativemsh/pwrshexe/MainEntry.cpp index 7253d31b6..e85bed577 100644 --- a/src/powershell-native/nativemsh/pwrshexe/MainEntry.cpp +++ b/src/powershell-native/nativemsh/pwrshexe/MainEntry.cpp @@ -26,7 +26,6 @@ #include #include #include "OutputWriter.h" -#include "ConfigFileReader.h" #include "WinSystemCallFacade.h" // include the tlb for mscorlib for access to the default AppDomain through COM Interop @@ -50,7 +49,7 @@ WCHAR g_IconApp[MAX_PATH+1]; // All these objects will be destroyed when pwrshCommon goes out of scope. PwrshExeOutput* pwrshExeOutput = new PwrshExeOutput(); -PwrshCommon pwrshCommon(pwrshExeOutput, new ConfigFileReader(), new WinSystemCallFacade()); +PwrshCommon pwrshCommon(pwrshExeOutput, new WinSystemCallFacade()); bool ConvertArgvToSafeArray( IN int argc, diff --git a/src/powershell-native/nativemsh/pwrshplugin/entrypoints.cpp b/src/powershell-native/nativemsh/pwrshplugin/entrypoints.cpp index 6490ec5ac..c5ae58224 100644 --- a/src/powershell-native/nativemsh/pwrshplugin/entrypoints.cpp +++ b/src/powershell-native/nativemsh/pwrshplugin/entrypoints.cpp @@ -8,10 +8,9 @@ // ---------------------------------------------------------------------- #include "pwrshplugin.h" -// [Porting note] SQM is for Telemetry in Windows. Temporarily disabled. -//#include -//#include "common/WindowsSqmDataID.h" -//#include "common/winrmsqm.h" +#include +#include "common/WindowsSqmDataID.h" +#include "common/winrmsqm.h" #if !CORECLR #include @@ -20,12 +19,11 @@ HINSTANCE g_hResourceInstance = 0; // TODO: Where is this freed? FreeMUILibrary for nonCoreClr and FreeLibrary for CoreCLR LPCWSTR g_MAIN_BINARY_NAME = L"pwrshplugin.dll"; -// [Porting note] SQM is for Telemetry in Windows. Temporarily disabled. -// typedef VOID (NTAPI *PFN_WinSqmSetDWORD)( -// __in_opt HSESSION hSession, -// __in DWORD dwDatapointId, -// __in DWORD dwDatapointValue -// ); +typedef VOID (NTAPI *PFN_WinSqmSetDWORD)( + __in_opt HSESSION hSession, + __in DWORD dwDatapointId, + __in DWORD dwDatapointValue + ); // gets the error message from the resources section of the current module. // the caller should free pwszErrorMessage using LocalFree(). @@ -186,7 +184,6 @@ static PwrshCommon sPwrshCommon; // pwszRuntimeVersion and pRuntimeVersionLength represents the size of pwszRuntimeVersion. // returns: 0 on success, non-zero on failure. _Success_(return == 0) //EXIT_CODE_SUCCESS -extern "C" unsigned int GetCLRVersionForPSVersion(int iPSMajorVersion, int iPSMinorVersion, size_t runtimeVersionLength, @@ -324,7 +321,6 @@ DWORD ReportOperationComplete(WSMAN_PLUGIN_REQUEST *requestDetails, DWORD errorC // initialized more than once within the same process, but only once per // applicationIdentification. // ----------------------------------------------------------------------------- -extern "C" DWORD WINAPI WSManPluginStartup( __in DWORD flags, __in PCWSTR applicationIdentification, @@ -355,24 +351,22 @@ DWORD WINAPI WSManPluginStartup( // Using global SQM session // WinSQMSetDWORD is not available on Vista + HMODULE hModule; + PFN_WinSqmSetDWORD pfnWinSqmSetDWORD; - // [Porting note] SQM is for Telemetry in Windows. Temporarily disabled. - // HMODULE hModule; - // PFN_WinSqmSetDWORD pfnWinSqmSetDWORD; - - // hModule = GetModuleHandleW(L"ntdll"); - // if (hModule) - // { - // pfnWinSqmSetDWORD = (PFN_WinSqmSetDWORD) GetProcAddress(hModule, "WinSqmSetDWORD"); - // if (pfnWinSqmSetDWORD) - // { - // pfnWinSqmSetDWORD( - // NULL, - // DATAID_WINRMREMOTEENABLED, - // WINRM_SQM_DATA_REMOTEENABLED - // ); - // } - // } + hModule = GetModuleHandleW(L"ntdll"); + if (hModule) + { + pfnWinSqmSetDWORD = (PFN_WinSqmSetDWORD) GetProcAddress(hModule, "WinSqmSetDWORD"); + if (pfnWinSqmSetDWORD) + { + pfnWinSqmSetDWORD( + NULL, + DATAID_WINRMREMOTEENABLED, + WINRM_SQM_DATA_REMOTEENABLED + ); + } + } return NO_ERROR; } @@ -408,7 +402,6 @@ DWORD WINAPI WSManPluginStartup( // reason: If this is a system shutdown this will be WSMAN_PLUGIN_SHUTDOWN_SYSTEM. // For WSMan service shutdown this will be WSMAN_PLUGIN_SHUTDOWN_SERVICE. For an IIS host //shutdown this will be WSMAN_PLUGIN_SHUTDOWN_IISHOST. -extern "C" DWORD WINAPI WSManPluginShutdown( __in PVOID pluginContext, __in DWORD flags, @@ -456,7 +449,6 @@ DWORD WINAPI WSManPluginShutdown( // requestDetails the plug-in needs to call WSManPluginOperationComplete. // The shell is active until this time. // ----------------------------------------------------------------------------- -extern "C" VOID WINAPI WSManPluginShell( __in PVOID pluginContext, __in WSMAN_PLUGIN_REQUEST *requestDetails, @@ -532,7 +524,6 @@ VOID WINAPI WSManPluginShell( // corresponding release function has been called. Failure to follow the contract // will result in errors being generated. // ----------------------------------------------------------------------------- -extern "C" VOID WINAPI WSManPluginReleaseShellContext(__in PVOID shellContext) { if ((NULL == shellContext)) @@ -565,7 +556,6 @@ VOID WINAPI WSManPluginReleaseShellContext(__in PVOID shellContext) // requestDetails the plug-in needs to call WSManPluginOperationComplete. // The command is active until this time. // ----------------------------------------------------------------------------- -extern "C" VOID WINAPI WSManPluginCommand( __in WSMAN_PLUGIN_REQUEST *requestDetails, __in DWORD flags, @@ -599,7 +589,6 @@ VOID WINAPI WSManPluginCommand( // corresponding release function has been called. Failure to follow the contract // will result in errors being generated. // --------------------------------------------------------------------------------- -extern "C" VOID WINAPI WSManPluginReleaseCommandContext( __in PVOID shellContext, __in PVOID commandContext @@ -631,7 +620,6 @@ VOID WINAPI WSManPluginReleaseCommandContext( // For each piece of data the plug-in calls WSManPluginResultComplete to // acknowledge receipt and to allow the next piece of data to be delivered. // ----------------------------------------------------------------------------- -extern "C" VOID WINAPI WSManPluginSend( __in WSMAN_PLUGIN_REQUEST *requestDetails, __in DWORD flags, @@ -671,7 +659,6 @@ VOID WINAPI WSManPluginSend( // WSManPluginResultComplete. The operation is marked as active until this // time. // ----------------------------------------------------------------------------- -extern "C" VOID WINAPI WSManPluginReceive( __in WSMAN_PLUGIN_REQUEST *requestDetails, __in DWORD flags, @@ -707,7 +694,6 @@ VOID WINAPI WSManPluginReceive( // of this callback may be many completion calls for the Signal, Receive, Command // and Shell operations. // ----------------------------------------------------------------------------- -extern "C" VOID WINAPI WSManPluginSignal( __in WSMAN_PLUGIN_REQUEST *requestDetails, __in DWORD flags, @@ -733,7 +719,7 @@ VOID WINAPI WSManPluginSignal( } } -extern "C" + VOID WINAPI WSManPluginConnect( __in WSMAN_PLUGIN_REQUEST *requestDetails, __in DWORD flags, diff --git a/src/powershell-native/nativemsh/pwrshplugin/pwrshclrhost.cpp b/src/powershell-native/nativemsh/pwrshplugin/pwrshclrhost.cpp index 054e1f1f5..db5a72c3d 100644 --- a/src/powershell-native/nativemsh/pwrshplugin/pwrshclrhost.cpp +++ b/src/powershell-native/nativemsh/pwrshplugin/pwrshclrhost.cpp @@ -40,10 +40,9 @@ typedef void (STDMETHODCALLTYPE *LoaderRunHelperFp)(LPCWSTR appPath); unsigned int PowerShellCoreClrWorker::LaunchClr( _In_ LPCWSTR wszMonadVersion, - _In_ LPCWSTR wszRuntimeVersion, - _In_ LPCSTR friendlyName) + _In_ LPCWSTR wszRuntimeVersion) { - return commonLib->LaunchCoreCLR(hostWrapper, hostEnvironment, friendlyName); + return commonLib->LaunchCoreCLR(hostWrapper, hostEnvironment); } unsigned int PowerShellCoreClrWorker::LoadWorkerCallbackPtrs( @@ -51,17 +50,24 @@ unsigned int PowerShellCoreClrWorker::LoadWorkerCallbackPtrs( _In_z_ wchar_t* wszMgdPlugInFileName, _Outptr_result_maybenull_ PlugInException** pPluginException) { + unsigned int exitCode = EXIT_CODE_SUCCESS; *pPluginException = NULL; + exitCode = commonLib->CreateAppDomain(hostWrapper, L"PwrshPlugin", hostEnvironment); + if (EXIT_CODE_SUCCESS != exitCode) + { + return exitCode; + } + // Set the powershell custom assembly loader to be the default LoaderRunHelperFp initDelegate = NULL; HRESULT hr = hostWrapper->CreateDelegate( - "Microsoft.PowerShell.CoreCLR.AssemblyLoadContext, Version=3.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35", - "System.Management.Automation.PowerShellAssemblyLoadContextInitializer", - "SetPowerShellAssemblyLoadContext", - //(INT_PTR*)&initDelegate); - (void**)&initDelegate); + hostWrapper->GetAppDomainId(), + L"Microsoft.PowerShell.CoreCLR.AssemblyLoadContext, Version=3.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35", + L"System.Management.Automation.PowerShellAssemblyLoadContextInitializer", + L"SetPowerShellAssemblyLoadContext", + (INT_PTR*)&initDelegate); if (FAILED(hr)) { @@ -69,7 +75,7 @@ unsigned int PowerShellCoreClrWorker::LoadWorkerCallbackPtrs( } else { - initDelegate(hostEnvironment.GetHostDirectoryPathW()); + initDelegate(hostEnvironment.GetHostDirectoryPath()); } // Call into powershell entry point @@ -78,12 +84,14 @@ unsigned int PowerShellCoreClrWorker::LoadWorkerCallbackPtrs( // Create the function pointer for the managed entry point // It must be targeted at a static method in the managed code. hr = hostWrapper->CreateDelegate( - "System.Management.Automation, Version=3.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35", - "System.Management.Automation.Remoting.WSManPluginManagedEntryWrapper", - "InitPlugin", - (void**)&entryPointDelegate); + hostWrapper->GetAppDomainId(), + L"System.Management.Automation, Version=3.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35", + L"System.Management.Automation.Remoting.WSManPluginManagedEntryWrapper", + L"InitPlugin", + (INT_PTR*)&entryPointDelegate); if (FAILED(hr)) { + //LONG systemErrorCode = GetLastError(); output->DisplayMessage(false, g_CREATING_MSH_ENTRANCE_FAILED, hr); return EXIT_CODE_INIT_FAILURE; @@ -95,7 +103,7 @@ unsigned int PowerShellCoreClrWorker::LoadWorkerCallbackPtrs( PowerShellCoreClrWorker::PowerShellCoreClrWorker() : systemCalls(new WinSystemCallFacade()), - hostWrapper(new CoreClrHostingApiWrapper()), + hostWrapper(new ICLRRuntimeHost2Wrapper()), output(new PwrshPluginOutputDefault()), commonLib(new PwrshCommon()) { @@ -125,12 +133,12 @@ PowerShellCoreClrWorker::PowerShellCoreClrWorker( { // Instantiate it even if one is not provided to guarantee that it will // always be non-NULL during execution. - hostWrapper = new CoreClrHostingApiWrapper(); + hostWrapper = new ICLRRuntimeHost2Wrapper(); } if (NULL == commonLib) { - commonLib = new PwrshCommon(new PwrshPluginOutputDefault(), new ConfigFileReader(), new WinSystemCallFacade()); + commonLib = new PwrshCommon(new PwrshPluginOutputDefault(), new WinSystemCallFacade()); } } @@ -232,8 +240,7 @@ PowerShellClrWorker::~PowerShellClrWorker() unsigned int PowerShellClrWorker::LaunchClr( _In_ LPCWSTR wszMonadVersion, - _In_ LPCWSTR wszRuntimeVersion, - _In_ LPCSTR friendlyName) + _In_ LPCWSTR wszRuntimeVersion) { return commonLib.LaunchCLR(wszMonadVersion, wszRuntimeVersion, &pHost); } @@ -303,8 +310,7 @@ unsigned int PowerShellClrWorker::LoadWorkerCallbackPtrs( unsigned int PowerShellClrManagedWorker::LaunchClr( _In_ LPCWSTR wszMonadVersion, - _In_ LPCWSTR wszRuntimeVersion, - _In_ LPCSTR friendlyName) + _In_ LPCWSTR wszRuntimeVersion) { return commonLib.LaunchCLR(wszMonadVersion, wszRuntimeVersion, &pHost); } @@ -344,8 +350,7 @@ unsigned int PowerShellClrManagedWorker::LoadWorkerCallbackPtrs( // use CreateInstance because we use the assembly strong name (as opposed to CreateInstanceFrom) // - // wszMgdPlugInFileName is system.management.automation.dll within the powershell install path. - // For inbox PowerShell, this is %systemdir%\Windows\System32\WindowsPowerShell\v1.0\system.management.automation.dll (Aka $PSHOME\system.management.automation.dll) + // wszMgdPlugInFileName is %systemdir%\Windows\System32\WindowsPowerShell\v1.0\system.management.automation.dll. _bstr_t bstrConsoleHostAssemblyName = _bstr_t(L"System.Management.Automation, Version=3.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35"); _bstr_t bstrUnmanagedMshEntryClass = _bstr_t(L"System.Management.Automation.Remoting.WSManPluginManagedEntryInstanceWrapper"); diff --git a/src/powershell-native/nativemsh/pwrshplugin/pwrshclrhost.h b/src/powershell-native/nativemsh/pwrshplugin/pwrshclrhost.h index 75c2e1f5c..50ea8258e 100644 --- a/src/powershell-native/nativemsh/pwrshplugin/pwrshclrhost.h +++ b/src/powershell-native/nativemsh/pwrshplugin/pwrshclrhost.h @@ -10,9 +10,7 @@ #pragma once #include "pwrshplugindefs.h" // PwrshPluginWkr_Ptrs and PlugInException -#if !CORECLR #include -#endif #include #include #include "SystemCallFacade.h" @@ -48,8 +46,7 @@ public: virtual unsigned int LaunchClr( _In_ LPCWSTR wszMonadVersion, - _In_ LPCWSTR wszRuntimeVersion, - _In_ LPCSTR friendlyName) = 0; + _In_ LPCWSTR wszRuntimeVersion) = 0; virtual unsigned int LoadWorkerCallbackPtrs( _In_ PwrshPluginWkr_Ptrs* workerCallbackPtrs, @@ -91,8 +88,7 @@ public: // virtual unsigned int LaunchClr( _In_ LPCWSTR wszMonadVersion, - _In_ LPCWSTR wszRuntimeVersion, - _In_ LPCSTR friendlyName); + _In_ LPCWSTR wszRuntimeVersion); virtual unsigned int LoadWorkerCallbackPtrs( _In_ PwrshPluginWkr_Ptrs* workerCallbackPtrs, @@ -118,8 +114,7 @@ public: // virtual unsigned int LaunchClr( _In_ LPCWSTR wszMonadVersion, - _In_ LPCWSTR wszRuntimeVersion, - _In_ LPCSTR friendlyName); + _In_ LPCWSTR wszRuntimeVersion); virtual unsigned int LoadWorkerCallbackPtrs( _In_ PwrshPluginWkr_Ptrs* workerCallbackPtrs, @@ -148,16 +143,15 @@ public: virtual ~PowerShellCoreClrWorker(); - std::wstring GetHostDirectory() { return std::wstring(hostEnvironment.GetHostDirectoryPathW()); } - std::wstring GetClrDirectory() { return std::wstring(hostEnvironment.GetCoreCLRDirectoryPathW()); } + std::wstring GetHostDirectory() { return std::wstring(hostEnvironment.GetHostDirectoryPath()); } + std::wstring GetClrDirectory() { return std::wstring(hostEnvironment.GetCoreCLRDirectoryPath()); } // // IPowerShellClrHost Methods // virtual unsigned int LaunchClr( _In_ LPCWSTR wszMonadVersion, - _In_ LPCWSTR wszRuntimeVersion, - _In_ LPCSTR friendlyName); + _In_ LPCWSTR wszRuntimeVersion); virtual unsigned int LoadWorkerCallbackPtrs( _In_ PwrshPluginWkr_Ptrs* workerCallbackPtrs, diff --git a/src/powershell-native/nativemsh/pwrshplugin/pwrshheaders.h b/src/powershell-native/nativemsh/pwrshplugin/pwrshheaders.h index a10d741dc..d63dc56cb 100644 --- a/src/powershell-native/nativemsh/pwrshplugin/pwrshheaders.h +++ b/src/powershell-native/nativemsh/pwrshplugin/pwrshheaders.h @@ -15,9 +15,8 @@ // pwszRuntimeVersion and pRuntimeVersionLength represents the size of pwszRuntimeVersion. // returns: 0 on success, non-zero on failure. _Success_(return == 0) // EXIT_CODE_SUCCESS -extern "C" -unsigned int GetCLRVersionForPSVersion(int iPSMajorVersion, - int iPSMinorVersion, - size_t runtimeVersionLength, - __inout_ecount_part(runtimeVersionLength , *pRuntimeVersionLength) wchar_t* pwszRuntimeVersion, - __out_ecount(1) size_t* pRuntimeVersionLength); +extern unsigned int GetCLRVersionForPSVersion(int iPSMajorVersion, + int iPSMinorVersion, + size_t runtimeVersionLength, + __inout_ecount_part(runtimeVersionLength , *pRuntimeVersionLength) wchar_t* pwszRuntimeVersion, + __out_ecount(1) size_t* pRuntimeVersionLength); \ No newline at end of file diff --git a/src/powershell-native/nativemsh/pwrshplugin/pwrshplugin.def b/src/powershell-native/nativemsh/pwrshplugin/pwrshplugin.def index af45f5c78..f80ff8ac2 100644 --- a/src/powershell-native/nativemsh/pwrshplugin/pwrshplugin.def +++ b/src/powershell-native/nativemsh/pwrshplugin/pwrshplugin.def @@ -15,4 +15,4 @@ WSManPluginSend WSManPluginSignal WSManPluginReceive WSManPluginConnect -PerformWSManPluginReportCompletion +PerformWSManPluginReportCompletion \ No newline at end of file diff --git a/src/powershell-native/nativemsh/pwrshplugin/pwrshplugin.h b/src/powershell-native/nativemsh/pwrshplugin/pwrshplugin.h index c1135cfd0..ab7c6d267 100644 --- a/src/powershell-native/nativemsh/pwrshplugin/pwrshplugin.h +++ b/src/powershell-native/nativemsh/pwrshplugin/pwrshplugin.h @@ -714,7 +714,7 @@ private: break; } - exitCode = powerShellClrHost->LaunchClr(wszMonadVersion, wszTempCLRVersion, "PwrshPlugin"); + exitCode = powerShellClrHost->LaunchClr(wszMonadVersion, wszTempCLRVersion); if (EXIT_CODE_SUCCESS != exitCode) { PWSTR msg = NULL; @@ -1091,7 +1091,6 @@ public: } }; -extern "C" void WINAPI PerformWSManPluginReportCompletion() { // Now report the plugin completion, to indicate that plugin is ready to shutdown. @@ -1099,4 +1098,4 @@ void WINAPI PerformWSManPluginReportCompletion() // - pluginContext MUST be the same context that plugin provided to the WSManPluginStartup method // - flags are reserved, so 0 WSManPluginReportCompletion(g_pPluginContext, 0); -} +} \ No newline at end of file diff --git a/test/powershell/Language/Classes/ProtectedAccess.Tests.ps1 b/test/powershell/Language/Classes/ProtectedAccess.Tests.ps1 index e9b7be2fb..2c79c9d99 100644 --- a/test/powershell/Language/Classes/ProtectedAccess.Tests.ps1 +++ b/test/powershell/Language/Classes/ProtectedAccess.Tests.ps1 @@ -138,7 +138,7 @@ class Derived2 : Base {} [Derived2]::new() '@ -Describe "Protected Member Access - w/ default ctor" -Tags "CI" { +Describe "Protected Member Access - w/ default ctor" -Tags "DRT" { It "Method Access" { $derived1.TestMethodAccess() | Should Be 42 } It "Dynamic Method Access" { $derived1.TestDynamicMethodAccess() | Should Be 42 } It "Field Access" { $derived1.TestFieldAccess() | Should Be 11 } @@ -157,7 +157,7 @@ Describe "Protected Member Access - w/ default ctor" -Tags "CI" { It "Implicit ctor calls protected ctor" { $derived3.OverloadedMethod2(42) | Should Be 84 } } -Describe "Protected Member Access - w/ non-default ctor" -Tags "CI" { +Describe "Protected Member Access - w/ non-default ctor" -Tags "DRT" { It "Method Access" { $derived2.TestMethodAccess() | Should Be 52 } It "Dynamic Method Access" { $derived2.TestDynamicMethodAccess() | Should Be 52 } It "Field Access" { $derived2.TestFieldAccess() | Should Be 11 } @@ -175,7 +175,7 @@ Describe "Protected Member Access - w/ non-default ctor" -Tags "CI" { It "Method Access - overloaded 3b" { $derived2.TestOverloadedMethodAccess3b() | Should Be 21 } } -Describe "Protected Member Access - members not visible outside class" -Tags "CI" { +Describe "Protected Member Access - members not visible outside class" -Tags "DRT" { Set-StrictMode -v 3 It "Invalid protected field Get Access" { { $derived1.Field } | Should Throw } It "Invalid protected property Get Access" { { $derived1.Property } | Should Throw } diff --git a/test/powershell/Language/Classes/Scripting.Classes.Attributes.Tests.ps1 b/test/powershell/Language/Classes/Scripting.Classes.Attributes.Tests.ps1 index 77dac3bc2..943b054f5 100644 --- a/test/powershell/Language/Classes/Scripting.Classes.Attributes.Tests.ps1 +++ b/test/powershell/Language/Classes/Scripting.Classes.Attributes.Tests.ps1 @@ -1,4 +1,4 @@ -Describe 'Attributes Test' -Tags "CI" { +Describe 'Attributes Test' -Tags "innerloop", "DRT" { BeforeAll { $dummyAttributesSource = @' @@ -45,7 +45,7 @@ namespace Dummy } } '@ - Add-Type -TypeDefinition $dummyAttributesSource -ReferencedAssemblies "System.Management.Automation","mscorlib" + Add-Type -TypeDefinition $dummyAttributesSource -ReferencedAssemblies "System.Management.Automation" } @@ -197,7 +197,7 @@ namespace Dummy } } -Describe 'Type resolution with attributes' -Tag "CI" { +Describe 'Type resolution with attributes' { # There is kind of a collision between names # System.Diagnostics.Tracing.EventSource # System.Diagnostics.Tracing.EventSourceAttribute @@ -215,4 +215,4 @@ Describe 'Type resolution with attributes' -Tag "CI" { } } -} +} \ No newline at end of file diff --git a/test/powershell/Language/Classes/Scripting.Classes.BasicParsing.Tests.ps1 b/test/powershell/Language/Classes/Scripting.Classes.BasicParsing.Tests.ps1 index 796e360e0..157a7024e 100644 --- a/test/powershell/Language/Classes/Scripting.Classes.BasicParsing.Tests.ps1 +++ b/test/powershell/Language/Classes/Scripting.Classes.BasicParsing.Tests.ps1 @@ -3,7 +3,7 @@ # Import-Module $PSScriptRoot\..\LanguageTestSupport.psm1 -force -Describe 'Positive Parse Properties Tests' -Tags "CI" { +Describe 'Positive Parse Properties Tests' -Tags "innerloop", "DRT" { It 'PositiveParsePropertiesTest' { # Just a bunch of random basic things here # This test doesn't need to check anything, if there are @@ -248,7 +248,7 @@ Describe 'Positive Parse Properties Tests' -Tags "CI" { [A]::new().h.GetType().Name | Should Be 'OrderedDictionary' } } -Describe 'Negative Parsing Tests' -Tags "CI" { +Describe 'Negative Parsing Tests' -Tags "innerloop", "DRT" { ShouldBeParseError 'class' MissingNameAfterKeyword 5 ShouldBeParseError 'class foo' MissingTypeBody 9 ShouldBeParseError 'class foo {' MissingEndCurlyBrace 10 @@ -309,7 +309,7 @@ Describe 'Negative Parsing Tests' -Tags "CI" { ShouldBeParseError 'class C : B' MissingTypeBody 11 } -Describe 'Negative methods Tests' -Tags "CI" { +Describe 'Negative methods Tests' -Tags "innerloop", "DRT" { ShouldBeParseError 'class foo { f() { param($x) } }' ParamBlockNotAllowedInMethod 18 ShouldBeParseError 'class foo { f() { dynamicparam {} } }' NamedBlockNotAllowedInMethod 18 ShouldBeParseError 'class foo { f() { begin {} } }' NamedBlockNotAllowedInMethod 18 @@ -320,13 +320,13 @@ Describe 'Negative methods Tests' -Tags "CI" { ShouldBeParseError 'class foo { [void] bar($a, [string][int]$b, $c) {} }' MultipleTypeConstraintsOnMethodParam 35 } -Describe 'Negative Assignment Tests' -Tags "CI" { +Describe 'Negative Assignment Tests' -Tags "innerloop", "DRT" { ShouldBeParseError 'class foo { [string ]$path; f() { $path="" } }' MissingThis 34 ShouldBeParseError 'class foo { [string ]$path; f() { [string] $path="" } }' MissingThis 43 ShouldBeParseError 'class foo { [string ]$path; f() { [int] [string] $path="" } }' MissingThis 49 } -Describe 'Negative Assignment Tests' -Tags "CI" { +Describe 'Negative Assignment Tests' -Tags "innerloop", "DRT" { ShouldBeParseError '[DscResource()]class C { [bool] Test() { return $false } [C] Get() { return $this } Set() {} }' DscResourceMissingKeyProperty 0 # Test method @@ -350,7 +350,7 @@ Describe 'Negative Assignment Tests' -Tags "CI" { ShouldBeParseError '[DscResource()]class C { [DscProperty(Key)][string]$Key; [bool] Test() { return $false } [C] Get() { return $this } Set() {} C($a) { } }' DscResourceMissingDefaultConstructor 0 } -Describe 'Negative DscResources Tests' -Tags "CI" { +Describe 'Negative DscResources Tests' -Tags "innerloop", "DRT" { # Usage errors ShouldBeParseError '[Flags()]class C{}' AttributeNotAllowedOnDeclaration 0 ShouldBeParseError 'class C { [Flags()]$field; }' AttributeNotAllowedOnDeclaration 10 @@ -367,42 +367,32 @@ Describe 'Negative DscResources Tests' -Tags "CI" { ShouldBeParseError 'class C{ [ValidateScript({})]$p; }' ParameterAttributeArgumentNeedsToBeConstant 25 } -Describe 'Negative ClassAttributes Tests' -Tags "CI" { - [System.Management.Automation.Cmdlet("Get", "Thing")]class C{} - $t = [C].GetCustomAttributes($false) - - It "Should have one attribute" {$t.Count | should be 1} - It "Should have instance of CmdletAttribute" {$t[0].GetType().FullName | should be System.Management.Automation.CmdletAttribute } +Describe 'Negative ClassAttributes Tests' -Tags "innerloop", "DRT" { - [System.Management.Automation.CmdletAttribute]$c = $t[0] - It "Verb should be Get" {$c.VerbName | should be 'Get'} - It "Noun should be Thing" {$c.NounName | should be 'Thing'} + [System.Management.Automation.Cmdlet("Get", "Thing")]class C{} + $t = [C].GetCustomAttributes($false) - [System.Management.Automation.Cmdlet("Get", "Thing", SupportsShouldProcess = $true, SupportsPaging = $true)]class C2{} - $t = [C2].GetCustomAttributes($false) - It "Should have one attribute" { $t.Count | should be 1 } - It "Should have instance of CmdletAttribute" { $t[0].GetType().FullName | should be System.Management.Automation.CmdletAttribute } - [System.Management.Automation.CmdletAttribute]$c = $t[0] - It "Verb should be Get" {$c.VerbName | should be 'Get'} - It "Noun should be Thing" {$c.NounName | should be 'Thing'} - - It "SupportsShouldProcess should be $true" { $c.ConfirmImpact | should be $true } - It "SupportsPaging should be `$true" { $c.SupportsPaging | should be $true } - Context "Support ConfirmImpact as an attribute" { - It "ConfirmImpact should be high" -pending { - [System.Management.Automation.Cmdlet("Get", "Thing", ConfirmImpact = 'High', SupportsPaging = $true)]class C3{} - $t = [C3].GetCustomAttributes($false) - It "Should have one attribute" { $t.Count | should be 1 } - It "Should have instance of CmdletAttribute" { $t[0].GetType().FullName | should be System.Management.Automation.CmdletAttribute } - [System.Management.Automation.CmdletAttribute]$c = $t[0] - $c.ConfirmImpact | should be 'High' - - } - } + It "Should have one attribute" {$t.Count | should be 1} + It "Should have instance of CmdletAttribute" {$t[0].GetType().FullName | should be System.Management.Automation.CmdletAttribute } + + [System.Management.Automation.CmdletAttribute]$c = $t[0] + It "Verb should be Get" {$c.VerbName | should be 'Get'} + It "Noun should be Thing" {$c.NounName | should be 'Thing'} + + [System.Management.Automation.Cmdlet("Get", "Thing", ConfirmImpact = 'High', SupportsPaging = $true)]class C2{} + $t = [C2].GetCustomAttributes($false) + It "Should have one attribute" { $t.Count | should be 1 } + It "Should have instance of CmdletAttribute" { $t[0].GetType().FullName | should be System.Management.Automation.CmdletAttribute } + [System.Management.Automation.CmdletAttribute]$c = $t[0] + It "Verb should be Get" {$c.VerbName | should be 'Get'} + It "Noun should be Thing" {$c.NounName | should be 'Thing'} + + It "ConfirmImpact should be high" { $c.ConfirmImpact | should be 'High' } + It "SupportsPaging should be `$true" { $c.SupportsPaging | should be $true } } -Describe 'Property Attributes Test' -Tags "CI" { +Describe 'Property Attributes Test' -Tags "innerloop", "DRT" { class C { [ValidateSet('a', 'b')]$p; } $t = [C].GetProperty('p').GetCustomAttributes($false) @@ -413,7 +403,7 @@ Describe 'Property Attributes Test' -Tags "CI" { It "second value should be b" { $v.ValidValues[1] -eq 'b' } } -Describe 'Method Attributes Test' -Tags "CI" { +Describe 'Method Attributes Test' -Tags "innerloop", "DRT" { class C { [Obsolete("aaa")][int]f() { return 1 } } $t = [C].GetMethod('f').GetCustomAttributes($false) @@ -421,7 +411,7 @@ Describe 'Method Attributes Test' -Tags "CI" { It "Attribute type should be ObsoleteAttribute" { $t[0].GetType().FullName | should be System.ObsoleteAttribute } } -Describe 'Positive SelfClass Type As Parameter Test' -Tags "CI" { +Describe 'Positive SelfClass Type As Parameter Test' -Tags "innerloop", "DRT" { class Point { Point($x, $y) { $this.x = $x; $this.y = $y } @@ -453,7 +443,7 @@ Describe 'Positive SelfClass Type As Parameter Test' -Tags "CI" { } } -Describe 'PositiveReturnSelfClassTypeFromMemberFunction Test' -Tags "CI" { +Describe 'PositiveReturnSelfClassTypeFromMemberFunction Test' -Tags "innerloop", "DRT" { class ReturnObjectFromMemberFunctionTest { [ReturnObjectFromMemberFunctionTest] CreateInstance() @@ -470,9 +460,8 @@ Describe 'PositiveReturnSelfClassTypeFromMemberFunction Test' -Tags "CI" { It "CreateInstance works" { $z.SayHello() | should be 'Hello1' } } -Describe 'TestMultipleArguments Test' -Tags "CI" { - if ( $IsCoreCLR ) { $maxCount = 14 } else { $maxCount = 16 } - for ($i = 0; $i -lt $maxCount; $i++) +Describe 'TestMultipleArguments Test' -Tags "innerloop", "DRT" { + for ($i = 0; $i -lt 16; $i++) { $properties = $(for ($j = 0; $j -le $i; $j++) { " [int]`$Prop$j" @@ -525,7 +514,7 @@ $ctorAssignments Invoke-Expression $class } } -Describe 'Scopes Test' -Tags "CI" { +Describe 'Scopes Test' -Tags "innerloop", "DRT" { class C1 { static C1() { @@ -543,7 +532,7 @@ Describe 'Scopes Test' -Tags "CI" { } } -Describe 'Check PS Class Assembly Test' -Tags "CI" { +Describe 'Check PS Class Assembly Test' -Tags "innerloop", "DRT" { class C1 {} $assem = [C1].Assembly $attrs = @($assem.GetCustomAttributes($true)) @@ -551,7 +540,7 @@ Describe 'Check PS Class Assembly Test' -Tags "CI" { It "Expected a DynamicClassImplementationAssembly attribute" { $expectedAttr.Length | should be 1} } -Describe 'ScriptScopeAccessFromClassMethod' -Tags "CI" { +Describe 'ScriptScopeAccessFromClassMethod' -Tags "innerloop", "DRT" { Import-Module "$PSScriptRoot\MSFT_778492.psm1" try { @@ -564,7 +553,7 @@ Describe 'ScriptScopeAccessFromClassMethod' -Tags "CI" { } } -Describe 'Hidden Members Test ' -Tags "CI" { +Describe 'Hidden Members Test ' -Tags "innerloop", "DRT" { class C1 { [int]$visibleX @@ -598,13 +587,13 @@ Describe 'Hidden Members Test ' -Tags "CI" { It "Tab completion should not return a hidden member" { $completions.CompletionMatches.Count | should be 0 } } -Describe 'BaseMethodCall Test ' -Tags "CI" { +Describe 'BaseMethodCall Test ' -Tags "innerloop", "DRT" { It "Derived class method call" {"abc".ToString() | should be "abc" } # call [object] ToString() method as a base class method. It "Base class method call" {([object]"abc").ToString() | should be "System.String" } } -Describe 'Scoped Types Test' -Tags "CI" { +Describe 'Scoped Types Test' -Tags "innerloop", "DRT" { class C1 { [string] GetContext() { return "Test scope" } } filter f1 @@ -632,7 +621,7 @@ Describe 'Scoped Types Test' -Tags "CI" { It "'new-object C1' in nested scope (in pipeline)" { (1 | f2 | f1 | f2) | should be "f2 scope" } } -Describe 'ParameterOfClassTypeInModule Test' -Tags "CI" { +Describe 'ParameterOfClassTypeInModule Test' -Tags "innerloop", "DRT" { try { $sb = [scriptblock]::Create(@' @@ -649,7 +638,7 @@ function test-it([EE]$ee){$ee} } } -Describe 'Type building' -Tags "CI" { +Describe 'Type building' -Tags "DRT" { It 'should build the type only once for scriptblock' { $a = $null 1..10 | % { @@ -671,9 +660,9 @@ Describe 'Type building' -Tags "CI" { } } -Describe 'RuntimeType created for TypeDefinitionAst' -Tags "CI" { +Describe 'RuntimeType created for TypeDefinitionAst' { - It 'can make cast to the right RuntimeType in two different contexts' -pending { + It 'can make cast to the right RuntimeType in two different contexts' { $ssfe = [System.Management.Automation.Runspaces.SessionStateFunctionEntry]::new("foo", @' class Base @@ -689,7 +678,7 @@ class Derived : Base [Derived]::new().foo() '@) - $iss = [System.Management.Automation.Runspaces.initialsessionstate]::CreateDefault2() + $iss = [System.Management.Automation.Runspaces.initialsessionstate]::CreateDefault() $iss.Commands.Add($ssfe) $ps = [powershell]::Create($iss) @@ -707,7 +696,7 @@ class Derived : Base } } -Describe 'TypeTable lookups' -Tags "CI" { +Describe 'TypeTable lookups' { Context 'Call methods from a different thread' { $b = [powershell]::Create().AddScript( @@ -733,7 +722,7 @@ class B } } -Describe 'Protected method access' -Tags "CI" { +Describe 'Protected method access' { Add-Type @' namespace Foo @@ -745,7 +734,7 @@ namespace Foo } '@ - It 'doesn''t allow protected methods access outside of inheritance chain' -pending { + It 'doesn''t allow protected methods access outside of inheritance chain' { $a = [scriptblock]::Create(@' class A { @@ -816,7 +805,7 @@ return [A]::new() } } -Describe 'variable analysis' -Tags "CI" { +Describe 'variable analysis' { It 'can specify type construct on the local variables' { class A { [string] getFoo() { return 'foo'} } diff --git a/test/powershell/Language/Classes/Scripting.Classes.Break.Tests.ps1 b/test/powershell/Language/Classes/Scripting.Classes.Break.Tests.ps1 index ac1dc3ac5..d9e1f8f74 100644 --- a/test/powershell/Language/Classes/Scripting.Classes.Break.Tests.ps1 +++ b/test/powershell/Language/Classes/Scripting.Classes.Break.Tests.ps1 @@ -1,4 +1,4 @@ -Describe 'Break statements with classes' -Tags "CI" { +Describe 'Break statements with classes' -Tags "DRT" { function Get-Errors([string]$sourceCode) { $tokens = $null diff --git a/test/powershell/Language/Classes/Scripting.Classes.Exceptions.Tests.ps1 b/test/powershell/Language/Classes/Scripting.Classes.Exceptions.Tests.ps1 index ca9c20db6..539e90d18 100644 --- a/test/powershell/Language/Classes/Scripting.Classes.Exceptions.Tests.ps1 +++ b/test/powershell/Language/Classes/Scripting.Classes.Exceptions.Tests.ps1 @@ -1,4 +1,4 @@ -Describe 'Exceptions flow for classes' -Tags "CI" { +Describe 'Exceptions flow for classes' -Tags "DRT" { $canaryHashtable = @{} @@ -224,7 +224,7 @@ $canaryHashtable['canary'] += 100 } } -Describe "Exception error position" -Tags "CI" { +Describe "Exception error position" -Tags "DRT" { class MSFT_3090412 { static f1() { [MSFT_3090412]::bar = 42 } @@ -270,7 +270,7 @@ Describe "Exception error position" -Tags "CI" { } } -Describe "Exception from initializer" -Tags "CI" { +Describe "Exception from initializer" -Tags "DRT" { class MSFT_6397334a { [int]$a = "zz" diff --git a/test/powershell/Language/Classes/Scripting.Classes.MiscOps.Tests.ps1 b/test/powershell/Language/Classes/Scripting.Classes.MiscOps.Tests.ps1 index ee798cf12..45b4efdf4 100644 --- a/test/powershell/Language/Classes/Scripting.Classes.MiscOps.Tests.ps1 +++ b/test/powershell/Language/Classes/Scripting.Classes.MiscOps.Tests.ps1 @@ -1,4 +1,4 @@ -Describe 'Misc Test' -Tags "CI" { +Describe 'Misc Test' -Tags "innerloop", "DRT" { Context 'Where' { class C1 { @@ -43,4 +43,4 @@ Describe 'Misc Test' -Tags "CI" { [C1]::new().Bar() | should be "1;2;3;" } } -} +} \ No newline at end of file diff --git a/test/powershell/Language/Classes/Scripting.Classes.Modules.Tests.ps1 b/test/powershell/Language/Classes/Scripting.Classes.Modules.Tests.ps1 index 5caca7d22..a5310275b 100644 --- a/test/powershell/Language/Classes/Scripting.Classes.Modules.Tests.ps1 +++ b/test/powershell/Language/Classes/Scripting.Classes.Modules.Tests.ps1 @@ -1,36 +1,36 @@ -Describe 'PSModuleInfo.GetExportedTypeDefinitions()' -Tags "CI" { +Describe 'PSModuleInfo.GetExportedTypeDefinitions()' { It "doesn't throw for any module" { $discard = Get-Module -ListAvailable | % { $_.GetExportedTypeDefinitions() } $true | Should Be $true # we only verify that we didn't throw. This line contains a dummy Should to make pester happy. } } -Describe 'use of a module from two runspaces' -Tags "CI" { +Describe 'use of a module from two runspaces' { function New-TestModule { param( [string]$Name, [string]$Content ) - Setup -Dir $Name + mkdir -Force "TestDrive:\$Name" > $null $manifestParams = @{ Path = "TestDrive:\$Name\$Name.psd1" } if ($Content) { - Set-Content -Path "${TestDrive}\$Name\$Name.psm1" -Value $Content + Set-Content -Path TestDrive:\$Name\$Name.psm1 -Value $Content $manifestParams['RootModule'] = "$Name.psm1" } New-ModuleManifest @manifestParams - $resolvedTestDrivePath = Split-Path ((get-childitem TestDrive:\)[0].FullName) - if (-not ($env:PSMODULEPATH -like "*$resolvedTestDrivePath*")) { - $env:PSMODULEPATH += ";$resolvedTestDrivePath" + $resolvedTestDrivePath = Split-Path ((ls TestDrive:\)[0].FullName) + if (-not ($env:PSModulePath -like "*$resolvedTestDrivePath*")) { + $env:PSModulePath += ";$resolvedTestDrivePath" } } - $originalPSMODULEPATH = $env:PSMODULEPATH + $originalPSModulePath = $env:PSModulePath try { New-TestModule -Name 'Random' -Content @' @@ -68,7 +68,7 @@ Import-Module Random } } finally { - $env:PSMODULEPATH = $originalPSMODULEPATH + $env:PSModulePath = $originalPSModulePath } -} +} \ No newline at end of file diff --git a/test/powershell/Language/Classes/scripting.Classes.NestedModules.tests.ps1 b/test/powershell/Language/Classes/scripting.Classes.NestedModules.tests.ps1 index 86ae42c12..8b0be4247 100644 --- a/test/powershell/Language/Classes/scripting.Classes.NestedModules.tests.ps1 +++ b/test/powershell/Language/Classes/scripting.Classes.NestedModules.tests.ps1 @@ -1,4 +1,4 @@ -Describe 'NestedModules' -Tags "CI" { +Describe 'NestedModules' -Tags "DRT" { Import-Module $PSScriptRoot\..\LanguageTestSupport.psm1 @@ -9,33 +9,33 @@ Describe 'NestedModules' -Tags "CI" { [string[]]$NestedContents ) - new-item -type directory -Force "TestDrive:\$Name" > $null + mkdir -Force "TestDrive:\$Name" > $null $manifestParams = @{ Path = "TestDrive:\$Name\$Name.psd1" } if ($Content) { - Set-Content -Path "${TestDrive}\$Name\$Name.psm1" -Value $Content + Set-Content -Path TestDrive:\$Name\$Name.psm1 -Value $Content $manifestParams['RootModule'] = "$Name.psm1" } if ($NestedContents) { $manifestParams['NestedModules'] = 1..$NestedContents.Count | % { - $null = new-item -type directory TestDrive:\$Name\Nested$_ - $null = Set-Content -Path "${TestDrive}\$Name\Nested$_\Nested$_.psm1" -Value $NestedContents[$_ - 1] + $null = mkdir TestDrive:\$Name\Nested$_ + $null = Set-Content -Path TestDrive:\$Name\Nested$_\Nested$_.psm1 -Value $NestedContents[$_ - 1] "Nested$_" } } New-ModuleManifest @manifestParams - $resolvedTestDrivePath = Split-Path ((get-childitem TestDrive:\)[0].FullName) - if (-not ($env:PSMODULEPATH -like "*$resolvedTestDrivePath*")) { - $env:PSMODULEPATH += ";$resolvedTestDrivePath" + $resolvedTestDrivePath = Split-Path ((ls TestDrive:\)[0].FullName) + if (-not ($env:PSModulePath -like "*$resolvedTestDrivePath*")) { + $env:PSModulePath += ";$resolvedTestDrivePath" } } - $originalPSMODULEPATH = $env:PSMODULEPATH + $originalPSModulePath = $env:PSModulePath try { @@ -104,7 +104,7 @@ using module WithRoot # We need to think about it: should it work or not. # Currently, types are resolved in compile-time to the 'local' versions # So at runtime we don't call the module versions. - It 'Can execute type creation in the module context with new()' -pending { + It 'Can execute type creation in the module context with new()' -Skip { & (Get-Module ABC) { [C]::new().foo() } | Should Be C & (Get-Module NoRoot) { [A]::new().foo() } | Should Be A2 & (Get-Module WithRoot) { [A]::new().foo() } | Should Be A0 @@ -120,7 +120,7 @@ using module WithRoot } } finally { - $env:PSMODULEPATH = $originalPSMODULEPATH + $env:PSModulePath = $originalPSModulePath Get-Module @('ABC', 'NoRoot', 'WithRoot') | Remove-Module } } diff --git a/test/powershell/Language/Classes/scripting.Classes.inheritance.tests.ps1 b/test/powershell/Language/Classes/scripting.Classes.inheritance.tests.ps1 index 2b4f153ac..b02d18f12 100644 --- a/test/powershell/Language/Classes/scripting.Classes.inheritance.tests.ps1 +++ b/test/powershell/Language/Classes/scripting.Classes.inheritance.tests.ps1 @@ -4,7 +4,7 @@ Import-Module $PSScriptRoot\..\LanguageTestSupport.psm1 -Describe 'Classes inheritance syntax' -Tags "CI" { +Describe 'Classes inheritance syntax' -Tags "DRT" { It 'Base types' { class C1 {} @@ -27,16 +27,16 @@ Describe 'Classes inheritance syntax' -Tags "CI" { class C7 : C6 { C7() : base() {} } } - It 'inheritance syntax allows newlines in various places' { + It 'inheritance syntax allows newlines in varius places' { class C {} - class C2a:C,system.IDisposable{ [void] Dispose() { }} + class C2a:C,system.ICloneable{ [object] Clone() {return $null}} class C2b : C , - system.IDisposable + system.ICloneable { - [void] Dispose() {} + [object] Clone() {return $null} C2b() : # there are extra spaces here base @@ -46,8 +46,8 @@ Describe 'Classes inheritance syntax' -Tags "CI" { } } - [C2a].GetInterface("System.IDisposable") | Should Not Be $null - [C2b].GetInterface("System.IDisposable") | Should Not Be $null + [C2a].GetInterface("System.ICloneable") | Should Not Be $null + [C2b].GetInterface("System.ICloneable") | Should Not Be $null } It 'can subclass .NET type' { @@ -81,7 +81,7 @@ Describe 'Classes inheritance syntax' -Tags "CI" { } } -Describe 'Classes inheritance syntax errors' -Tags "CI" { +Describe 'Classes inheritance syntax errors' -Tags "DRT" { ShouldBeParseError "class A : NonExistingClass {}" TypeNotFound 10 ShouldBeParseError "class A : {}" TypeNameExpected 9 ShouldBeParseError "class A {}; class B : A, {}" TypeNameExpected 24 @@ -90,7 +90,7 @@ Describe 'Classes inheritance syntax errors' -Tags "CI" { ShouldBeParseError "class A {}; class B : A, NonExistingInterface {}" TypeNotFound 25 ShouldBeParseError "class A {} ; class B {}; class C : A, B {}" InterfaceNameExpected 38 -SkipAndCheckRuntimeError - ShouldBeParseError "class A{} ; class B : A, System.IDisposable[] {}" SubtypeArray 25 -SkipAndCheckRuntimeError + ShouldBeParseError "class A{} ; class B : A, System.ICloneable[] {}" SubtypeArray 25 -SkipAndCheckRuntimeError ShouldBeParseError "class A {}; class B : A, NonExistingInterface {}" TypeNotFound 25 # base should be accepted only on instance ctors @@ -118,7 +118,7 @@ Describe 'Classes inheritance syntax errors' -Tags "CI" { ShouldBeParseError "class A : C {}; class B : A {}; class C : B {}" TypeNotFound 10 -SkipAndCheckRuntimeError } -Describe 'Classes methods with inheritance' -Tags "CI" { +Describe 'Classes methods with inheritance' -Tags "DRT" { Context 'Method calls' { @@ -367,7 +367,7 @@ Describe 'Classes methods with inheritance' -Tags "CI" { } -Describe 'Classes inheritance ctors syntax errors' -Tags "CI" { +Describe 'Classes inheritance ctors syntax errors' -Tags "DRT" { #DotNet.Interface.NotImplemented ShouldBeParseError "class MyComparable : system.IComparable {}" TypeCreationError 0 -SkipAndCheckRuntimeError @@ -382,7 +382,7 @@ Describe 'Classes inheritance ctors syntax errors' -Tags "CI" { ShouldBeParseError 'class A { A([int]$a) {} }; class B : A {}' BaseClassNoDefaultCtor 27 -SkipAndCheckRuntimeError } -Describe 'Classes inheritance ctors' -Tags "CI" { +Describe 'Classes inheritance ctors' -Tags "DRT" { It 'can call base ctor' { class A { @@ -508,7 +508,7 @@ Describe 'Classes inheritance ctors' -Tags "CI" { } } -Describe 'Type creation' -Tags "CI" { +Describe 'Type creation' { It 'can call super-class methods sequentially' { $sb = [scriptblock]::Create(@' class Base @@ -526,4 +526,4 @@ class Derived : Base $sb.Invoke() | Should Be 200 $sb.Invoke() | Should Be 200 } -} +} \ No newline at end of file diff --git a/test/powershell/Language/Classes/scripting.Classes.using.tests.ps1 b/test/powershell/Language/Classes/scripting.Classes.using.tests.ps1 index d4c6fc42f..cb697e103 100644 --- a/test/powershell/Language/Classes/scripting.Classes.using.tests.ps1 +++ b/test/powershell/Language/Classes/scripting.Classes.using.tests.ps1 @@ -1,89 +1,85 @@ -Describe 'using module' -Tags "CI" { - BeforeAll { - $originalPSMODULEPATH = $env:PSMODULEPATH +Describe 'using module' -Tags "DRT" { + + Import-Module $PSScriptRoot\..\LanguageTestSupport.psm1 + + function New-TestModule { + param( + [string]$Name, + [string]$Content, + [switch]$Manifest, + [version]$Version = '1.0', # ignored, if $Manifest -eq $false + [string]$ModulePathPrefix = 'modules' # module is created under TestDrive:\$ModulePathPrefix\$Name + ) - Import-Module $PSScriptRoot\..\LanguageTestSupport.psm1 - - function New-TestModule { - param( - [string]$Name, - [string]$Content, - [switch]$Manifest, - [version]$Version = '1.0', # ignored, if $Manifest -eq $false - [string]$ModulePathPrefix = 'modules' # module is created under TestDrive:\$ModulePathPrefix\$Name - ) - - if ($manifest) { - new-item -type directory -Force "${TestDrive}\$ModulePathPrefix\$Name\$Version" > $null - Set-Content -Path "${TestDrive}\$ModulePathPrefix\$Name\$Version\$Name.psm1" -Value $Content - New-ModuleManifest -RootModule "$Name.psm1" -Path "${TestDrive}\$ModulePathPrefix\$Name\$Version\$Name.psd1" -ModuleVersion $Version - } else { - new-item -type directory -Force "${TestDrive}\$ModulePathPrefix\$Name" > $null - Set-Content -Path "${TestDrive}\$ModulePathPrefix\$Name\$Name.psm1" -Value $Content - } - - $resolvedTestDrivePath = Split-Path ((get-childitem "${TestDrive}\$ModulePathPrefix")[0].FullName) - if (-not ($env:PSMODULEPATH -like "*$resolvedTestDrivePath*")) { - $env:PSMODULEPATH += ";$resolvedTestDrivePath" - } + if ($manifest) { + mkdir -Force "TestDrive:\$ModulePathPrefix\$Name\$Version" > $null + Set-Content -Path TestDrive:\$ModulePathPrefix\$Name\$Version\$Name.psm1 -Value $Content + New-ModuleManifest -RootModule "$Name.psm1" -Path TestDrive:\$ModulePathPrefix\$Name\$Version\$Name.psd1 -ModuleVersion $Version + } else { + mkdir -Force "TestDrive:\$ModulePathPrefix\$Name" > $null + Set-Content -Path TestDrive:\$ModulePathPrefix\$Name\$Name.psm1 -Value $Content } + $resolvedTestDrivePath = Split-Path ((ls TestDrive:\$ModulePathPrefix)[0].FullName) + if (-not ($env:PSModulePath -like "*$resolvedTestDrivePath*")) { + $env:PSModulePath += ";$resolvedTestDrivePath" + } } - AfterAll { - $env:PSMODULEPATH = $originalPSMODULEPATH - } + $originalPSModulePath = $env:PSModulePath - It 'Import-Module has ImplementedAssembly, when classes are present in the module' { + try { + # Create modules in TestDrive:\ New-TestModule -Name Foo -Content 'class Foo { [string] GetModuleName() { return "Foo" } }' New-TestModule -Manifest -Name FooWithManifest -Content 'class Foo { [string] GetModuleName() { return "FooWithManifest" } }' - $module = Import-Module Foo -PassThru - try { - $module.ImplementingAssembly | Should Not Be $null - } finally { - $module | Remove-Module + It 'Import-Module has ImplementedAssembly, when classes are present in the module' { + $module = Import-Module Foo -PassThru + try { + $module.ImplementingAssembly | Should Not Be $null + } finally { + $module | Remove-Module + } } - } - It "can use class from another module as a base class with using module" { - $barType = [scriptblock]::Create(@" + It "can use class from another module as a base class with using module" { + $barType = [scriptblock]::Create(@" using module Foo class Bar : Foo {} [Bar] "@).Invoke() - $barType.BaseType.Name | Should Be 'Foo' - } + $barType.BaseType.Name | Should Be 'Foo' + } - It "can use class from another module in New-Object" { - $foo = [scriptblock]::Create(@" + It "can use class from another module in New-Object" { + $foo = [scriptblock]::Create(@" using module FooWithManifest using module Foo New-Object FooWithManifest.Foo New-Object Foo.Foo "@).Invoke() - $foo.Count | Should Be 2 - $foo[0].GetModuleName() | Should Be 'FooWithManifest' - $foo[1].GetModuleName() | Should Be 'Foo' - } + $foo.Count | Should Be 2 + $foo[0].GetModuleName() | Should Be 'FooWithManifest' + $foo[1].GetModuleName() | Should Be 'Foo' + } - It "can use class from another module by full name as base class and [type]" { - $fooObject = [scriptblock]::Create(@" + It "can use class from another module by full name as base class and [type]" { + $fooObject = [scriptblock]::Create(@" using module Foo class Bar : Foo.Foo {} [Foo.Foo]::new() "@).Invoke() - $fooObject.GetModuleName() | Should Be 'Foo' - } + $fooObject.GetModuleName() | Should Be 'Foo' + } - It "can use modules with classes collision" { - # we use 3 classes with name Foo at the same time - # two of them come from 'using module' and one is defined in the scriptblock itself. - # we should be able to use first two of them by the module-quilified name and the third one it's name. - $fooModuleName = [scriptblock]::Create(@" + It "can use modules with classes collision" { + # we use 3 classes with name Foo at the same time + # two of them come from 'using module' and one is defined in the scriptblock itself. + # we should be able to use first two of them by the module-quilified name and the third one it's name. + $fooModuleName = [scriptblock]::Create(@" using module Foo using module FooWithManifest @@ -99,21 +95,21 @@ class Bar : Foo {} (New-Object Foo).GetModuleName() # This "@).Invoke() - $fooModuleName.Count | Should Be 4 - $fooModuleName[0] | Should Be 'Foo' - $fooModuleName[1] | Should Be 'FooWithManifest' - $fooModuleName[2] | Should Be 'This' - $fooModuleName[3] | Should Be 'This' - } + $fooModuleName.Count | Should Be 4 + $fooModuleName[0] | Should Be 'Foo' + $fooModuleName[1] | Should Be 'FooWithManifest' + $fooModuleName[2] | Should Be 'This' + $fooModuleName[3] | Should Be 'This' + } - It "doesn't mess up two consequitive scripts" { - $sb1 = [scriptblock]::Create(@" + It "doesn't mess up two consequitive scripts" { + $sb1 = [scriptblock]::Create(@" using module Foo class Bar : Foo {} [Bar]::new().GetModuleName() "@) - $sb2 = [scriptblock]::Create(@" + $sb2 = [scriptblock]::Create(@" using module Foo class Foo { [string] GetModuleName() { return "This" } } @@ -121,12 +117,12 @@ class Bar : Foo {} [Bar]::new().GetModuleName() "@) - $sb1.Invoke() | Should Be 'Foo' - $sb2.Invoke() | Should Be 'This' - } + $sb1.Invoke() | Should Be 'Foo' + $sb2.Invoke() | Should Be 'This' + } - It "can use modules with classes collision simple" { - $fooModuleName = [scriptblock]::Create(@" + It "can use modules with classes collision simple" { + $fooModuleName = [scriptblock]::Create(@" using module Foo class Foo { [string] GetModuleName() { return "This" } } @@ -141,302 +137,300 @@ class Bar : Foo {} (New-Object Foo).GetModuleName() # This "@).Invoke() - $fooModuleName.Count | Should Be 5 - $fooModuleName[0] | Should Be 'Foo' - $fooModuleName[1] | Should Be 'Foo' - $fooModuleName[2] | Should Be 'This' - $fooModuleName[3] | Should Be 'This' - $fooModuleName[4] | Should Be 'This' - } + $fooModuleName.Count | Should Be 5 + $fooModuleName[0] | Should Be 'Foo' + $fooModuleName[1] | Should Be 'Foo' + $fooModuleName[2] | Should Be 'This' + $fooModuleName[3] | Should Be 'This' + $fooModuleName[4] | Should Be 'This' + } - It "can use class from another module as a base class with using module with manifest" { - $barType = [scriptblock]::Create(@" + It "can use class from another module as a base class with using module with manifest" { + $barType = [scriptblock]::Create(@" using module FooWithManifest class Bar : Foo {} [Bar] "@).Invoke() - $barType.BaseType.Name | Should Be 'Foo' - } + $barType.BaseType.Name | Should Be 'Foo' + } - It "can instantiate class from another module" { - $foo = [scriptblock]::Create(@" + It "can instantiate class from another module" { + $foo = [scriptblock]::Create(@" using module Foo [Foo]::new() "@).Invoke() - $foo.GetModuleName() | Should Be 'Foo' - } + $foo.GetModuleName() | Should Be 'Foo' + } - It "cannot instantiate class from another module without using statement" { - $err = Get-RuntimeError @" + It "cannot instantiate class from another module without using statement" { + $err = Get-RuntimeError @" #using module Foo [Foo]::new() "@ - $err.FullyQualifiedErrorId | Should Be TypeNotFound - } - - It "can use class from another module in New-Object by short name" { - $foo = [scriptblock]::Create(@" -using module FooWithManifest -New-Object Foo -"@).Invoke() - $foo.GetModuleName() | Should Be 'FooWithManifest' - } - - It "can use class from this module in New-Object by short name" { - $foo = [scriptblock]::Create(@" -class Foo {} -New-Object Foo -"@).Invoke() - $foo | Should Not Be $null - } - - # Pending reason: - # it's not yet implemented. - It "accept module specification" { - $foo = [scriptblock]::Create(@" -using module @{ ModuleName = 'FooWithManifest'; ModuleVersion = '1.0' } -New-Object Foo -"@).Invoke() - $foo.GetModuleName() | Should Be 'FooWithManifest' - } - - Context 'parse time errors' { - - It "report an error about not found module" { - $err = Get-ParseResults "using module ThisModuleDoesntExist" - $err.Count | Should Be 1 - $err[0].ErrorId | Should Be 'ModuleNotFoundDuringParse' + $err.FullyQualifiedErrorId | Should Be TypeNotFound } - It "report an error about misformatted module specification" { - $err = Get-ParseResults "using module @{ Foo = 'Foo' }" - $err.Count | Should Be 1 - $err[0].ErrorId | Should Be 'RequiresModuleInvalid' - } - - It "report an error about wildcard in the module name" { - $err = Get-ParseResults "using module fo*" - $err.Count | Should Be 1 - $err[0].ErrorId | Should Be 'WildCardModuleNameError' - } - - It "report an error about wildcard in the module path" { - $err = Get-ParseResults "using module C:\fo*" - $err.Count | Should Be 1 - $err[0].ErrorId | Should Be 'WildCardModuleNameError' - } - - It "report an error about wildcard in the module name inside ModuleSpecification hashtable" { - $err = Get-ParseResults "using module @{ModuleName = 'Fo*'; RequiredVersion = '1.0'}" - $err.Count | Should Be 1 - $err[0].ErrorId | Should Be 'WildCardModuleNameError' - } - - # MSFT:5246105 - It "report an error when tokenizer encounters comma" { - $err = Get-ParseResults "using module ,FooWithManifest" - $err.Count | Should Be 1 - $err[0].ErrorId | Should Be 'MissingUsingItemName' - } - - It "report an error when tokenizer encounters nothing" { - $err = Get-ParseResults "using module " - $err.Count | Should Be 1 - $err[0].ErrorId | Should Be 'MissingUsingItemName' - } - - It "report an error on badly formatted RequiredVersion" { - $err = Get-ParseResults "using module @{ModuleName = 'FooWithManifest'; RequiredVersion = 1. }" - $err.Count | Should Be 1 - $err[0].ErrorId | Should Be 'RequiresModuleInvalid' - } - - # MSFT:6897275 - It "report an error on incomplete using input" { - $err = Get-ParseResults "using module @{ModuleName = 'FooWithManifest'; FooWithManifest = 1." # missing closing bracket - $err.Count | Should Be 2 - $err[0].ErrorId | Should Be 'IncompleteHashLiteral' - $err[1].ErrorId | Should Be 'RequiresModuleInvalid' - } - - } - - Context 'short name in case of name collision' { - It "cannot use as base class" { - $err = Get-RuntimeError @" -using module Foo -using module FooWithManifest -class Bar : Foo {} -"@ - $err.FullyQualifiedErrorId | Should Be AmbiguousTypeReference - } - - It "cannot use as [...]" { - $err = Get-RuntimeError @" -using module Foo -using module FooWithManifest -[Foo] -"@ - $err.FullyQualifiedErrorId | Should Be AmbiguousTypeReference - } - - It "cannot use in New-Object" { - $err = Get-RuntimeError @" -using module Foo -using module FooWithManifest -New-Object Foo -"@ - $err.FullyQualifiedErrorId | Should Be 'AmbiguousTypeReference,Microsoft.PowerShell.Commands.NewObjectCommand' - } - - It "cannot use [type] cast from string" { - $err = Get-RuntimeError @" -using module Foo -using module FooWithManifest -[type]"Foo" -"@ - $err.FullyQualifiedErrorId | Should Be AmbiguousTypeReference - } - } - - Context 'using use the latest version of module after Import-Module -Force' { - BeforeAll { - New-TestModule -Name Foo -Content 'class Foo { [string] GetModuleName() { return "Foo2" } }' - Import-Module Foo -Force - } - It "can use class from another module as a base class with using module" { - $moduleName = [scriptblock]::Create(@" -using module Foo -[Foo]::new().GetModuleName() -"@).Invoke() - - $moduleName | Should Be 'Foo2' - } - } - - Context 'Side by side' { - BeforeAll { - # Add side-by-side module - $newVersion = '3.4.5' - New-TestModule -Manifest -Name FooWithManifest -Content 'class Foo { [string] GetModuleName() { return "Foo230" } }' -Version '2.3.0' - New-TestModule -Manifest -Name FooWithManifest -Content 'class Foo { [string] GetModuleName() { return "Foo345" } }' -Version '3.4.5' -ModulePathPrefix 'Modules2' - } - - # 'using module' behavior must be alligned with Import-Module. - # Import-Module does the following: - # 1) find the first directory from $env:PSMODULEPATH that contains the module - # 2) Import highest available version of the module - # In out case TestDrive:\Module is before TestDrive:\Modules2 and so 2.3.0 is the right version - It "uses the last module, if multiple versions are present" { + It "can use class from another module in New-Object by short name" { $foo = [scriptblock]::Create(@" using module FooWithManifest -[Foo]::new() -"@).Invoke() - $foo.GetModuleName() | Should Be 'Foo230' - } - - It "uses right version, when RequiredModule=1.0 specified" { - $foo = [scriptblock]::Create(@" -using module @{ModuleName = 'FooWithManifest'; RequiredVersion = '1.0'} -[Foo]::new() +New-Object Foo "@).Invoke() $foo.GetModuleName() | Should Be 'FooWithManifest' } - It "uses right version, when RequiredModule=2.3.0 specified" { + It "can use class from this module in New-Object by short name" { $foo = [scriptblock]::Create(@" +class Foo {} +New-Object Foo +"@).Invoke() + $foo | Should Not Be $null + } + + # Pending reason: + # it's not yet implemented. + It "accept module specification" { + $foo = [scriptblock]::Create(@" +using module @{ ModuleName = 'FooWithManifest'; ModuleVersion = '1.0' } +New-Object Foo +"@).Invoke() + $foo.GetModuleName() | Should Be 'FooWithManifest' + } + + Context 'parse time errors' { + + It "report an error about not found module" { + $err = Get-ParseResults "using module ThisModuleDoesntExist" + $err.Count | Should Be 1 + $err[0].ErrorId | Should Be 'ModuleNotFoundDuringParse' + } + + + It "report an error about misformatted module specification" { + $err = Get-ParseResults "using module @{ Foo = 'Foo' }" + $err.Count | Should Be 1 + $err[0].ErrorId | Should Be 'RequiresModuleInvalid' + } + + It "report an error about wildcard in the module name" { + $err = Get-ParseResults "using module fo*" + $err.Count | Should Be 1 + $err[0].ErrorId | Should Be 'WildCardModuleNameError' + } + + It "report an error about wildcard in the module path" { + $err = Get-ParseResults "using module C:\fo*" + $err.Count | Should Be 1 + $err[0].ErrorId | Should Be 'WildCardModuleNameError' + } + + It "report an error about wildcard in the module name inside ModuleSpecification hashtable" { + $err = Get-ParseResults "using module @{ModuleName = 'Fo*'; RequiredVersion = '1.0'}" + $err.Count | Should Be 1 + $err[0].ErrorId | Should Be 'WildCardModuleNameError' + } + + # MSFT:5246105 + It "report an error when tokenizer encounters comma" { + $err = Get-ParseResults "using module ,FooWithManifest" + $err.Count | Should Be 1 + $err[0].ErrorId | Should Be 'MissingUsingItemName' + } + + It "report an error when tokenizer encounters nothing" { + $err = Get-ParseResults "using module " + $err.Count | Should Be 1 + $err[0].ErrorId | Should Be 'MissingUsingItemName' + } + + It "report an error on badly formatted RequiredVersion" { + $err = Get-ParseResults "using module @{ModuleName = 'FooWithManifest'; RequiredVersion = 1. }" + $err.Count | Should Be 1 + $err[0].ErrorId | Should Be 'RequiresModuleInvalid' + } + + # MSFT:6897275 + It "report an error on incomplete using input" { + $err = Get-ParseResults "using module @{ModuleName = 'FooWithManifest'; FooWithManifest = 1." # missing closing bracket + $err.Count | Should Be 2 + $err[0].ErrorId | Should Be 'IncompleteHashLiteral' + $err[1].ErrorId | Should Be 'RequiresModuleInvalid' + } + + } + + Context 'short name in case of name collision' { + It "cannot use as base class" { + $err = Get-RuntimeError @" +using module Foo +using module FooWithManifest +class Bar : Foo {} +"@ + $err.FullyQualifiedErrorId | Should Be AmbiguousTypeReference + } + + It "cannot use as [...]" { + $err = Get-RuntimeError @" +using module Foo +using module FooWithManifest +[Foo] +"@ + $err.FullyQualifiedErrorId | Should Be AmbiguousTypeReference + } + + It "cannot use in New-Object" { + $err = Get-RuntimeError @" +using module Foo +using module FooWithManifest +New-Object Foo +"@ + $err.FullyQualifiedErrorId | Should Be 'AmbiguousTypeReference,Microsoft.PowerShell.Commands.NewObjectCommand' + } + + It "cannot use [type] cast from string" { + $err = Get-RuntimeError @" +using module Foo +using module FooWithManifest +[type]"Foo" +"@ + $err.FullyQualifiedErrorId | Should Be AmbiguousTypeReference + } + } + + Context 'using use the latest version of module after Import-Module -Force' { + New-TestModule -Name Foo -Content 'class Foo { [string] GetModuleName() { return "Foo2" } }' + Import-Module Foo -Force + It "can use class from another module as a base class with using module" { + $moduleName = [scriptblock]::Create(@" +using module Foo +[Foo]::new().GetModuleName() +"@).Invoke() + + $moduleName | Should Be 'Foo2' + } + } + + Context 'Side by side' { + # Add side-by-side module + $newVersion = '3.4.5' + New-TestModule -Manifest -Name FooWithManifest -Content 'class Foo { [string] GetModuleName() { return "Foo230" } }' -Version '2.3.0' + New-TestModule -Manifest -Name FooWithManifest -Content 'class Foo { [string] GetModuleName() { return "Foo345" } }' -Version '3.4.5' -ModulePathPrefix 'Modules2' + + # 'using module' behavior must be alligned with Import-Module. + # Import-Module does the following: + # 1) find the first directory from $env:PSModulePath that contains the module + # 2) Import highest available version of the module + # In out case TestDrive:\Module is before TestDrive:\Modules2 and so 2.3.0 is the right version + It "uses the last module, if multiple versions are present" { + $foo = [scriptblock]::Create(@" +using module FooWithManifest +[Foo]::new() +"@).Invoke() + $foo.GetModuleName() | Should Be 'Foo230' + } + + It "uses right version, when RequiredModule=1.0 specified" { + $foo = [scriptblock]::Create(@" +using module @{ModuleName = 'FooWithManifest'; RequiredVersion = '1.0'} +[Foo]::new() +"@).Invoke() + $foo.GetModuleName() | Should Be 'FooWithManifest' + } + + It "uses right version, when RequiredModule=2.3.0 specified" { + $foo = [scriptblock]::Create(@" using module @{ModuleName = 'FooWithManifest'; RequiredVersion = '2.3.0'} [Foo]::new() "@).Invoke() - $foo.GetModuleName() | Should Be 'Foo230' - } + $foo.GetModuleName() | Should Be 'Foo230' + } - It "uses right version, when RequiredModule=3.4.5 specified" { - $foo = [scriptblock]::Create(@" + It "uses right version, when RequiredModule=3.4.5 specified" { + $foo = [scriptblock]::Create(@" using module @{ModuleName = 'FooWithManifest'; RequiredVersion = '3.4.5'} [Foo]::new() "@).Invoke() - $foo.GetModuleName() | Should Be 'Foo345' + $foo.GetModuleName() | Should Be 'Foo345' + } } - } - Context 'Use module with runtime error' { - BeforeAll { + Context 'Use module with runtime error' { + New-TestModule -Name ModuleWithRuntimeError -Content @' class Foo { [string] GetModuleName() { return "ModuleWithRuntimeError" } } throw 'error' '@ - } - It "handles runtime errors in imported module" { - $err = Get-RuntimeError @" + It "handles runtime errors in imported module" { + $err = Get-RuntimeError @" using module ModuleWithRuntimeError [Foo]::new().GetModuleName() "@ $err | Should Be 'error' + } } - } - Context 'shared InitialSessionState' { + Context 'shared InitialSessionState' { - It 'can pick the right module' { + It 'can pick the right module' { - $scriptToProcessPath = "${TestDrive}\toProcess.ps1" - Set-Content -Path $scriptToProcessPath -Value @' + $scriptToProcessPath = 'TestDrive:\toProcess.ps1' + Set-Content -Path $scriptToProcessPath -Value @' using module Foo function foo() { [Foo]::new() } '@ - # resolve name to absolute path - $scriptToProcessPath = (get-childitem $scriptToProcessPath).FullName - $iss = [System.Management.Automation.Runspaces.initialsessionstate]::CreateDefault() - $iss.StartupScripts.Add($scriptToProcessPath) + # resolve name to absolute path + $scriptToProcessPath = (ls $scriptToProcessPath).FullName + $iss = [System.Management.Automation.Runspaces.initialsessionstate]::CreateDefault() + $iss.StartupScripts.Add($scriptToProcessPath) - $ps = [powershell]::Create($iss) - $ps.AddCommand("foo").Invoke() | Should be Foo - $ps.Streams.Error | Should Be $null + $ps = [powershell]::Create($iss) + $ps.AddCommand("foo").Invoke() | Should be Foo + $ps.Streams.Error | Should Be $null - $ps1 = [powershell]::Create($iss) - $ps1.AddCommand("foo").Invoke() | Should be Foo - $ps1.Streams.Error | Should Be $null + $ps1 = [powershell]::Create($iss) + $ps1.AddCommand("foo").Invoke() | Should be Foo + $ps1.Streams.Error | Should Be $null - $ps.Commands.Clear() - $ps.Streams.Error.Clear() - $ps.AddScript(". foo").Invoke() | Should be Foo - $ps.Streams.Error | Should Be $null + $ps.Commands.Clear() + $ps.Streams.Error.Clear() + $ps.AddScript(". foo").Invoke() | Should be Foo + $ps.Streams.Error | Should Be $null + } } - } + # this is a setup for Context "Module by path" + New-TestModule -Name FooForPaths -Content 'class Foo { [string] GetModuleName() { return "FooForPaths" } }' - # here we are back to normal $env:PSMODULEPATH, but all modules are there + + } finally { + $env:PSModulePath = $originalPSModulePath + } + + # here we are back to normal $env:PSModulePath, but all modules are there Context "Module by path" { - BeforeAll { - # this is a setup for Context "Module by path" - New-TestModule -Name FooForPaths -Content 'class Foo { [string] GetModuleName() { return "FooForPaths" } }' - $env:PSMODULEPATH = $originalPSMODULEPATH - new-item -type directory -Force TestDrive:\FooRelativeConsumer - Set-Content -Path "${TestDrive}\FooRelativeConsumer\FooRelativeConsumer.ps1" -Value @' -using module ..\modules\FooForPaths + It 'use non-modified PSModulePath' { + $env:PSModulePath | Should Be $originalPSModulePath + } + + mkdir -Force TestDrive:\FooRelativeConsumer + Set-Content -Path TestDrive:\FooRelativeConsumer\FooRelativeConsumer.ps1 -Value @' +using module ..\Modules\FooForPaths class Bar : Foo {} [Bar]::new() '@ - Set-Content -Path "${TestDrive}\FooRelativeConsumerErr.ps1" -Value @' + Set-Content -Path TestDrive:\FooRelativeConsumerErr.ps1 -Value @' using module FooForPaths class Bar : Foo {} [Bar]::new() '@ - } - - It 'use non-modified PSMODULEPATH' { - $env:PSMODULEPATH | Should Be $originalPSMODULEPATH - } It "can be accessed by relative path" { $barObject = & TestDrive:\FooRelativeConsumer\FooRelativeConsumer.ps1 @@ -449,7 +443,7 @@ class Bar : Foo {} } It "can be accessed by absolute path" { - $resolvedTestDrivePath = Split-Path ((get-childitem TestDrive:\modules)[0].FullName) + $resolvedTestDrivePath = Split-Path ((ls TestDrive:\Modules)[0].FullName) $s = @" using module $resolvedTestDrivePath\FooForPaths [Foo]::new() @@ -461,7 +455,7 @@ using module $resolvedTestDrivePath\FooForPaths } It "can be accessed by absolute path with file extension" { - $resolvedTestDrivePath = Split-Path ((get-childitem TestDrive:\modules)[0].FullName) + $resolvedTestDrivePath = Split-Path ((ls TestDrive:\Modules)[0].FullName) $barObject = [scriptblock]::Create(@" using module $resolvedTestDrivePath\FooForPaths\FooForPaths.psm1 [Foo]::new() @@ -477,7 +471,7 @@ using module .\FooForPaths "@ $err.FullyQualifiedErrorId | Should Be ModuleNotFoundDuringParse - Push-Location TestDrive:\modules + Push-Location TestDrive:\Modules try { $barObject = [scriptblock]::Create(@" using module .\FooForPaths @@ -490,7 +484,7 @@ using module .\FooForPaths } It "cannot be accessed by relative path without .\" { - Push-Location TestDrive:\modules + Push-Location TestDrive:\Modules try { $err = Get-RuntimeError @" using module FooForPaths diff --git a/test/powershell/Language/Classes/scripting.enums.tests.ps1 b/test/powershell/Language/Classes/scripting.enums.tests.ps1 index fbca0604c..88258d620 100644 --- a/test/powershell/Language/Classes/scripting.enums.tests.ps1 +++ b/test/powershell/Language/Classes/scripting.enums.tests.ps1 @@ -2,7 +2,7 @@ # Copyright (c) Microsoft Corporation, 2015 # -Describe 'enums' -Tags "CI" { +Describe 'enums' -Tags "DRT" { Context 'basic enums' { enum E1 @@ -73,7 +73,7 @@ Describe 'enums' -Tags "CI" { } } -Describe 'Basic enum errors' -Tags "CI" { +Describe 'Basic enum errors' -Tags "DRT" { Import-Module $PSScriptRoot\..\LanguageTestSupport.psm1 diff --git a/test/powershell/Language/CompletionTestSupport.psm1 b/test/powershell/Language/CompletionTestSupport.psm1 index bbda7ac58..aeaa12da5 100644 --- a/test/powershell/Language/CompletionTestSupport.psm1 +++ b/test/powershell/Language/CompletionTestSupport.psm1 @@ -98,7 +98,7 @@ function Test-Completions { foreach ($test in $TestCases) { - Describe $test.Description -Tags "CI" { + Describe $test.Description { $hash = $Test.TestInput $results = Get-Completions @hash diff --git a/test/powershell/Language/Parser/Ast.Tests.ps1 b/test/powershell/Language/Parser/Ast.Tests.ps1 index fa3341c97..f220ef362 100644 --- a/test/powershell/Language/Parser/Ast.Tests.ps1 +++ b/test/powershell/Language/Parser/Ast.Tests.ps1 @@ -1,5 +1,5 @@ using Namespace System.Management.Automation.Language -Describe "The SafeGetValue method on AST returns safe values" -Tags "CI" { +Describe "The SafeGetValue method on AST returns safe values" -Tags "DRT" { It "A hashtable is returned from a HashtableAst" { $HashtableAstType = [HashtableAst] $HtAst = { diff --git a/test/powershell/Language/Parser/AutomaticVariables.Tests.ps1 b/test/powershell/Language/Parser/AutomaticVariables.Tests.ps1 index b73d68dfa..0912e2206 100644 --- a/test/powershell/Language/Parser/AutomaticVariables.Tests.ps1 +++ b/test/powershell/Language/Parser/AutomaticVariables.Tests.ps1 @@ -1,8 +1,6 @@ -Describe 'Automatic variable $input' -Tags "CI" { - # Skip on hold for discussion on https://github.com/PowerShell/PowerShell/issues/1563 - # $input type in advanced functions - It '$input Type should be enumerator' -Skip { +Describe 'Automatic variable $input' { + It '$input Type should be enumerator' { function from_begin { [cmdletbinding()]param() begin { Write-Output -NoEnumerate $input } } function from_process { [cmdletbinding()]param() process { Write-Output -NoEnumerate $input } } function from_end { [cmdletbinding()]param() end { Write-Output -NoEnumerate $input } } diff --git a/test/powershell/Language/Parser/BNotOperator.Tests.ps1 b/test/powershell/Language/Parser/BNotOperator.Tests.ps1 index 79475e58e..8e5c4be66 100644 --- a/test/powershell/Language/Parser/BNotOperator.Tests.ps1 +++ b/test/powershell/Language/Parser/BNotOperator.Tests.ps1 @@ -32,7 +32,7 @@ $typeDefinition += "`n}" Write-Verbose $typeDefinition Add-Type $typeDefinition -Describe "bnot on enums" -Tags "CI" { +Describe "bnot on enums" -Tags "DRT" { foreach ($enumType in [type[]]$enumTypeNames) { Context $enumType.Name { @@ -63,7 +63,7 @@ Describe "bnot on enums" -Tags "CI" { } } -Describe "bnot on integral types" -Tags "CI" { +Describe "bnot on integral types" -Tags "DRT" { foreach ($baseType in $baseTypes.Keys) { Context $baseType.Name { diff --git a/test/powershell/Language/Parser/Conversions.Tests.ps1 b/test/powershell/Language/Parser/Conversions.Tests.ps1 index 1b6bc63f1..593ba4281 100644 --- a/test/powershell/Language/Parser/Conversions.Tests.ps1 +++ b/test/powershell/Language/Parser/Conversions.Tests.ps1 @@ -1,4 +1,4 @@ -Describe 'conversion syntax' -Tags "CI" { +Describe 'conversion syntax' -Tags "innerloop", "DRT" { # these test suite covers ([]).() syntax. # it mixes two purposes: casting and super-class method calls. diff --git a/test/powershell/Language/Parser/ExtensibleCompletion.Tests.ps1 b/test/powershell/Language/Parser/ExtensibleCompletion.Tests.ps1 index 77cdcfd2c..bffad6e4d 100644 --- a/test/powershell/Language/Parser/ExtensibleCompletion.Tests.ps1 +++ b/test/powershell/Language/Parser/ExtensibleCompletion.Tests.ps1 @@ -104,9 +104,7 @@ function Test-Completions } foreach ($expected in $test.ExpectedResults) { - $skip = $false - if ( $expected.CompletionText -match "System.Management.Automation.PerformanceData|System.Management.Automation.Security" ) { $skip = $true } - It ($expected.CompletionText) -skip:$skip { + It ($expected.CompletionText) { $expected.Found | Should Be $true } } @@ -173,7 +171,7 @@ function TestFunction ) } -Describe "Script block based extensible completion" -Tags "CI" { +Describe "Script block based extensible completion" -Tags "Innerloop", "BVT" { @{ ExpectedResults = @( @{CompletionText = "beta: 11 gamma: 22 command: TestFunction parameterName: Alpha wordToComplete: aa" @@ -182,7 +180,7 @@ Describe "Script block based extensible completion" -Tags "CI" { } | Get-CompletionTestCaseData | Test-Completions } -Describe "Test class based extensible completion" -Tags "CI" { +Describe "Test class based extensible completion" -Tags "Innerloop", "BVT" { @{ ExpectedResults = @( @{CompletionText = "alpha: 42 gamma: 44 command: TestFunction parameterName: Beta wordToComplete: zz" @@ -191,7 +189,7 @@ Describe "Test class based extensible completion" -Tags "CI" { } | Get-CompletionTestCaseData | Test-Completions } -Describe "Test registration based exensible completion" -Tags "CI" { +Describe "Test registration based exensible completion" -Tags "Innerloop", "BVT" { Register-ArgumentCompleter -Command TestFunction -Parameter Gamma -ScriptBlock { param( [string] $CommandName, @@ -214,7 +212,7 @@ Describe "Test registration based exensible completion" -Tags "CI" { } | Get-CompletionTestCaseData | Test-Completions } -Describe "Test extensible completion of native commands" -Tags "CI" { +Describe "Test extensible completion of native commands" -Tags "Innerloop", "BVT" { Register-ArgumentCompleter -Command netsh -Native -ScriptBlock { [CompletionResult]::new('advfirewall', 'advfirewall', "ParameterValue", 'advfirewall') [CompletionResult]::new('bridge', 'bridge', "ParameterValue", 'bridge') @@ -229,7 +227,7 @@ Describe "Test extensible completion of native commands" -Tags "CI" { } | Get-CompletionTestCaseData | Test-Completions } -Describe "Test extensible completion of using namespace" -Tags "CI" { +Describe "Test extensible completion of using namespace" -Tags "Innerloop", "BVT" { @{ ExpectedResults = @( @{CompletionText = "System"; ResultType = "Namespace"} @@ -266,7 +264,7 @@ Describe "Test extensible completion of using namespace" -Tags "CI" { } | Get-CompletionTestCaseData | Test-Completions } -Describe "Type extensible completion of type after using namespace" -Tags "CI" { +Describe "Type extensible completion of type after using namespace" -Tags "Innerloop", "BVT" { @{ ExpectedResults = @( @{CompletionText = "IO.TextReader"; ResultType = "Type"} @@ -293,7 +291,7 @@ Describe "Type extensible completion of type after using namespace" -Tags "CI" { } | Get-CompletionTestCaseData | Test-Completions } -Describe "Additional type name completion tests" -Tags "CI" { +Describe "Additional type name completion tests" -Tags "Innerloop", "BVT" { @{ ExpectedResults = @( @{CompletionText = "System"; ResultType = "Namespace"} @@ -310,15 +308,15 @@ Describe "Additional type name completion tests" -Tags "CI" { }, @{ ExpectedResults = @( - @{CompletionText = "System.Collections.Generic.LinkedList"; ResultType = "Type"; ListItemText = "LinkedList<>"; ToolTip = "System.Collections.Generic.LinkedList[T]"} - @{CompletionText = "System.Collections.Generic.LinkedListNode"; ResultType = "Type"; ListItemText = "LinkedListNode<>"; ToolTip = "System.Collections.Generic.LinkedListNode[T]"} - @{CompletionText = "System.Collections.Generic.List"; ResultType = "Type"; ListItemText = "List<>"; ToolTip = "System.Collections.Generic.List[T]"} + @{CompletionText = "System.Collections.Generic.LinkedList"; ResultType = "Type"; ListItemText = "LinkedList<>"; ToolTip = "Class System.Collections.Generic.LinkedList[T]"} + @{CompletionText = "System.Collections.Generic.LinkedListNode"; ResultType = "Type"; ListItemText = "LinkedListNode<>"; ToolTip = "Class System.Collections.Generic.LinkedListNode[T]"} + @{CompletionText = "System.Collections.Generic.List"; ResultType = "Type"; ListItemText = "List<>"; ToolTip = "Class System.Collections.Generic.List[T]"} ) TestInput = 'Get-Command -ParameterType System.Collections.Generic.Li' }, @{ ExpectedResults = @( - @{CompletionText = "System.Collections.Generic.Dictionary"; ResultType = "Type"; ListItemText = "Dictionary<>"; ToolTip = "System.Collections.Generic.Dictionary[T1, T2]"} + @{CompletionText = "System.Collections.Generic.Dictionary"; ResultType = "Type"; ListItemText = "Dictionary<>"; ToolTip = "Class System.Collections.Generic.Dictionary[TKey, TValue]"} ) TestInput = 'Get-Command -ParameterType System.Collections.Generic.Dic' } | Get-CompletionTestCaseData | Test-Completions diff --git a/test/powershell/Language/Parser/LanguageAndParser.TestFollowup.Tests.ps1 b/test/powershell/Language/Parser/LanguageAndParser.TestFollowup.Tests.ps1 index 9854493d8..a8b2e4f5f 100644 --- a/test/powershell/Language/Parser/LanguageAndParser.TestFollowup.Tests.ps1 +++ b/test/powershell/Language/Parser/LanguageAndParser.TestFollowup.Tests.ps1 @@ -1,6 +1,5 @@ -$powershellexe = (get-process -id $PID).mainmodule.filename -Describe "Clone array" -Tags "CI" { +Describe "Clone array" -Tags DRT { It "Cast in target expr" { (([int[]](42)).clone()) | Should Be 42 (([int[]](1..5)).clone()).Length | Should Be 5 @@ -16,7 +15,7 @@ Describe "Clone array" -Tags "CI" { } } -Describe "Set fields through PSMemberInfo" -Tags "CI" { +Describe "Set fields through PSMemberInfo" -Tags DRT { Add-Type @" public struct AStruct { public string s; } "@ @@ -34,12 +33,12 @@ Describe "Set fields through PSMemberInfo" -Tags "CI" { } } -Describe "MSFT:3309783" -Tags "CI" { +Describe "MSFT:3309783" -Tags DRT { It "Run in another process" { # For a reliable test, we must run this in a new process because an earlier binding in this process # could mask the bug/fix. - & $powershellexe -noprofile -command "[psobject] | % FullName" | Should Be System.Management.Automation.PSObject + powershell -noprofile -command "[psobject] | % FullName" | Should Be System.Management.Automation.PSObject } It "Run in current process" { @@ -63,7 +62,7 @@ Describe "MSFT:3309783" -Tags "CI" { } } -Describe "ScriptBlockAst.GetScriptBlock throws on error" -Tags "CI" { +Describe "ScriptBlockAst.GetScriptBlock throws on error" -Tags DRT { $e = $null @@ -81,7 +80,7 @@ Describe "ScriptBlockAst.GetScriptBlock throws on error" -Tags "CI" { } } -Describe "Hashtable key property syntax" -Tags "CI" { +Describe "Hashtable key property syntax" -Tags DRT { $script = @' # First create a hashtable wrapped in PSObject $hash = New-Object hashtable @@ -102,11 +101,11 @@ Describe "Hashtable key property syntax" -Tags "CI" { It "In different process" { # So also run in a fresh process $bytes = [System.Text.Encoding]::Unicode.GetBytes($script) - & $powershellexe -noprofile -encodedCommand ([Convert]::ToBase64String($bytes)) | Should Be Hello + powershell -noprofile -encodedCommand ([Convert]::ToBase64String($bytes)) | Should Be Hello } } -Describe "Assign automatic variables" -Tags "CI" { +Describe "Assign automatic variables" -Tags DRT { $autos = '_', 'args', 'this', 'input', 'pscmdlet', 'psboundparameters', 'myinvocation', 'psscriptroot', 'pscommandpath' @@ -142,7 +141,7 @@ Describe "Assign automatic variables" -Tags "CI" { } } -Describe "Attribute error position" -Tags "CI" { +Describe "Attribute error position" -Tags DRT { It "Ambiguous overloads" { try { @@ -162,7 +161,7 @@ Describe "Attribute error position" -Tags "CI" { } } -Describe "Multiple alias attributes" -Tags "CI" { +Describe "Multiple alias attributes" -Tags DRT { It "basic test" { function foo { param( @@ -179,7 +178,7 @@ Describe "Multiple alias attributes" -Tags "CI" { } } -Describe "Members of System.Type" -Tags "CI" { +Describe "Members of System.Type" -Tags DRT { It "Members in public classes derived from System.Type should be found" { class MyType : System.Collections.IEnumerable { diff --git a/test/powershell/Language/Parser/MethodInvocation.Tests.ps1 b/test/powershell/Language/Parser/MethodInvocation.Tests.ps1 index f7b5bfd5a..d3c87a2a5 100644 --- a/test/powershell/Language/Parser/MethodInvocation.Tests.ps1 +++ b/test/powershell/Language/Parser/MethodInvocation.Tests.ps1 @@ -1,8 +1,5 @@ -if ( $IsCoreCLR ) { - return -} -Describe "Interface inheritance with remoting proxies" -Tags "CI" { +Describe "Interface inheritance with remoting proxies" -Tags "P1", "RI" { $src = @" using System; using System.ServiceModel; diff --git a/test/powershell/Language/Parser/ParameterBinding.Tests.ps1 b/test/powershell/Language/Parser/ParameterBinding.Tests.ps1 index b5ae9b7d5..0d08df763 100644 --- a/test/powershell/Language/Parser/ParameterBinding.Tests.ps1 +++ b/test/powershell/Language/Parser/ParameterBinding.Tests.ps1 @@ -1,6 +1,6 @@ -Describe 'Argument transformation attribute on optional argument with explicit $null' -Tags "CI" { - $tdefinition = @' +Describe 'Argument transformation attribute on optional argument with explicit $null' -Tags "P1", "RI" { + $mod = Add-Type -PassThru -TypeDefinition @' using System; using System.Management.Automation; using System.Reflection; @@ -45,7 +45,6 @@ Describe 'Argument transformation attribute on optional argument with explicit $ } } '@ - $mod = Add-Type -PassThru -TypeDefinition $tdefinition -refer mscorlib,System.Management.Automation Import-Module $mod[0].Assembly @@ -68,29 +67,13 @@ Describe 'Argument transformation attribute on optional argument with explicit $ } - It "Script function takes object" { - Invoke-ScriptFunctionTakesObject | Should Be 42 - } - It "Script function takes uint64" { - Invoke-ScriptFunctionTakesUInt64 | Should Be 42 - } - it "csharp cmdlet takes object" { - Invoke-CSharpCmdletTakesObject | Should Be "passed in null" - } - it "csharp cmdlet takes uint64" { - Invoke-CSharpCmdletTakesUInt64 | Should Be 0 - } + Invoke-ScriptFunctionTakesObject | Should Be 42 + Invoke-ScriptFunctionTakesUInt64 | Should Be 42 + Invoke-CSharpCmdletTakesObject | Should Be "passed in null" + Invoke-CSharpCmdletTakesUInt64 | Should Be 0 - it "script function takes object when parameter is null" { - Invoke-ScriptFunctionTakesObject -Address $null | Should Be 42 - } - it "script function takes unit64 when parameter is null" { - Invoke-ScriptFunctionTakesUInt64 -Address $null | Should Be 42 - } - it "script csharp cmdlet takes object when parameter is null" { - Invoke-CSharpCmdletTakesObject -Address $null | Should Be 42 - } - it "script csharp cmdlet takes uint64 when parameter is null" { - Invoke-CSharpCmdletTakesUInt64 -Address $null | Should Be 42 - } + Invoke-ScriptFunctionTakesObject -Address $null | Should Be 42 + Invoke-ScriptFunctionTakesUInt64 -Address $null | Should Be 42 + Invoke-CSharpCmdletTakesObject -Address $null | Should Be 42 + Invoke-CSharpCmdletTakesUInt64 -Address $null | Should Be 42 } diff --git a/test/powershell/Language/Parser/RedirectionOperator.Tests.ps1 b/test/powershell/Language/Parser/RedirectionOperator.Tests.ps1 index 82a79fb7b..9e641acff 100644 --- a/test/powershell/Language/Parser/RedirectionOperator.Tests.ps1 +++ b/test/powershell/Language/Parser/RedirectionOperator.Tests.ps1 @@ -1,14 +1,7 @@ -Describe "Redirection operator now supports encoding changes" -Tags "CI" { +Describe "Redirection operator now supports encoding changes" { BeforeAll { $asciiString = "abc" - - if ( $IsWindows ) { - $asciiCR = "`r`n" - } - else { - $asciiCR = [string][char]10 - } - + $asciiCR = "`r`n" # If out-file -encoding happens to have a default, be sure to # save it away diff --git a/test/powershell/Language/Parser/TypeAccelerator.Tests.ps1 b/test/powershell/Language/Parser/TypeAccelerator.Tests.ps1 index 8e8c5744d..fe011a453 100644 --- a/test/powershell/Language/Parser/TypeAccelerator.Tests.ps1 +++ b/test/powershell/Language/Parser/TypeAccelerator.Tests.ps1 @@ -1,5 +1,5 @@ -Describe "Type accelerators" -Tags "CI" { +Describe "Type accelerators" -Tags "DRT" { $TypeAcceleratorsType = [psobject].Assembly.GetType("System.Management.Automation.TypeAccelerators") $TypeAccelerators = $TypeAcceleratorsType::Get @@ -11,8 +11,7 @@ Describe "Type accelerators" -Tags "CI" { } It "Can query type accelerators" { - if ( $IsCoreCLR ) { $count = 80 } else { $count = 82 } - $TypeAccelerators.Count -gt $count | Should Be $true + $TypeAccelerators.Count -gt 82 | Should Be $true $TypeAccelerators['xml'] | Should Be ([System.Xml.XmlDocument]) $TypeAccelerators['AllowNull'] | Should Be ([System.Management.Automation.AllowNullAttribute]) } diff --git a/test/powershell/Language/Parser/UsingAssembly.Tests.ps1 b/test/powershell/Language/Parser/UsingAssembly.Tests.ps1 index c45e143cd..deb420045 100644 --- a/test/powershell/Language/Parser/UsingAssembly.Tests.ps1 +++ b/test/powershell/Language/Parser/UsingAssembly.Tests.ps1 @@ -1,5 +1,5 @@ -Describe "Using assembly" -Tags "CI" { +Describe "Using assembly" -Tags "DRT" { try { @@ -42,7 +42,7 @@ public class ABC {} $err[0].ErrorId | Should Be CannotLoadAssemblyWithUriSchema } - It "parse does not load the assembly" -pending { + It "parse does not load the assembly" { $assemblies = [Appdomain]::CurrentDomain.GetAssemblies().GetName().Name $assemblies -contains "UsingAssemblyTest$guid" | Should Be $false @@ -78,7 +78,7 @@ public class ABC {} $failed | Should be $true } #> - It "Assembly loaded at runtime" -pending { + It "Assembly loaded at runtime" { $assemblies = powershell -noprofile -command @" using assembly .\UsingAssemblyTest$guid.dll [Appdomain]::CurrentDomain.GetAssemblies().GetName().Name diff --git a/test/powershell/Language/Parser/UsingNamespace.Tests.ps1 b/test/powershell/Language/Parser/UsingNamespace.Tests.ps1 index 522fe1866..b2ad631cc 100644 --- a/test/powershell/Language/Parser/UsingNamespace.Tests.ps1 +++ b/test/powershell/Language/Parser/UsingNamespace.Tests.ps1 @@ -4,7 +4,6 @@ #using namespace System using namespace System.Threading using namespace System.Timers -using namespace System.Diagnostics # Test parsing more than one using statement on one line using namespace System.Diagnostics; using namespace System.Runtime.CompilerServices using namespace System.Collections.Generic @@ -49,7 +48,7 @@ class C1 { [Thread][CompilerGenerated()]$Thread [Int32][CompilerGenerated()]$Int - #[ElapsedEventHandler][CompilerGenerated()]$EventHandler + [ElapsedEventHandler][CompilerGenerated()]$EventHandler } # Test attributes that won't be found w/o using, but w/ implicit Attribute suffix @@ -58,30 +57,30 @@ class C2 { [Thread][CompilerGeneratedAttribute()]$Thread [Int32][CompilerGeneratedAttribute()]$Int - #[ElapsedEventHandler][CompilerGeneratedAttribute()]$EventHandler + [ElapsedEventHandler][CompilerGeneratedAttribute()]$EventHandler } -Describe "Using Namespace" -Tags "CI" { +Describe "Using Namespace" -Tags "DRT" { It "Type literals w/ using namespace" { [Thread].FullName | Should Be System.Threading.Thread [Int32].FullName | Should Be System.Int32 - #[ElapsedEventHandler].FullName | Should Be System.Timers.ElapsedEventHandler + [ElapsedEventHandler].FullName | Should Be System.Timers.ElapsedEventHandler [C1].GetProperty("Thread").PropertyType.FullName | Should Be System.Threading.Thread [C1].GetProperty("Int").PropertyType.FullName | Should Be System.Int32 - # [C1].GetProperty("EventHandler").PropertyType.FullName | Should Be System.Timers.ElapsedEventHandler + [C1].GetProperty("EventHandler").PropertyType.FullName | Should Be System.Timers.ElapsedEventHandler } It "Covert string to Type w/ using namespace" { ("Thread" -as [Type]).FullName | Should Be System.Threading.Thread ("Int32" -as [Type]).FullName | Should Be System.Int32 - # ("ElapsedEventHandler" -as [Type]).FullName | Should Be System.Timers.ElapsedEventHandler + ("ElapsedEventHandler" -as [Type]).FullName | Should Be System.Timers.ElapsedEventHandler New-Object Int32 | Should Be 0 New-Object CompilerGeneratedAttribute | Should Be System.Runtime.CompilerServices.CompilerGeneratedAttribute } - It "Attributes w/ using namespace" -pending { + It "Attributes w/ using namespace" { function foo { [DebuggerStepThrough()] @@ -104,11 +103,11 @@ Describe "Using Namespace" -Tags "CI" { [C1].GetProperty("Thread").GetCustomAttributesData()[0].AttributeType.FullName | Should Be System.Runtime.CompilerServices.CompilerGeneratedAttribute [C1].GetProperty("Int").GetCustomAttributesData()[0].AttributeType.FullName | Should Be System.Runtime.CompilerServices.CompilerGeneratedAttribute - # [C1].GetProperty("EventHandler").GetCustomAttributesData()[0].AttributeType.FullName | Should Be System.Runtime.CompilerServices.CompilerGeneratedAttribute + [C1].GetProperty("EventHandler").GetCustomAttributesData()[0].AttributeType.FullName | Should Be System.Runtime.CompilerServices.CompilerGeneratedAttribute [C2].GetProperty("Thread").GetCustomAttributesData()[0].AttributeType.FullName | Should Be System.Runtime.CompilerServices.CompilerGeneratedAttribute [C2].GetProperty("Int").GetCustomAttributesData()[0].AttributeType.FullName | Should Be System.Runtime.CompilerServices.CompilerGeneratedAttribute - # [C2].GetProperty("EventHandler").GetCustomAttributesData()[0].AttributeType.FullName | Should Be System.Runtime.CompilerServices.CompilerGeneratedAttribute + [C2].GetProperty("EventHandler").GetCustomAttributesData()[0].AttributeType.FullName | Should Be System.Runtime.CompilerServices.CompilerGeneratedAttribute [C1].GetCustomAttributesData()[0].AttributeType.FullName | Should Be System.Runtime.CompilerServices.CompilerGeneratedAttribute [C2].GetCustomAttributesData()[0].AttributeType.FullName | Should Be System.Runtime.CompilerServices.CompilerGeneratedAttribute @@ -117,7 +116,7 @@ Describe "Using Namespace" -Tags "CI" { } It "Ambiguous type reference" { - { [ThreadState] } | ShouldBeErrorId AmbiguousTypeReference + { [Timer] } | ShouldBeErrorId AmbiguousTypeReference } It "Parameters" { diff --git a/test/powershell/Language/Scripting/Debugging/DebuggerScriptTests.Tests.ps1 b/test/powershell/Language/Scripting/Debugging/DebuggerScriptTests.Tests.ps1 index 682079824..82a342a36 100644 Binary files a/test/powershell/Language/Scripting/Debugging/DebuggerScriptTests.Tests.ps1 and b/test/powershell/Language/Scripting/Debugging/DebuggerScriptTests.Tests.ps1 differ diff --git a/test/powershell/Language/Scripting/Debugging/DebuggingInHost.Tests.ps1 b/test/powershell/Language/Scripting/Debugging/DebuggingInHost.Tests.ps1 index b8b07e739..81628df62 100644 --- a/test/powershell/Language/Scripting/Debugging/DebuggingInHost.Tests.ps1 +++ b/test/powershell/Language/Scripting/Debugging/DebuggingInHost.Tests.ps1 @@ -4,7 +4,7 @@ ## Debugging in Host tests ## -Describe "Tests Debugger GetCallStack() on runspaces when attached to a WinRM host process" -Tags "CI" { +Describe "Tests Debugger GetCallStack() on runspaces when attached to a WinRM host process" -Tags 'InnerLoop','P1' { It -skip "Disabled test because it is fragile and does not consistently succeed on test VMs" { } return diff --git a/test/powershell/Modules/Microsoft.PowerShell.Management/TimeZone.Tests.ps1 b/test/powershell/Modules/Microsoft.PowerShell.Management/TimeZone.Tests.ps1 index 3a87622ce..775dab764 100644 --- a/test/powershell/Modules/Microsoft.PowerShell.Management/TimeZone.Tests.ps1 +++ b/test/powershell/Modules/Microsoft.PowerShell.Management/TimeZone.Tests.ps1 @@ -9,13 +9,11 @@ Localization Many of the tests below looking-up timezones by Name do not support localization. That is, the current tests use us english versions of StandardName and DaylighName for tests. - + ref: https://msdn.microsoft.com/en-us/library/windows/desktop/ms725481.aspx [snippet] Both StandardName and DaylightName are localized according to the current user default UI language. #> -if ($IsWindows) { - function Assert-ListsSame { param([object[]] $expected, [object[]] $observed ) @@ -28,200 +26,232 @@ function Assert-ListsSame } } -Describe "Get-Timezone test case no switches" -Tags "CI" { +Describe "Get-Timezone test case no switches" -tags 'BVT' { It "Call without ListAvailable switch returns current TimeZoneInfo" { - $observed = (Get-TimeZone).Id - $expected = ([System.TimeZoneInfo]::Local).Id - $observed -eq $expected | Should Be $true - } + $result = Remotely { + $observed = (Get-TimeZone).Id + $expected = ([System.TimeZoneInfo]::Local).Id + return $observed -eq $expected + } + $result | Should Be $true + } } -Describe "Get-Timezone test cases" -Tags "CI" { +Describe "Get-Timezone test cases" -tags 'Innerloop','RI' { It "Call without ListAvailable switch returns an object of type TimeZoneInfo" { - $result = (Get-TimeZone).GetType().Name + $result = Remotely { (Get-TimeZone).GetType().Name } $result | Should Be "TimeZoneInfo" - } + } It "Call WITH ListAvailable switch returns ArrayList of TimeZoneInfo objects where the list is greater than 0 item" { - $list = Get-TimeZone -ListAvailable - $list.Count -gt 0 | Should Be $true - - $list.GetType().Name | Should Be "Object[]" - $list[0].GetType().Name | Should Be "TimeZoneInfo" - } + $result = Remotely { + $list = Get-TimeZone -ListAvailable + $observedListType = $list.GetType().Name + $observedItemType = $list[0].GetType().Name + return @($observedListType,$observedItemType,$list.Count > 0) + } + $result | Should Be @("Object[]","TimeZoneInfo",$true) + } It "Call with ListAvailable switch returns a list containing TimeZoneInfo.Local" { - $observedIdList = Get-TimeZone -ListAvailable | select -ExpandProperty Id - $oneExpectedId = ([System.TimeZoneInfo]::Local).Id - $observedIdList -contains $oneExpectedId | Should Be $true - } + $result = Remotely { + $observedIdList = Get-TimeZone -ListAvailable | select -ExpandProperty Id + $oneExpectedId = ([System.TimeZoneInfo]::Local).Id + $observedIdList -contains $oneExpectedId + } + $result | Should Be $true + } It "Call with ListAvailable switch returns a list containing one returned by Get-TimeZone" { - $observedIdList = Get-TimeZone -ListAvailable | select -ExpandProperty Id - $oneExpectedId = (Get-TimeZone).Id - $observedIdList -contains $oneExpectedId | Should Be $true + $result = Remotely { + $observedIdList = Get-TimeZone -ListAvailable | select -ExpandProperty Id + $oneExpectedId = (Get-TimeZone).Id + $observedIdList -contains $oneExpectedId + } + $result | Should Be $true } - + It "Call Get-TimeZone using ID param and single item" { - (Get-TimeZone -Id "Cape Verde Standard Time").Id -eq "Cape Verde Standard Time" | Should Be $true - } - + $result = Remotely { (Get-TimeZone -Id "Cape Verde Standard Time").Id -eq "Cape Verde Standard Time" } + $result | Should Be $true + } + It "Call Get-TimeZone using ID param and multiple items" { $idList = @("Cape Verde Standard Time","Morocco Standard Time","Azores Standard Time") - $result = (Get-TimeZone -Id $idList).Id - Assert-ListsSame $result $idList - } - + $result = Remotely { + param([string[]] $idList) + (Get-TimeZone -Id $idList).Id + } -ArgumentList (,$idList) + Assert-ListsSame $result $idList + } + It "Call Get-TimeZone using ID param and multiple items, where first and third are invalid ids - expect error" { - $null = Get-TimeZone -Id @("Cape Verde Standard","Morocco Standard Time","Azores Standard") ` - -ErrorVariable errVar -ErrorAction SilentlyContinue - $errVar.Count -eq 2 | Should Be $true - $errVar[0].FullyQualifiedErrorID | Should Be "TimeZoneNotFound,Microsoft.PowerShell.Commands.GetTimeZoneCommand" - } - + $result = Remotely { Get-TimeZone -Id @("Cape Verde Standard","Morocco Standard Time","Azores Standard") } + $result.GetError().FullyQualifiedErrorID | Should Be "TimeZoneNotFound,Microsoft.PowerShell.Commands.GetTimeZoneCommand" + } + It "Call Get-TimeZone using ID param and multiple items, one is wild card but error action ignore works as expected" { - $result = Get-TimeZone -Id @("Cape Verde Standard Time","Morocco Standard Time","*","Azores Standard Time") ` - -ErrorAction SilentlyContinue | % Id + $result = Remotely { (Get-TimeZone -Id @("Cape Verde Standard Time","Morocco Standard Time","*","Azores Standard Time") -ErrorAction SilentlyContinue).Id } $expectedIdList = @("Cape Verde Standard Time","Morocco Standard Time","Azores Standard Time") Assert-ListsSame $expectedIdList $result - } - + } + It "Call Get-TimeZone using Name param and singe item" { - $timezoneList = Get-TimeZone -ListAvailable - $timezoneName = $timezoneList[0].StandardName - $observed = Get-TimeZone -Name $timezoneName - $observed.StandardName -eq $timezoneName | Should Be $true - } + $result = Remotely { + $timezoneList = Get-TimeZone -ListAvailable + $timezoneName = $timezoneList[0].StandardName + $observed = Get-TimeZone -Name $timezoneName + $observed.StandardName -eq $timezoneName + } + $result | Should Be $true + } It "Call Get-TimeZone using Name param with wild card" { - $result = (Get-TimeZone -Name "Pacific*").Id + $result = Remotely { (Get-TimeZone -Name "Pacific*").Id } $expectedIdList = @("Pacific Standard Time (Mexico)","Pacific Standard Time","Pacific SA Standard Time") - Assert-ListsSame $expectedIdList $result - } - + Assert-ListsSame $expectedIdList $result + } + It "Verify that alias 'gtz' exists" { - (Get-Alias -Name "gtz").Name | Should Be "gtz" - } + $result = Remotely { (Get-Alias -Name "gtz").Name } + $result | Should Be "gtz" + } It "Call Get-TimeZone Name parameter from pipeline by value " { - $result = ("Pacific*" | Get-TimeZone).Id + $result = Remotely { ("Pacific*" | Get-TimeZone).Id } $expectedIdList = @("Pacific Standard Time (Mexico)","Pacific Standard Time","Pacific SA Standard Time") - Assert-ListsSame $expectedIdList $result - } + Assert-ListsSame $expectedIdList $result + } It "Call Get-TimeZone Id parameter from pipeline by ByPropertyName" { - $timezoneList = Get-TimeZone -ListAvailable - $timezone = $timezoneList[0] - $observed = $timezone | Get-TimeZone - $observed.StandardName -eq $timezone.StandardName | Should Be $true + $result = Remotely { + $timezoneList = Get-TimeZone -ListAvailable + $timezone = $timezoneList[0] + $observed = $timezone | Get-TimeZone + $observed.StandardName -eq $timezone.StandardName + } + $result | Should Be $true } } -Describe "Set-Timezone test case: call by single Id" -Tags "CI" { +Describe "Set-Timezone test case: call by single Id" -tags 'BVT' { $originalTimeZoneId BeforeAll { - $originalTimeZoneId = (Get-TimeZone).Id + $originalTimeZoneId = Remotely { (Get-TimeZone).Id } } AfterAll { - Set-TimeZone -ID $originalTimeZoneId + Remotely { param($tz) Set-TimeZone -ID $tz } -ArgumentList $originalTimeZoneId } It "Call Set-TimeZone by Id" { - $origTimeZoneID = (Get-TimeZone).Id - $timezoneList = Get-TimeZone -ListAvailable - $testTimezone = $null - foreach($timezone in $timezoneList) - { - if ($timezone.Id -ne $origTimeZoneID) + $result = Remotely { + $origTimeZoneID = (Get-TimeZone).Id + $timezoneList = Get-TimeZone -ListAvailable + $testTimezone = $null + foreach($timezone in $timezoneList) { - $testTimezone = $timezone - break + if ($timezone.Id -ne $origTimeZoneID) + { + $testTimezone = $timezone + break + } } + Set-TimeZone -Id $testTimezone.Id + $observed = Get-TimeZone + $testTimezone.Id -eq $observed.Id } - Set-TimeZone -Id $testTimezone.Id - $observed = Get-TimeZone - $testTimezone.Id -eq $observed.Id | Should Be $true + $result| Should Be $true } } -Describe "Set-Timezone test cases" -Tags "Feature" { +Describe "Set-Timezone test cases" -tags 'Innerloop','RI' { $originalTimeZoneId BeforeAll { - $originalTimeZoneId = (Get-TimeZone).Id + $originalTimeZoneId = Remotely { (Get-TimeZone).Id } } AfterAll { - Set-TimeZone -ID $originalTimeZoneId + Remotely { param($tz) Set-TimeZone -ID $tz } -ArgumentList $originalTimeZoneId } + + It "Call Set-TimeZone with invalid Id" { - $exception = $null - try { Set-TimeZone -Id "zzInvalidID" } catch { $exception = $_ } - $exception.FullyQualifiedErrorID | Should Be "TimeZoneNotFound,Microsoft.PowerShell.Commands.SetTimeZoneCommand" + $result = Remotely { Set-TimeZone -Id "zzInvalidID" } + $result.GetError().FullyQualifiedErrorID | Should Be "TimeZoneNotFound,Microsoft.PowerShell.Commands.SetTimeZoneCommand" } It "Call Set-TimeZone by Name" { - $origTimeZoneName = (Get-TimeZone).StandardName - $timezoneList = Get-TimeZone -ListAvailable - $testTimezone = $null - foreach($timezone in $timezoneList) - { - if ($timezone.StandardName -ne $origTimeZoneName) + $result = Remotely { + $origTimeZoneName = (Get-TimeZone).StandardName + $timezoneList = Get-TimeZone -ListAvailable + $testTimezone = $null + foreach($timezone in $timezoneList) { - $testTimezone = $timezone - break + if ($timezone.StandardName -ne $origTimeZoneName) + { + $testTimezone = $timezone + break + } } + + Set-TimeZone -Name $testTimezone.StandardName + $observed = Get-TimeZone + $testTimezone.StandardName -eq $observed.StandardName } - Set-TimeZone -Name $testTimezone.StandardName - $observed = Get-TimeZone - $testTimezone.StandardName -eq $observed.StandardName | Should Be $true + $result | Should Be $true } - It "Call Set-TimeZone with invalid Name" { - $exception = $null - try { Set-TimeZone -Name "zzINVALID_Name" } catch { $exception = $_ } - $exception.FullyQualifiedErrorID | Should Be "TimeZoneNotFound,Microsoft.PowerShell.Commands.SetTimeZoneCommand" + It "Call Set-TimeZone with invalid Name" { + $result = Remotely { Set-TimeZone -Name "zzINVALID_Name" } + $result.GetError().FullyQualifiedErrorID | Should Be "TimeZoneNotFound,Microsoft.PowerShell.Commands.SetTimeZoneCommand" } It "Verify that alias 'stz' exists" { - (Get-Alias -Name "stz").Name | Should Be "stz" + $result = Remotely { (Get-Alias -Name "stz").Name } + $result | Should Be "stz" } It "Call Set-TimeZone from pipeline input object of type TimeZoneInfo" { - $origTimeZoneID = (Get-TimeZone).Id - $timezoneList = Get-TimeZone -ListAvailable - $testTimezone = $null - foreach($timezone in $timezoneList) - { - if ($timezone.Id -ne $origTimeZoneID) + $result = Remotely { + $origTimeZoneID = (Get-TimeZone).Id + $timezoneList = Get-TimeZone -ListAvailable + $testTimezone = $null + foreach($timezone in $timezoneList) { - $testTimezone = $timezone - break + if ($timezone.Id -ne $origTimeZoneID) + { + $testTimezone = $timezone + break + } } + + $testTimezone | Set-TimeZone + $observed = Get-TimeZone + $observed.ID -eq $testTimezone.Id } - - $testTimezone | Set-TimeZone - $observed = Get-TimeZone - $observed.ID -eq $testTimezone.Id | Should Be $true + $result | Should Be $true } It "Call Set-TimeZone from pipeline input object of type TimeZoneInfo, verify supports whatif" { - $origTimeZoneID = (Get-TimeZone).Id - $timezoneList = Get-TimeZone -ListAvailable - $testTimezone = $null - foreach($timezone in $timezoneList) - { - if ($timezone.Id -ne $origTimeZoneID) + $result = Remotely { + $origTimeZoneID = (Get-TimeZone).Id + $timezoneList = Get-TimeZone -ListAvailable + $testTimezone = $null + foreach($timezone in $timezoneList) { - $testTimezone = $timezone - break + if ($timezone.Id -ne $origTimeZoneID) + { + $testTimezone = $timezone + break + } } + + Set-TimeZone -Id $testTimezone.Id -WhatIf > $null + $observed = Get-TimeZone + $observed.Id -eq $origTimeZoneID } - - Set-TimeZone -Id $testTimezone.Id -WhatIf > $null - $observed = Get-TimeZone - $observed.Id -eq $origTimeZoneID | Should Be $true + $result.GetError() | Should BeNullOrEmpty + $result | Should Be $true } } - -} diff --git a/test/powershell/Modules/Microsoft.PowerShell.Security/FileCatalog.Tests.ps1 b/test/powershell/Modules/Microsoft.PowerShell.Security/FileCatalog.Tests.ps1 index 3cba2d422..dff064138 100644 --- a/test/powershell/Modules/Microsoft.PowerShell.Security/FileCatalog.Tests.ps1 +++ b/test/powershell/Modules/Microsoft.PowerShell.Security/FileCatalog.Tests.ps1 @@ -3,15 +3,14 @@ # Copyright (c) Microsoft Corporation, 2016 # -if ($IsWindows) { - $script:catalogPath = "" -Describe "Test suite for NewFileCatalogAndTestFileCatalogCmdlets" -Tags "CI" { +Describe "Test suite for NewFileCatalogAndTestFileCatalogCmdlets" -Tags "Innerloop","BVT" { - #compare two hashtables - function CompareHashTables - { + +#compare two hashtables +function CompareHashTables +{ param ( $hashTable1, @@ -20,362 +19,513 @@ Describe "Test suite for NewFileCatalogAndTestFileCatalogCmdlets" -Tags "CI" { foreach ($key in $hashTable1.keys) { + $keyValue1 = $hashTable1["$key"] if($hashTable2.ContainsKey($key)) { - $keyValue2 = $hashTable2["$key"] - $keyValue1 | Should Be $keyValue2 + $keyValue2 = $hashTable2["$key"] + $keyValue1 | Should Be $keyValue2 + } else { throw "Failed to find the file $keyValue1 for $key in Hashtable" } - } - } - - BeforeAll { - $testDataPath = "$PSScriptRoot\TestData\CatalogTestData" - } - - Context "NewAndTestCatalogTests PositiveTestCases when validation Succeeds" { - - It "NewFileCatalogFolder" { - - $sourcePath = Join-Path $testDataPath 'UserConfigProv\DSCResources\scriptdsc' - $catalogPath = "$testDataPath\NewFileCatalogFolder.cat" - - try - { - $null = New-FileCatalog -Path $sourcePath -CatalogFilePath $catalogPath -CatalogVersion 1.0 - $result = Test-FileCatalog -Path $sourcePath -CatalogFilePath $catalogPath -Detailed - } - finally - { - Remove-Item $catalogPath -Force -ErrorAction SilentlyContinue - } - - # Validate result properties - $result.Status | Should Be "Valid" - $result.Signature.Status | Should Be "NotSigned" - $result.HashAlgorithm | Should Be "SHA1" } - It "NewFileCatalogFolderWithSubFolders" { - - $sourcePath = Join-Path $testDataPath 'UserConfigProv' - # use non existant Path for the directory when .cat file name is specified - $catalogPath = "$testDataPath\OutPutCatalog\NewFileCatalogFolderWithSubFolders.cat" - - try +} + + BeforeAll { + + $testCaseFolderPath = ".\Security_TestData\CatalogTestData" + + # Copy the test files to the remote target + $remoteSystemDrive = Remotely { $env:SystemDrive } + $remoteSystemDrive | Should Not Be $null + + $remoteTestDirectory = "$remoteSystemDrive\MultiMachineTestData\Commands\" + + Remotely { + param ($path) + if (-not (Test-Path $path)) { - $null = New-FileCatalog -Path $sourcePath -CatalogFilePath $catalogPath - $result = Test-FileCatalog -Path $sourcePath -CatalogFilePath $catalogPath -Detailed - } - finally - { - Remove-Item "$sourcePath\OutPutCatalog" -Force -ErrorAction SilentlyContinue -Recurse + New-Item -Path $path -ItemType Directory -Force | Out-Null } + } -ArgumentList $remoteTestDirectory | Out-Null + + $sessions = @(Get-RemoteSession) + ($sessions.Count -eq 1) | Should be true + + foreach ($session in $sessions) + { + Copy-Item -Path $testCaseFolderPath -Destination $remoteTestDirectory -Force -Recurse -ToSession $session -Verbose + } + + $exists = Remotely { + param ($path) + Test-Path -Path $path + } -ArgumentList $remoteTestDirectory + $exists | Should be $true + + $remoteTestSubDirectory = "$remoteTestDirectory\CatalogTestData" + } + + + Context "NewAndTestCatalogTests PositiveTestCases when validation Succeeds" { + + It "NewFileCatalogFolder" { + $result = Remotely { + + param ($testDataPath) + + $sourcePath = Join-Path $testDataPath 'UserConfigProv\DSCResources\scriptdsc' + $catalogPath = "$testDataPath\NewFileCatalogFolder.cat" + + try + { + $null = New-FileCatalog -Path $sourcePath -CatalogFilePath $catalogPath -CatalogVersion 1.0 + Test-FileCatalog -Path $sourcePath -CatalogFilePath $catalogPath -Detailed + } + finally + { + Remove-Item $catalogPath -Force -ErrorAction SilentlyContinue + } + } -ArgumentList $remoteTestSubDirectory + # Validate result properties - $result.Status | Should Be "Valid" - $result.Signature.Status | Should Be "NotSigned" + $result.Status | Should Be "Valid" + $result.Signature.Status.Value | Should Be "NotSigned" $result.HashAlgorithm | Should Be "SHA1" + } + + It "NewFileCatalogFolderWithSubFolders" { + + $result = Remotely { + + param ($testDataPath) + + $sourcePath = Join-Path $testDataPath 'UserConfigProv' + # use non existant Path for the directory when .cat file name is specified + $catalogPath = "$testDataPath\OutPutCatalog\NewFileCatalogFolderWithSubFolders.cat" + + try + { + + $null = New-FileCatalog -Path $sourcePath -CatalogFilePath $catalogPath + Test-FileCatalog -Path $sourcePath -CatalogFilePath $catalogPath -Detailed + } + finally + { + Remove-Item "$sourcePath\OutPutCatalog" -Force -ErrorAction SilentlyContinue -Recurse + } + } -ArgumentList $remoteTestSubDirectory + + # Validate result properties + $result.Status | Should Be "Valid" + $result.Signature.Status.Value | Should Be "NotSigned" + $result.HashAlgorithm | Should Be "SHA1" } - It "NewFileCatalogWithSingleFile" { - - $sourcePath = Join-Path $testDataPath '\CatalogTestFile1.mof' - # use existant Path for the directory when .cat file name is not specified - $catalogPath = $testDataPath - try - { - $null = New-FileCatalog -Path $sourcePath -CatalogFilePath $catalogPath - $result = Test-FileCatalog -Path $sourcePath -CatalogFilePath ($catalogPath + "\catalog.cat") - } - finally - { - Remove-Item "$catalogPath\catalog.cat" -Force -ErrorAction SilentlyContinue - } - - # Validate result properties - $result | Should Be "Valid" - } + It "NewFileCatalogWithSingleFile" { + + $result = Remotely { - It "NewFileCatalogForFilesThatDoNotSupportEmbeddedSignatures" { + param ($testDataPath) + + $sourcePath = Join-Path $testDataPath '\CatalogTestFile1.mof' + + # use existant Path for the directory when .cat file name is not specified + $catalogPath = $testDataPath + try + { + $null = New-FileCatalog -Path $sourcePath -CatalogFilePath $catalogPath + Test-FileCatalog -Path $sourcePath -CatalogFilePath ($catalogPath + "\catalog.cat") + } + finally + { + Remove-Item "$catalogPath\catalog.cat" -Force -ErrorAction SilentlyContinue + } + } -ArgumentList $remoteTestSubDirectory + + # Validate result properties + $result.Value | Should Be "Valid" + } + + It "NewFileCatalogForFilesThatDoNotSupportEmbeddedSignatures" { $expectedPathsAndHashes = @{ "TestImage.gif" = "B0E4B9F0BB21284AA0AF0D525C913420AD73DA6A" ; "TestFileCatalog.txt" = "925834D22A8AEB8E0A5EAFABC739F8AFAAD3E490" } - - # use non existant Path for the directory when .cat file name is not specified - $catalogPath = "$testDataPath\OutPutCatalog" + $result = Remotely { - try - { - $null = New-FileCatalog -Path "$testDataPath\TestImage.gif","$testDataPath\TestFileCatalog.txt" -CatalogFilePath $catalogPath -CatalogVersion 1.0 - $result = Test-FileCatalog -Path "$testDataPath\TestImage.gif","$testDataPath\TestFileCatalog.txt" -CatalogFilePath ($catalogPath + "\catalog.cat") -Detailed - } - finally - { - Remove-Item "$catalogPath" -Force -ErrorAction SilentlyContinue -Recurse - } - + param ($testDataPath) + + # use non existant Path for the directory when .cat file name is not specified + $catalogPath = "$testDataPath\OutPutCatalog" + + try + { + $null = New-FileCatalog -Path "$testDataPath\TestImage.gif","$testDataPath\TestFileCatalog.txt" -CatalogFilePath $catalogPath -CatalogVersion 1.0 + Test-FileCatalog -Path "$testDataPath\TestImage.gif","$testDataPath\TestFileCatalog.txt" -CatalogFilePath ($catalogPath + "\catalog.cat") -Detailed + } + finally + { + Remove-Item "$catalogPath" -Force -ErrorAction SilentlyContinue -Recurse + } + } -ArgumentList $remoteTestSubDirectory + $result.Status | Should Be "Valid" $result.CatalogItems.Count | Should Be 2 $result.PathItems.Count | Should Be 2 CompareHashTables $result.CatalogItems $result.PathItems CompareHashTables $result.CatalogItems $expectedPathsAndHashes - } + } - It "NewFileCatalogWithMutipleFoldersAndFiles" -Skip:$true { + It "NewFileCatalogWithMutipleFoldersAndFiles" { - $expectedPathsAndHashes = @{ - "UserConfigProv.psd1" = "748E5486814051DA3DFB79FE8964152727213248" ; - "DSCResources\UserConfigProviderModVersion1\UserConfigProviderModVersion1.schema.mof" ="F7CAB050E32CF0C9B2AC2807C4F24D31EFCC8B61"; - "dscresources\UserConfigProviderModVersion3\UserConfigProviderModVersion3.psm1" = "F9DD6B02C7BD0FB98A25BE0D41210B2A2333E139"; - "DSCResources\scriptdsc\scriptDSC.schema.psm1"= "CDBAF85FEDE2E0CD09B1AEA0532010CEFCECBC12"; - "DSCResources\UserConfigProviderModVersion1\UserConfigProviderModVersion1.psm1" = "7599777B85B60377B1F3E492C817190090A754A7" - "DSCResources\scriptdsc\scriptdsc.psd1"= "CDDC68AF9B863760A14031772DC9ADDAFD209D80"; - "DSCResources\UserConfigProviderModVersion3\UserConfigProviderModVersion3.schema.mof" ="AFEB46104F506FC64CAB4B0B2A9C6C50622B487A"; - "DSCResources\UserConfigProviderModVersion2\UserConfigProviderModVersion2.psm1"= "60CB9C8AEDA7A64127D34361ED4F30DEAFE37022"; - "DSCResources\UserConfigProviderModVersion2\UserConfigProviderModVersion2.schema.mof" = "E33FBFEA28E9A8FBA793FBC3D8015BCC9A10944B"; - "CatalogTestFile1.mof" = "083B0953D0D70FFF62710F0356FEB86BCE327FE7"; - "CatalogTestFile2.xml" = "E73BB7A0DD9FAC6A8182F67B750D9CA3094490F1" } + $expectedPathsAndHashes = @{ "UserConfigProv.psd1" = "748E5486814051DA3DFB79FE8964152727213248" ; + "DSCResources\UserConfigProviderModVersion1\UserConfigProviderModVersion1.schema.mof" ="F7CAB050E32CF0C9B2AC2807C4F24D31EFCC8B61"; + "dscresources\UserConfigProviderModVersion3\UserConfigProviderModVersion3.psm1" = "F9DD6B02C7BD0FB98A25BE0D41210B2A2333E139"; + "DSCResources\scriptdsc\scriptDSC.schema.psm1"= "CDBAF85FEDE2E0CD09B1AEA0532010CEFCECBC12"; + "DSCResources\UserConfigProviderModVersion1\UserConfigProviderModVersion1.psm1" = "7599777B85B60377B1F3E492C817190090A754A7" + "DSCResources\scriptdsc\scriptdsc.psd1"= "CDDC68AF9B863760A14031772DC9ADDAFD209D80"; + "DSCResources\UserConfigProviderModVersion3\UserConfigProviderModVersion3.schema.mof" ="AFEB46104F506FC64CAB4B0B2A9C6C50622B487A"; + "DSCResources\UserConfigProviderModVersion2\UserConfigProviderModVersion2.psm1"= "60CB9C8AEDA7A64127D34361ED4F30DEAFE37022"; + "DSCResources\UserConfigProviderModVersion2\UserConfigProviderModVersion2.schema.mof" = "E33FBFEA28E9A8FBA793FBC3D8015BCC9A10944B"; + "CatalogTestFile1.mof" = "083B0953D0D70FFF62710F0356FEB86BCE327FE7"; + "CatalogTestFile2.xml" = "E73BB7A0DD9FAC6A8182F67B750D9CA3094490F1" } + + $result = Remotely { + + param ($testDataPath) + + $catalogPath = "$env:TEMP\NewFileCatalogWithMutipleFoldersAndFiles.cat" + $catalogDataPath = @("$testDataPath\UserConfigProv\","$testDataPath\CatalogTestFile1.mof","$testDataPath\CatalogTestFile2.xml") + + try + { + $null =New-FileCatalog -Path $catalogDataPath -CatalogFilePath $catalogPath -CatalogVersion 1.0 + Test-FileCatalog -Path $catalogDataPath -CatalogFilePath $catalogPath -Detailed + } + finally + { + Remove-Item "$catalogPath" -Force -ErrorAction SilentlyContinue + } + } -ArgumentList $remoteTestSubDirectory - $catalogPath = "$env:TEMP\NewFileCatalogWithMutipleFoldersAndFiles.cat" - $catalogDataPath = @("$testDataPath\UserConfigProv\","$testDataPath\CatalogTestFile1.mof","$testDataPath\CatalogTestFile2.xml") - - try - { - $null =New-FileCatalog -Path $catalogDataPath -CatalogFilePath $catalogPath -CatalogVersion 1.0 - $result = Test-FileCatalog -Path $catalogDataPath -CatalogFilePath $catalogPath -Detailed - } - finally - { - Remove-Item "$catalogPath" -Force -ErrorAction SilentlyContinue - } - - $result.Status | Should Be "Valid" - $result.Signature.Status | Should Be "NotSigned" - $result.HashAlgorithm | Should Be "SHA1" - $result.CatalogItems.Count | Should Be 11 - $result.PathItems.Count | Should Be 11 + $result.Status | Should Be "Valid" + $result.Signature.Status.Value | Should Be "NotSigned" + $result.HashAlgorithm | Should Be "SHA1" + $result.CatalogItems.Count | Should Be 11 + $result.PathItems.Count | Should Be 11 CompareHashTables $result.CatalogItems $result.PathItems - CompareHashTables $result.CatalogItems $expectedPathsAndHashes + CompareHashTables $result.CatalogItems $expectedPathsAndHashes + } + + It "NewFileCatalogVersion2WithMutipleFoldersAndFiles" { + + $expectedPathsAndHashes = @{ "UserConfigProv.psd1" = "9FFE4CA2873CD91CDC9D71362526446ECACDA64D26DEA768E6CE489B84D888E4" ; + "DSCResources\UserConfigProviderModVersion1\UserConfigProviderModVersion1.schema.mof" ="517F625CB6C465928586F5C613F768B33C20F477DAF843C179071B8C74B992AA"; + "DSCResources\UserConfigProviderModVersion3\UserConfigProviderModVersion3.psm1" = "0774A539E73B1A480E38CFFE2CF0B8AC46120A0B2E0377E0DE2630031BE83347"; + "DSCResources\scriptdsc\scriptdsc.schema.psm1"= "7DE80DED0F96FA7D34CF34089A1B088E91CD7B1D80251949FC7C78A6308D51C3"; + "DSCResources\UserConfigProviderModVersion1\UserConfigProviderModVersion1.psm1" = "EB0310C630EDFDFBDD1D993A636EC9B75BB1F04DF7E7FFE39CF6357679C852C7" + "DSCResources\scriptdsc\scriptdsc.psd1"= "AB8E8D0840D4854CDCDE25058872413AF417FC016BD77FD5EC677BBB7393532B"; + "DSCResources\UserConfigProviderModVersion3\UserConfigProviderModVersion3.schema.mof" ="7163E607F067A3C4F91D3AFF3C466ECA47C0CF84B5F0DDA22B2C0E99929B5E21"; + "DSCResources\UserConfigProviderModVersion2\UserConfigProviderModVersion2.psm1"= "6591FE02528D7FB66F00E09D7F1A025D5D5BAF30A49C5FF1EC562FAE39B38F43"; + "DSCResources\UserConfigProviderModVersion2\UserConfigProviderModVersion2.schema.mof" = "679318201B012CC5936B29C095956B2131FAF828C0CCA4342A5914F721480FB9"; + "CatalogTestFile1.mof" = "7C1885AE5F76F58DAA232A5E962875F90308C3CB8580400EE12F999B4E10F940"; + "CatalogTestFile2.xml" = "00B7DA28CD285F796660D36B77B2EC6054F21A44D5B329EB6BC4EC7687D70B13"; + "TestImage.gif" = "2D938D255D0D6D547747BD21447CF7295318D34D9B4105D04C1C27487D2FF402" } + + $result = Remotely { + + param ($testDataPath) + + $catalogPath = "$env:TEMP\NewFileCatalogVersion2WithMutipleFoldersAndFiles.cat" + $catalogDataPath = @("$testDataPath\UserConfigProv\","$testDataPath\CatalogTestFile1.mof","$testDataPath\CatalogTestFile2.xml", "$testDataPath\TestImage.gif") + + try + { + $null = New-FileCatalog -Path $catalogDataPath -CatalogFilePath $catalogPath -CatalogVersion 2.0 + Test-FileCatalog -Path $catalogDataPath -CatalogFilePath $catalogPath -Detailed + } + finally + { + Remove-Item "$catalogPath" -Force -ErrorAction SilentlyContinue + } + } -ArgumentList $remoteTestSubDirectory + + $result.Status | Should Be "Valid" + $result.Signature.Status.Value | Should Be "NotSigned" + $result.HashAlgorithm | Should Be "SHA256" + $result.CatalogItems.Count | Should Be 12 + $result.PathItems.Count | Should Be 12 + CompareHashTables $result.CatalogItems $result.PathItems + CompareHashTables $result.CatalogItems $expectedPathsAndHashes } - It "NewFileCatalogVersion2WithMutipleFoldersAndFiles" -Skip:$true { + It "NewFileCatalogFolderWhenCatlogFileIsCreatedInsideSameFolder" { - $expectedPathsAndHashes = @{ - "UserConfigProv.psd1" = "9FFE4CA2873CD91CDC9D71362526446ECACDA64D26DEA768E6CE489B84D888E4" ; - "DSCResources\UserConfigProviderModVersion1\UserConfigProviderModVersion1.schema.mof" ="517F625CB6C465928586F5C613F768B33C20F477DAF843C179071B8C74B992AA"; - "DSCResources\UserConfigProviderModVersion3\UserConfigProviderModVersion3.psm1" = "0774A539E73B1A480E38CFFE2CF0B8AC46120A0B2E0377E0DE2630031BE83347"; - "DSCResources\scriptdsc\scriptdsc.schema.psm1"= "7DE80DED0F96FA7D34CF34089A1B088E91CD7B1D80251949FC7C78A6308D51C3"; - "DSCResources\UserConfigProviderModVersion1\UserConfigProviderModVersion1.psm1" = "EB0310C630EDFDFBDD1D993A636EC9B75BB1F04DF7E7FFE39CF6357679C852C7" - "DSCResources\scriptdsc\scriptdsc.psd1"= "AB8E8D0840D4854CDCDE25058872413AF417FC016BD77FD5EC677BBB7393532B"; - "DSCResources\UserConfigProviderModVersion3\UserConfigProviderModVersion3.schema.mof" ="7163E607F067A3C4F91D3AFF3C466ECA47C0CF84B5F0DDA22B2C0E99929B5E21"; - "DSCResources\UserConfigProviderModVersion2\UserConfigProviderModVersion2.psm1"= "6591FE02528D7FB66F00E09D7F1A025D5D5BAF30A49C5FF1EC562FAE39B38F43"; - "DSCResources\UserConfigProviderModVersion2\UserConfigProviderModVersion2.schema.mof" = "679318201B012CC5936B29C095956B2131FAF828C0CCA4342A5914F721480FB9"; - "CatalogTestFile1.mof" = "7C1885AE5F76F58DAA232A5E962875F90308C3CB8580400EE12F999B4E10F940"; - "CatalogTestFile2.xml" = "00B7DA28CD285F796660D36B77B2EC6054F21A44D5B329EB6BC4EC7687D70B13"; - "TestImage.gif" = "2D938D255D0D6D547747BD21447CF7295318D34D9B4105D04C1C27487D2FF402" } + + $result = Remotely { - - $catalogPath = "$env:TEMP\NewFileCatalogVersion2WithMutipleFoldersAndFiles.cat" - $catalogDataPath = @("$testDataPath\UserConfigProv\","$testDataPath\CatalogTestFile1.mof","$testDataPath\CatalogTestFile2.xml", "$testDataPath\TestImage.gif") + param ($testDataPath) - try - { - $null = New-FileCatalog -Path $catalogDataPath -CatalogFilePath $catalogPath -CatalogVersion 2.0 - $result = Test-FileCatalog -Path $catalogDataPath -CatalogFilePath $catalogPath -Detailed - } - finally - { - Remove-Item "$catalogPath" -Force -ErrorAction SilentlyContinue - } - - $result.Status | Should Be "Valid" - $result.Signature.Status | Should Be "NotSigned" - $result.HashAlgorithm | Should Be "SHA256" - $result.CatalogItems.Count | Should Be 12 - $result.PathItems.Count | Should Be 12 - CompareHashTables $result.CatalogItems $result.PathItems - CompareHashTables $result.CatalogItems $expectedPathsAndHashes + $catalogPath = "$env:TEMP\UserConfigProv\NewFileCatalogFolderWhenCatlogFileIsCreatedInsideSameFolder.cat" + try + { + copy-item $testDataPath\UserConfigProv $env:temp -Recurse -ErrorAction SilentlyContinue + $null = New-FileCatalog -Path $env:temp\UserConfigProv\ -CatalogFilePath $catalogPath -CatalogVersion 1.0 + Test-FileCatalog -Path $env:temp\UserConfigProv\ -CatalogFilePath $catalogPath + } + finally + { + Remove-Item "$catalogPath" -Force -ErrorAction SilentlyContinue + Remove-Item "$env:temp\UserConfigProv\" -Force -ErrorAction SilentlyContinue -Recurse + } + } -ArgumentList $remoteTestSubDirectory + + $result.Value | Should Be "Valid" } - It "NewFileCatalogFolderWhenCatlogFileIsCreatedInsideSameFolder" { - - $catalogPath = "$env:TEMP\UserConfigProv\NewFileCatalogFolderWhenCatlogFileIsCreatedInsideSameFolder.cat" - try - { - copy-item $testDataPath\UserConfigProv $env:temp -Recurse -ErrorAction SilentlyContinue - $null = New-FileCatalog -Path $env:temp\UserConfigProv\ -CatalogFilePath $catalogPath -CatalogVersion 1.0 - $result = Test-FileCatalog -Path $env:temp\UserConfigProv\ -CatalogFilePath $catalogPath - } - finally - { - Remove-Item "$catalogPath" -Force -ErrorAction SilentlyContinue - Remove-Item "$env:temp\UserConfigProv\" -Force -ErrorAction SilentlyContinue -Recurse - } + It "NewFileCatalogWithUnicodeCharactersInFileNames" { + + $expectedPathsAndHashes = @{ "UserConfigProv.psd1" = "9FFE4CA2873CD91CDC9D71362526446ECACDA64D26DEA768E6CE489B84D888E4" ; + "DSCResources\UserConfigProviderModVersion1\UserConfigProviderModVersion1.schema.mof" ="517F625CB6C465928586F5C613F768B33C20F477DAF843C179071B8C74B992AA"; + "DSCResources\UserConfigProviderModVersion3\UserConfigProviderModVersion3.psm1" = "0774A539E73B1A480E38CFFE2CF0B8AC46120A0B2E0377E0DE2630031BE83347"; + "DSCResources\scriptdsc\scriptdsc.schema.psm1"= "7DE80DED0F96FA7D34CF34089A1B088E91CD7B1D80251949FC7C78A6308D51C3"; + "DSCResources\UserConfigProviderModVersion1\UserConfigProviderModVersion1.psm1" = "EB0310C630EDFDFBDD1D993A636EC9B75BB1F04DF7E7FFE39CF6357679C852C7" + "DSCResources\scriptdsc\scriptdsc.psd1"= "AB8E8D0840D4854CDCDE25058872413AF417FC016BD77FD5EC677BBB7393532B"; + "DSCResources\UserConfigProviderModVersion3\UserConfigProviderModVersion3.schema.mof" ="7163E607F067A3C4F91D3AFF3C466ECA47C0CF84B5F0DDA22B2C0E99929B5E21"; + "DSCResources\UserConfigProviderModVersion2\UserConfigProviderModVersion2.psm1"= "6591FE02528D7FB66F00E09D7F1A025D5D5BAF30A49C5FF1EC562FAE39B38F43"; + "DSCResources\UserConfigProviderModVersion2\UserConfigProviderModVersion2.schema.mof" = "679318201B012CC5936B29C095956B2131FAF828C0CCA4342A5914F721480FB9"; + "ٿ ڀ ځ ڂ ڃ ڄ څ چ ڇ ڈ ډ ڊ ڋ ڌ ڍ ڎ ڏ ڐ ڑ.txt" = "EFD0AE8FF12C7387D51FFC03259B60E06DA012BF7D3B7B9D3480FAB2864846CE"; + "ɥ ɦ ɧ ɨ ɩ ɪ ɫ ɬ.txt" = "9FB57660EDD8DA898A9F1E7F5A36B8B760B4A21625F9968D87A32A55B3546BF9"} - $result | Should Be "Valid" - } + $result = Remotely { - It "NewFileCatalogWithUnicodeCharactersInFileNames" -Skip:$true { - - $expectedPathsAndHashes = @{ - "UserConfigProv.psd1" = "9FFE4CA2873CD91CDC9D71362526446ECACDA64D26DEA768E6CE489B84D888E4" ; - "DSCResources\UserConfigProviderModVersion1\UserConfigProviderModVersion1.schema.mof" ="517F625CB6C465928586F5C613F768B33C20F477DAF843C179071B8C74B992AA"; - "DSCResources\UserConfigProviderModVersion3\UserConfigProviderModVersion3.psm1" = "0774A539E73B1A480E38CFFE2CF0B8AC46120A0B2E0377E0DE2630031BE83347"; - "DSCResources\scriptdsc\scriptdsc.schema.psm1"= "7DE80DED0F96FA7D34CF34089A1B088E91CD7B1D80251949FC7C78A6308D51C3"; - "DSCResources\UserConfigProviderModVersion1\UserConfigProviderModVersion1.psm1" = "EB0310C630EDFDFBDD1D993A636EC9B75BB1F04DF7E7FFE39CF6357679C852C7" - "DSCResources\scriptdsc\scriptdsc.psd1"= "AB8E8D0840D4854CDCDE25058872413AF417FC016BD77FD5EC677BBB7393532B"; - "DSCResources\UserConfigProviderModVersion3\UserConfigProviderModVersion3.schema.mof" ="7163E607F067A3C4F91D3AFF3C466ECA47C0CF84B5F0DDA22B2C0E99929B5E21"; - "DSCResources\UserConfigProviderModVersion2\UserConfigProviderModVersion2.psm1"= "6591FE02528D7FB66F00E09D7F1A025D5D5BAF30A49C5FF1EC562FAE39B38F43"; - "DSCResources\UserConfigProviderModVersion2\UserConfigProviderModVersion2.schema.mof" = "679318201B012CC5936B29C095956B2131FAF828C0CCA4342A5914F721480FB9"; - "ٿ ڀ ځ ڂ ڃ ڄ څ چ ڇ ڈ ډ ڊ ڋ ڌ ڍ ڎ ڏ ڐ ڑ.txt" = "EFD0AE8FF12C7387D51FFC03259B60E06DA012BF7D3B7B9D3480FAB2864846CE"; - "ɥ ɦ ɧ ɨ ɩ ɪ ɫ ɬ.txt" = "9FB57660EDD8DA898A9F1E7F5A36B8B760B4A21625F9968D87A32A55B3546BF9"} - - # Create Test Files with unicode characters in names and content - $unicodeTempDir = Join-Path -Path $testDataPath -ChildPath "UnicodeTestDir" - $null = New-Item -ItemType Directory -Path $unicodeTempDir -Force + param ($testDataPath) - $null = New-Item -ItemType File -Path "$unicodeTempDir\ɥ ɦ ɧ ɨ ɩ ɪ ɫ ɬ.txt" -Force -ErrorAction SilentlyContinue - $null = Add-Content -Path "$unicodeTempDir\ɥ ɦ ɧ ɨ ɩ ɪ ɫ ɬ.txt" -Value "Testing unicode" - $null = Out-File -FilePath "$unicodeTempDir\ɥ ɦ ɧ ɨ ɩ ɪ ɫ ɬ.txt" -Encoding unicode -InputObject "ɗ ɘ ə ɚ ɛ ɜ ɝ ɞ ɟ ɠ ɡ ɢ ɣ ɤ ɥ ɦ ɧ ɨ ɩ ɪ ɫ ɬ ɭ ɮ ɯ ɰ ɱ ɲ ɳ ɴ ɵ ɶ ɷ ɸ ɹ ɺ ɻ ɼ ɽ ɾ ɿ ʀ ʁ ʂ ʃ ʄ ʅ" -Append - $null = New-Item -ItemType File -Path "$unicodeTempDir\ٿ ڀ ځ ڂ ڃ ڄ څ چ ڇ ڈ ډ ڊ ڋ ڌ ڍ ڎ ڏ ڐ ڑ.txt" -Force -ErrorAction SilentlyContinue - $null = Out-File -FilePath "$unicodeTempDir\ٿ ڀ ځ ڂ ڃ ڄ څ چ ڇ ڈ ډ ڊ ڋ ڌ ڍ ڎ ڏ ڐ ڑ.txt" -Encoding unicode -InputObject "ਅ ਆ ਇ ਈ ਉ ਊ ਏ ਐ ਓ ਔ ਕ ਖ ਗ ਘ ਙ ਚ ਛ ਜ ਝ ਞ ਟ ਠ ਡ ਢ ਣ ਤ ਥ ਦ ਧ ਨ ਪ ਫ ਬ ਭ ਮ ਯ ਰ ਲ ਲ਼ ਵ " -Append - $null = Out-File -FilePath "$unicodeTempDir\ٿ ڀ ځ ڂ ڃ ڄ څ چ ڇ ڈ ډ ڊ ڋ ڌ ڍ ڎ ڏ ڐ ڑ.txt" -Encoding unicode -InputObject "அ ஆ இ ஈ உ ஊ எ ஏ ஐ ஒ ஓ ஔ க ங ச ஜ ஞ ட ண த ந ன ப ம ய ர ற ல ள ழ வ ஷ ஸ ஹ " -Append + # Create Test Files with unicode characters in names and content + $null = New-Item -ItemType File -Path "$testDataPath\ɥ ɦ ɧ ɨ ɩ ɪ ɫ ɬ.txt" -Force -ErrorAction SilentlyContinue + $null = Add-Content -Path "$testDataPath\ɥ ɦ ɧ ɨ ɩ ɪ ɫ ɬ.txt" -Value "Testing unicode" + $null = Out-File -FilePath "$testDataPath\ɥ ɦ ɧ ɨ ɩ ɪ ɫ ɬ.txt" -Encoding unicode -InputObject "ɗ ɘ ə ɚ ɛ ɜ ɝ ɞ ɟ ɠ ɡ ɢ ɣ ɤ ɥ ɦ ɧ ɨ ɩ ɪ ɫ ɬ ɭ ɮ ɯ ɰ ɱ ɲ ɳ ɴ ɵ ɶ ɷ ɸ ɹ ɺ ɻ ɼ ɽ ɾ ɿ ʀ ʁ ʂ ʃ ʄ ʅ" -Append + + $null = New-Item -ItemType File -Path "$testDataPath\ٿ ڀ ځ ڂ ڃ ڄ څ چ ڇ ڈ ډ ڊ ڋ ڌ ڍ ڎ ڏ ڐ ڑ.txt" -Force -ErrorAction SilentlyContinue + $null = Out-File -FilePath "$testDataPath\ٿ ڀ ځ ڂ ڃ ڄ څ چ ڇ ڈ ډ ڊ ڋ ڌ ڍ ڎ ڏ ڐ ڑ.txt" -Encoding unicode -InputObject "ਅ ਆ ਇ ਈ ਉ ਊ ਏ ਐ ਓ ਔ ਕ ਖ ਗ ਘ ਙ ਚ ਛ ਜ ਝ ਞ ਟ ਠ ਡ ਢ ਣ ਤ ਥ ਦ ਧ ਨ ਪ ਫ ਬ ਭ ਮ ਯ ਰ ਲ ਲ਼ ਵ " -Append + $null = Out-File -FilePath "$testDataPath\ٿ ڀ ځ ڂ ڃ ڄ څ چ ڇ ڈ ډ ڊ ڋ ڌ ڍ ڎ ڏ ڐ ڑ.txt" -Encoding unicode -InputObject "அ ஆ இ ஈ உ ஊ எ ஏ ஐ ஒ ஓ ஔ க ங ச ஜ ஞ ட ண த ந ன ப ம ய ர ற ல ள ழ வ ஷ ஸ ஹ " -Append - $catalogPath = "$env:TEMP\క ఖ గ ఘ ఙ చ ఛ జ ఝ ఞ.cat" - $catalogDataPath = @("$testDataPath\UserConfigProv\", "$unicodeTempDir\ٿ ڀ ځ ڂ ڃ ڄ څ چ ڇ ڈ ډ ڊ ڋ ڌ ڍ ڎ ڏ ڐ ڑ.txt" ,"$unicodeTempDir\ɥ ɦ ɧ ɨ ɩ ɪ ɫ ɬ.txt") + $catalogPath = "$env:TEMP\క ఖ గ ఘ ఙ చ ఛ జ ఝ ఞ.cat" + $catalogDataPath = @("$testDataPath\UserConfigProv\", "$testDataPath\ٿ ڀ ځ ڂ ڃ ڄ څ چ ڇ ڈ ډ ڊ ڋ ڌ ڍ ڎ ڏ ڐ ڑ.txt" ,"$testDataPath\ɥ ɦ ɧ ɨ ɩ ɪ ɫ ɬ.txt") - try - { - $null = New-FileCatalog -Path $catalogDataPath -CatalogFilePath $catalogPath -CatalogVersion 2.0 - $result = Test-FileCatalog -Path $catalogDataPath -CatalogFilePath $catalogPath -Detailed - } - finally - { - Remove-Item $unicodeTempDir -Recurse -Force -ErrorAction SilentlyContinue - Remove-Item "$catalogPath" -Force -ErrorAction SilentlyContinue - } - - $result.Status | Should Be "Valid" - $result.Signature.Status | Should Be "NotSigned" + try + { + $null = New-FileCatalog -Path $catalogDataPath -CatalogFilePath $catalogPath -CatalogVersion 2.0 + Test-FileCatalog -Path $catalogDataPath -CatalogFilePath $catalogPath -Detailed + + + } + finally + { + Remove-Item "$catalogPath" -Force -ErrorAction SilentlyContinue + } + } -ArgumentList $remoteTestSubDirectory + + $result.Status | Should Be "Valid" + $result.Signature.Status.Value | Should Be "NotSigned" $result.HashAlgorithm | Should Be "SHA256" $result.CatalogItems.Count | Should Be 11 $result.PathItems.Count | Should Be 11 CompareHashTables $result.CatalogItems $result.PathItems CompareHashTables $result.CatalogItems $expectedPathsAndHashes } - } + } Context "NewAndTestCatalogTests NegativeTestCases when creation or validation Fails"{ + AfterEach { - Remove-Item "$script:catalogPath" -Force -ErrorAction SilentlyContinue - Remove-Item "$env:temp\UserConfigProv" -Force -Recurse -ErrorAction SilentlyContinue + + $result = Remotely { + + param ($testDataPath) + + Remove-Item "$script:catalogPath" -Force -ErrorAction SilentlyContinue + Remove-Item "$env:temp\UserConfigProv" -Force -Recurse -ErrorAction SilentlyContinue + + } -ArgumentList $remoteTestSubDirectory } - It "TestCatalogWhenNewFileAddedtoFolderBeforeValidation" { + It "TestCatalogWhenNewFileAddedtoFolderBeforeValidation" { + + $result = Remotely { + + param ($testDataPath) + + $script:catalogPath = "$env:TEMP\TestCatalogWhenNewFileAddedtoFolderBeforeValidation.cat" + $null = New-FileCatalog -Path $testDataPath\UserConfigProv\ -CatalogFilePath $script:catalogPath -CatalogVersion 2.0 + $null = copy-item $testDataPath\UserConfigProv $env:temp -Recurse -ErrorAction SilentlyContinue + $null = New-Item $env:temp\UserConfigProv\DSCResources\NewFile.txt -ItemType File + Add-Content $env:temp\UserConfigProv\DSCResources\NewFile.txt -Value "More Data" -force + Test-FileCatalog -Path $env:temp\UserConfigProv -CatalogFilePath $script:catalogPath -Detailed + + } -ArgumentList $remoteTestSubDirectory + + $result.Status | Should Be "ValidationFailed" + $result.CatalogItems.Count | Should Be 9 + $result.PathItems.Count | Should Be 10 + $result.CatalogItems.ContainsKey("DSCResources\NewFile.txt") | Should Be $false + $result.PathItems.ContainsKey("DSCResources\NewFile.txt") | Should Be $true - $script:catalogPath = "$env:TEMP\TestCatalogWhenNewFileAddedtoFolderBeforeValidation.cat" - $null = New-FileCatalog -Path $testDataPath\UserConfigProv\ -CatalogFilePath $script:catalogPath -CatalogVersion 2.0 - $null = copy-item $testDataPath\UserConfigProv $env:temp -Recurse -ErrorAction SilentlyContinue - $null = New-Item $env:temp\UserConfigProv\DSCResources\NewFile.txt -ItemType File - Add-Content $env:temp\UserConfigProv\DSCResources\NewFile.txt -Value "More Data" -force - $result = Test-FileCatalog -Path $env:temp\UserConfigProv -CatalogFilePath $script:catalogPath -Detailed - - $result.Status | Should Be "ValidationFailed" - $result.CatalogItems.Count | Should Be 9 - $result.PathItems.Count | Should Be 10 - $result.CatalogItems.ContainsKey("DSCResources\NewFile.txt") | Should Be $false - $result.PathItems.ContainsKey("DSCResources\NewFile.txt") | Should Be $true - - # By Skipping the new added file validation will pass - $result = Test-FileCatalog -Path $env:temp\UserConfigProv -CatalogFilePath $script:catalogPath -Detailed -FilesToSkip "NewFile.txt" - $result.Status | Should Be "Valid" + $result = Remotely { + + param ($testDataPath) + + # By Skipping the new added file validation will pass + Test-FileCatalog -Path $env:temp\UserConfigProv -CatalogFilePath $script:catalogPath -Detailed -FilesToSkip "NewFile.txt" + + } -ArgumentList $remoteTestSubDirectory + + $result.Status | Should Be "Valid" } - It "TestCatalogWhenNewFileDeletedFromFolderBeforeValidation" { - - $script:catalogPath = "$env:TEMP\TestCatalogWhenNewFileDeletedFromFolderBeforeValidation.cat" - $null = New-FileCatalog -Path $testDataPath\UserConfigProv\ -CatalogFilePath $script:catalogPath -CatalogVersion 1.0 - $null = copy-item $testDataPath\UserConfigProv $env:temp -Recurse -ErrorAction SilentlyContinue - del $env:temp\UserConfigProv\DSCResources\UserConfigProviderModVersion1\UserConfigProviderModVersion1.psm1 -force -ErrorAction SilentlyContinue - $result = Test-FileCatalog -Path $env:temp\UserConfigProv -CatalogFilePath $script:catalogPath -Detailed + It "TestCatalogWhenNewFileDeletedFromFolderBeforeValidation" { + + $result = Remotely { - $result.Status | Should Be "ValidationFailed" - $result.CatalogItems.Count | Should Be 9 - $result.PathItems.Count | Should Be 8 - $result.CatalogItems.ContainsKey("DSCResources\UserConfigProviderModVersion1\UserConfigProviderModVersion1.psm1") | Should Be $true - $result.PathItems.ContainsKey("DSCResources\UserConfigProviderModVersion1\UserConfigProviderModVersion1.psm1") | Should Be $false - - # By Skipping the deleted file validation will pass - $result = Test-FileCatalog -Path $env:temp\UserConfigProv -CatalogFilePath $script:catalogPath -Detailed -FilesToSkip "UserConfigProviderModVersion1.psm1" - $result.Status | Should Be "Valid" + param ($testDataPath) + + $script:catalogPath = "$env:TEMP\TestCatalogWhenNewFileDeletedFromFolderBeforeValidation.cat" + $null = New-FileCatalog -Path $testDataPath\UserConfigProv\ -CatalogFilePath $script:catalogPath -CatalogVersion 1.0 + $null = copy-item $testDataPath\UserConfigProv $env:temp -Recurse -ErrorAction SilentlyContinue + del $env:temp\UserConfigProv\DSCResources\UserConfigProviderModVersion1\UserConfigProviderModVersion1.psm1 -force -ErrorAction SilentlyContinue + Test-FileCatalog -Path $env:temp\UserConfigProv -CatalogFilePath $script:catalogPath -Detailed + + } -ArgumentList $remoteTestSubDirectory + + $result.Status | Should Be "ValidationFailed" + $result.CatalogItems.Count | Should Be 9 + $result.PathItems.Count | Should Be 8 + $result.CatalogItems.ContainsKey("DSCResources\UserConfigProviderModVersion1\UserConfigProviderModVersion1.psm1") | Should Be $true + $result.PathItems.ContainsKey("DSCResources\UserConfigProviderModVersion1\UserConfigProviderModVersion1.psm1") | Should Be $false + + $result = Remotely { + + param ($testDataPath) + + # By Skipping the deleted file validation will pass + Test-FileCatalog -Path $env:temp\UserConfigProv -CatalogFilePath $script:catalogPath -Detailed -FilesToSkip "UserConfigProviderModVersion1.psm1" + + } -ArgumentList $remoteTestSubDirectory + + $result.Status | Should Be "Valid" } - It "TestCatalogWhenFileContentModifiedBeforeValidation" { - - $script:catalogPath = "$env:TEMP\TestCatalogWhenFileContentModifiedBeforeValidation.cat" - $null = New-FileCatalog -Path $testDataPath\UserConfigProv\ -CatalogFilePath $script:catalogPath -CatalogVersion 1.0 - $null = copy-item $testDataPath\UserConfigProv $env:temp -Recurse -ErrorAction SilentlyContinue - Add-Content $env:temp\UserConfigProv\DSCResources\UserConfigProviderModVersion1\UserConfigProviderModVersion1.psm1 -Value "More Data" -Force - $result = Test-FileCatalog -Path $env:temp\UserConfigProv -CatalogFilePath $script:catalogPath -Detailed - - $result.Status | Should Be "ValidationFailed" - $result.CatalogItems.Count | Should Be 9 + It "TestCatalogWhenFileContentModifiedBeforeValidation" { + + + $result = Remotely { + + param ($testDataPath) + + $script:catalogPath = "$env:TEMP\TestCatalogWhenFileContentModifiedBeforeValidation.cat" + $null = New-FileCatalog -Path $testDataPath\UserConfigProv\ -CatalogFilePath $script:catalogPath -CatalogVersion 1.0 + + $null = copy-item $testDataPath\UserConfigProv $env:temp -Recurse -ErrorAction SilentlyContinue + Add-Content $env:temp\UserConfigProv\DSCResources\UserConfigProviderModVersion1\UserConfigProviderModVersion1.psm1 -Value "More Data" -force + Test-FileCatalog -Path $env:temp\UserConfigProv -CatalogFilePath $script:catalogPath -Detailed + } -ArgumentList $remoteTestSubDirectory + + $result.Status | Should Be "ValidationFailed" + $result.CatalogItems.Count | Should Be 9 $result.PathItems.Count | Should Be 9 $catalogHashValue = $result.CatalogItems["DSCResources\UserConfigProviderModVersion1\UserConfigProviderModVersion1.psm1"] $pathHashValue = $result.PathItems["DSCResources\UserConfigProviderModVersion1\UserConfigProviderModVersion1.psm1"] ($catalogHashValue -eq $pathHashValue) | Should Be $false - # By Skipping the file with modifed contents validation will pass - $result = Test-FileCatalog -Path $env:temp\UserConfigProv -CatalogFilePath $script:catalogPath -Detailed -FilesToSkip "UserConfigProviderModVersion1.psm1" - $result.Status | Should Be "Valid" - } - } + $result = Remotely { - Context "TestCatalog Skip Validation Tests"{ + param ($testDataPath) + + # By Skipping the file with modifed contents validation will pass + Test-FileCatalog -Path $env:temp\UserConfigProv -CatalogFilePath $script:catalogPath -Detailed -FilesToSkip "UserConfigProviderModVersion1.psm1" + + } -ArgumentList $remoteTestSubDirectory + + $result.Status | Should Be "Valid" + } + } + + Context "TestCatalog Skip Validation Tests"{ + AfterEach { - Remove-Item "$script:catalogPath" -Force -ErrorAction SilentlyContinue + + $result = Remotely { + + param ($testDataPath) + + Remove-Item "$script:catalogPath" -Force -ErrorAction SilentlyContinue + + } -ArgumentList $remoteTestSubDirectory } - It "TestCatalogSkipSingleFileDuringValidation" { - - $script:catalogPath = "$env:TEMP\TestCatalogSkipSingleFileDuringValidation.cat" - $null = New-FileCatalog -Path $testDataPath\UserConfigProv\ -CatalogFilePath $script:catalogPath -CatalogVersion 2.0 - $result = Test-FileCatalog -Path $testDataPath\UserConfigProv\ -CatalogFilePath $script:catalogPath -FilesToSkip "scriptdsc.schema" - $result | Should Be "Valid" - } + It "TestCatalogSkipSingleFileDuringValidation" { + + $result = Remotely { - It "TestCatalogSkipCertainFileTypeDuringValidation" { - - $script:catalogPath = "$env:TEMP\TestCatalogSkipCertainFileTypeDuringValidation.cat" - $null = New-FileCatalog -Path $testDataPath\UserConfigProv\ -CatalogFilePath $script:catalogPath -CatalogVersion 2.0 - $result = Test-FileCatalog -Path $testDataPath\UserConfigProv\ -CatalogFilePath $script:catalogPath -FilesToSkip "*.mof" - $result | Should Be "Valid" - } + param ($testDataPath) - It "TestCatalogSkipWildCardPatternDuringValidation" { - - $script:catalogPath = "$env:TEMP\TestCatalogSkipWildCardPatternDuringValidation.cat" - $null = New-FileCatalog -Path $testDataPath\UserConfigProv\ -CatalogFilePath $script:catalogPath -CatalogVersion 1.0 - $result = Test-FileCatalog -Path $testDataPath\UserConfigProv\ -CatalogFilePath $script:catalogPath -FilesToSkip "UserConfigProvider*.psm1" - $result | Should Be "Valid" - } + $script:catalogPath = "$env:TEMP\TestCatalogSkipSingleFileDuringValidation.cat" + $null = New-FileCatalog -Path $testDataPath\UserConfigProv\ -CatalogFilePath $script:catalogPath -CatalogVersion 2.0 + Test-FileCatalog -Path $testDataPath\UserConfigProv\ -CatalogFilePath $script:catalogPath -FilesToSkip "scriptdsc.schema" + + } -ArgumentList $remoteTestSubDirectory - It "TestCatalogSkipMuitplePattensDuringValidation" { - - $script:catalogPath = "$env:TEMP\TestCatalogSkipMuitplePattensDuringValidation.cat" - $null = New-FileCatalog -Path $testDataPath\UserConfigProv\ -CatalogFilePath $script:catalogPath -CatalogVersion 1.0 - $result = Test-FileCatalog -Path $testDataPath\UserConfigProv\ -CatalogFilePath $script:catalogPath -FilesToSkip "*.psd1","UserConfigProviderModVersion2.psm1","*ModVersion1.schema.mof" - $result | Should Be "Valid" - } + $result.Value | Should Be "Valid" + } + + It "TestCatalogSkipCertainFileTypeDuringValidation" { + $result = Remotely { + + param ($testDataPath) + $script:catalogPath = "$env:TEMP\TestCatalogSkipCertainFileTypeDuringValidation.cat" + $null = New-FileCatalog -Path $testDataPath\UserConfigProv\ -CatalogFilePath $script:catalogPath -CatalogVersion 2.0 + Test-FileCatalog -Path $testDataPath\UserConfigProv\ -CatalogFilePath $script:catalogPath -FilesToSkip "*.mof" + + } -ArgumentList $remoteTestSubDirectory + + $result.Value | Should Be "Valid" + } + + It "TestCatalogSkipWildCardPatternDuringValidation" { + + $result = Remotely { + + param ($testDataPath) + + $script:catalogPath = "$env:TEMP\TestCatalogSkipWildCardPatternDuringValidation.cat" + $null = New-FileCatalog -Path $testDataPath\UserConfigProv\ -CatalogFilePath $script:catalogPath -CatalogVersion 1.0 + Test-FileCatalog -Path $testDataPath\UserConfigProv\ -CatalogFilePath $script:catalogPath -FilesToSkip "UserConfigProvider*.psm1" + + } -ArgumentList $remoteTestSubDirectory + + $result.Value | Should Be "Valid" + } + + It "TestCatalogSkipMuitplePattensDuringValidation" { + + $result = Remotely { + + param ($testDataPath) + $script:catalogPath = "$env:TEMP\TestCatalogSkipMuitplePattensDuringValidation.cat" + $null = New-FileCatalog -Path $testDataPath\UserConfigProv\ -CatalogFilePath $script:catalogPath -CatalogVersion 1.0 + Test-FileCatalog -Path $testDataPath\UserConfigProv\ -CatalogFilePath $script:catalogPath -FilesToSkip "*.psd1","UserConfigProviderModVersion2.psm1","*ModVersion1.schema.mof" + + } -ArgumentList $remoteTestSubDirectory + + $result.Value | Should Be "Valid" + } } -} - -} +} \ No newline at end of file diff --git a/test/powershell/Modules/PackageManagement/Find-PackageProvider.Tests.ps1 b/test/powershell/Modules/PackageManagement/Find-PackageProvider.Tests.ps1 index 350420246..80c788a4e 100644 --- a/test/powershell/Modules/PackageManagement/Find-PackageProvider.Tests.ps1 +++ b/test/powershell/Modules/PackageManagement/Find-PackageProvider.Tests.ps1 @@ -12,12 +12,25 @@ # limitations under the License. # # ------------------ PackageManagement Test ----------------------------------- +ipmo "$PSScriptRoot\utility.psm1" $InternalGallery = "https://dtlgalleryint.cloudapp.net/api/v2/" # ------------------------------------------------------------------------------ # Actual Tests: -Describe "find-packageprovider" -Tags "Feature" { +Describe "find-packageprovider" -Tags @('BVT', 'DRT'){ + # make sure that packagemanagement is loaded + import-packagemanagement + + BeforeAll{ + #make sure we are using the latest Nuget provider + install-PackageProvider -name nuget -force + } + AfterAll{ + #make sure we are using the latest Nuget provider + Install-PackageProvider -name nuget -force + } + #make sure the package repository exists $a=Get-PackageSource -force| select Location, ProviderName @@ -34,31 +47,34 @@ Describe "find-packageprovider" -Tags "Feature" { if(-not $found) { -# Commented out because powershellget is not fully working yet -# Register-PackageSource -Name 'OneGetTestSource' -Location $InternalGallery -ProviderName 'PowerShellGet' -ForceBootstrap -ErrorAction SilentlyContinue + Register-PackageSource -Name 'OneGetTestSource' -Location $InternalGallery -ProviderName 'PowerShellGet' -ForceBootstrap -ErrorAction SilentlyContinue } - It "find-packageprovider without any parameters, Expect succeed" -Pending { + It "find-packageprovider without any parameters, Expect succeed" { $a = (Find-PackageProvider -force).name $a -contains "TSDProvider" | should be $true + $a -contains "nuget" | should be $true } - It "find-packageprovider -name, Expect succeed" -Pending { + It "find-packageprovider -name, Expect succeed" { $a = (Find-PackageProvider -name nuget).name $a -contains "GistProvider" | should be $false + $a -contains "nuget" | should be $true } - It "find-packageprovider -name with wildcards, Expect succeed" -Pending { + It "find-packageprovider -name with wildcards, Expect succeed" { $a = (Find-PackageProvider -name gist*).name $a -contains "GistProvider" | should be $true + $a -contains "nuget" | should be $false } - It "find-packageprovider -name with wildcards, Expect succeed" -Pending { + It "find-packageprovider -name with wildcards, Expect succeed" { $a = (Find-PackageProvider -name nu*).name $a -contains "GistProvider" | should be $false + $a -contains "nuget" | should be $true } - It "find-packageprovider -name array, Expect succeed" -Pending { + It "find-packageprovider -name array, Expect succeed" { $names=@("gistprovider", "TSD*") $a = (Find-PackageProvider -name $names).name @@ -66,14 +82,15 @@ Describe "find-packageprovider" -Tags "Feature" { $a -contains "TSDProvider" | should be $true } - It "find-packageprovider -allversions, Expect succeed" -Pending { + It "find-packageprovider -allversions, Expect succeed" { $a = (Find-PackageProvider -allversions) $a.Name -contains "TSDProvider" | should be $true - $a.Count -ge 1 | should be $true + $a.Name -contains "nuget" | should be $true + $a.Count -gt 1 | should be $true } - It "find-packageprovider -name -allversions, Expect succeed" -Pending { + It "find-packageprovider -name -allversions, Expect succeed" { $a = (Find-PackageProvider -name TSDProvider -AllVersions).name $a -contains "TSDProvider" | should be $true @@ -82,7 +99,7 @@ Describe "find-packageprovider" -Tags "Feature" { } - It "EXPECTED: success 'find-packageprovider nuget -allVersions'" -Skip { + It "EXPECTED: success 'find-packageprovider nuget -allVersions'" { $a = find-packageprovider -name nuget -allVersions $a.Count -ge 5| should be $true @@ -90,24 +107,25 @@ Describe "find-packageprovider" -Tags "Feature" { $b.Count -gt $a.Count| should be $true } - It "find-packageprovider -Source, Expect succeed" -Pending { + It "find-packageprovider -Source, Expect succeed" { $a = (Find-PackageProvider -source $InternalGallery).name $a -contains "TSDProvider" | should be $true + $a -contains "nuget" | should be $false } - It "find-packageprovider -Source -Name, Expect succeed" -Pending { + It "find-packageprovider -Source -Name, Expect succeed" { $a = (Find-PackageProvider -name gistprovider -source $InternalGallery).name $a -contains "gistprovider" | should be $true + $a -contains "nuget" | should be $false } - - It "find-packageprovider -Name with dependencies, Expect succeed" -Pending { + It "find-packageprovider -Name with dependencies, Expect succeed" { # gistprovider 1.5 depends on tsdprovider 0.2 $a = (Find-PackageProvider -name gistprovider -RequiredVersion 1.5 -source $InternalGallery -IncludeDependencies) $a.Name -contains "gistprovider" | should be $true $a.Name -contains "tsdprovider" | should be $true } - It "find-install-packageprovider with PowerShell provider, Expect succeed" -Pending { + It "find-install-packageprovider with PowerShell provider, Expect succeed" { $provider= find-packageprovider -name TSDProvider -MinimumVersion 0.1 -MaximumVersion 0.2 -Source $InternalGallery $provider | ?{ $_.Version -eq "0.2" } | should not BeNullOrEmpty @@ -116,7 +134,7 @@ Describe "find-packageprovider" -Tags "Feature" { $a.Version | should match "0.2" } - It "find-install-packageprovider nuget, Expect succeed" -Skip { + It "find-install-packageprovider nuget, Expect succeed" { $provider= find-packageprovider -name nuget -MinimumVersion 2.8.5.1 -MaximumVersion 2.8.5.123 $provider | ?{ $_.Version -eq "2.8.5.122" } | should not BeNullOrEmpty @@ -132,7 +150,18 @@ Describe "find-packageprovider" -Tags "Feature" { } -Describe "Find-Package With FilterOnTag" -Tags "Feature" { +Describe "Find-Package With FilterOnTag" -Tags @('BVT', 'DRT'){ + # make sure that packagemanagement is loaded + import-packagemanagement + + BeforeAll{ + #make sure we are using the latest Nuget provider + install-PackageProvider -name nuget -force + } + AfterAll{ + #make sure we are using the latest Nuget provider + Install-PackageProvider -name nuget -force + } it "EXPECTED: Find a package with FilterOnTag" { @@ -160,7 +189,9 @@ Describe "Find-Package With FilterOnTag" -Tags "Feature" { } } -Describe "Find-PackageProvider with Versions" -Tags "Feature" { +Describe "Find-PackageProvider with Versions" -Tags @('BVT', 'DRT') { + # make sure that packagemanagement is loaded + import-packagemanagement <# Nuget 2.8.5.127 2.8.5.122 @@ -168,86 +199,88 @@ Describe "Find-PackageProvider with Versions" -Tags "Feature" { 2.8.5.101 2.8.5.24#> - It "EXPECTED: success 'Find a provider -requiredVersion 3.5'" -Skip { + It "EXPECTED: success 'Find a provider -requiredVersion 3.5'" { (find-packageprovider -name Nuget -RequiredVersion 2.8.5.122).Version.ToString() | should match "2.8.5.122" } - It "EXPECTED: success 'find a provider with MinimumVersion and MaximumVersion'" -Skip { + It "EXPECTED: success 'find a provider with MinimumVersion and MaximumVersion'" { (find-packageprovider -name nuget -MinimumVersion 2.8.5.105 -MaximumVersion 2.8.5.123).Version.ToString() | should match "2.8.5.122" } - It "EXPECTED: success 'find a provider with MaximumVersion'" -Skip { + It "EXPECTED: success 'find a provider with MaximumVersion'" { (find-packageprovider -name nuget -MaximumVersion 2.8.5.122).Version -contains "2.8.5.122" | should be $true } } -Describe "find-packageprovider Error Cases" -Tags "Feature" { +Describe "find-packageprovider Error Cases" -Tags @('BVT', 'DRT') { + # make sure that packagemanagement is loaded + import-packagemanagement - AfterAll { + AfterAll { $x =Get-PackageSource -Name OneGetTestSource -ErrorAction SilentlyContinue -WarningAction SilentlyContinue if($x) { Unregister-PackageSource -Name OneGetTestSource } - } + } - It "EXPECTED: returns an error when inputing a bad version format" { + It "EXPECTED: returns an error when inputing a bad version format" { $Error.Clear() - find-packageprovider -name Gistprovider -RequiredVersion BOGUSVERSION -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "InvalidVersion,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackageProvider" + $msg = powershell 'find-packageprovider -name Gistprovider -RequiredVersion BOGUSVERSION -warningaction:silentlycontinue -ea silentlycontinue; $ERROR[0].FullyQualifiedErrorId' + $msg | should be "InvalidVersion,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackageProvider" } It "EXPECTED: returns an error when asking for a provider that does not exist" { $Error.Clear() - find-packageprovider -name NOT_EXISTS -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "NoMatchFoundForCriteria,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackageProvider" + $msg = powershell 'find-packageprovider -name NOT_EXISTS -warningaction:silentlycontinue -ea silentlycontinue; $ERROR[0].FullyQualifiedErrorId' + $msg | should be "NoMatchFoundForCriteria,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackageProvider" } It "EXPECTED: returns an error when asking for a provider with RequiredVersoin and MinimumVersion" { $Error.Clear() - find-packageprovider -name NOT_EXISTS -RequiredVersion 1.0 -MinimumVersion 2.0 -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "VersionRangeAndRequiredVersionCannotBeSpecifiedTogether,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackageProvider" + $msg = powershell 'find-packageprovider -name NOT_EXISTS -RequiredVersion 1.0 -MinimumVersion 2.0 -warningaction:silentlycontinue -ea silentlycontinue; $ERROR[0].FullyQualifiedErrorId' + $msg | should be "VersionRangeAndRequiredVersionCannotBeSpecifiedTogether,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackageProvider" } It "EXPECTED: returns an error when asking for a provider with RequiredVersoin and MaximumVersion" { $Error.Clear() - find-packageprovider -name NOT_EXISTS -RequiredVersion 1.0 -MaximumVersion 2.0 -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "VersionRangeAndRequiredVersionCannotBeSpecifiedTogether,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackageProvider" + $msg = powershell 'find-packageprovider -name NOT_EXISTS -RequiredVersion 1.0 -MaximumVersion 2.0 -warningaction:silentlycontinue -ea silentlycontinue;$ERROR[0].FullyQualifiedErrorId' + $msg | should be "VersionRangeAndRequiredVersionCannotBeSpecifiedTogether,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackageProvider" } It "EXPECTED: returns an error when asking for a provider with a MinimumVersion greater than MaximumVersion" { $Error.Clear() - find-packageprovider -name nuget -MaximumVersion 1.0 -MinimumVersion 2.0 -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "NoMatchFoundForCriteria,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackageProvider" + $msg = powershell 'find-packageprovider -name nuget -MaximumVersion 1.0 -MinimumVersion 2.0 -warningaction:silentlycontinue -ea silentlycontinue;$ERROR[0].FullyQualifiedErrorId' + $msg | should be "NoMatchFoundForCriteria,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackageProvider" } It "EXPECTED: returns an error when asking for a provider with MinimumVersion that does not exist" { $Error.Clear() - find-packageprovider -name gistprovider -MinimumVersion 20.2 -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "NoMatchFoundForCriteria,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackageProvider" + $msg = powershell 'find-packageprovider -name gistprovider -MinimumVersion 20.2 -warningaction:silentlycontinue -ea silentlycontinue;$ERROR[0].FullyQualifiedErrorId' + $msg | should be "NoMatchFoundForCriteria,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackageProvider" } It "EXPECTED: returns an error when asking for a provider with MaximumVersion that does not exist" { $Error.Clear() - find-packageprovider -name gistprovider -MaximumVersion 0.1 -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "NoMatchFoundForCriteria,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackageProvider" + $msg = powershell 'find-packageprovider -name gistprovider -MaximumVersion 0.1 -warningaction:silentlycontinue -ea silentlycontinue;$ERROR[0].FullyQualifiedErrorId' + $msg | should be "NoMatchFoundForCriteria,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackageProvider" } It "EXPECTED: returns an error when asking for a provider that has name with wildcard and version" { $Error.Clear() - find-packageprovider -name "AnyName*" -RequiredVersion 4.5 -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "MultipleNamesWithVersionNotAllowed,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackageProvider" + $msg = powershell 'find-packageprovider -name "AnyName*" -RequiredVersion 4.5 -warningaction:silentlycontinue -ea silentlycontinue;$ERROR[0].FullyQualifiedErrorId' + $msg | should be "MultipleNamesWithVersionNotAllowed,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackageProvider" } It "EXPECTED: returns an error when asking for a provider that has name with wildcard and version" { $Error.Clear() - find-packageprovider -name "AnyName" -RequiredVersion 4.5 -allVersions -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "AllVersionsCannotBeUsedWithOtherVersionParameters,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackageProvider" + $msg = powershell 'find-packageprovider -name "AnyName" -RequiredVersion 4.5 -allVersions -warningaction:silentlycontinue -ea silentlycontinue;$ERROR[0].FullyQualifiedErrorId' + $msg | should be "AllVersionsCannotBeUsedWithOtherVersionParameters,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackageProvider" } } diff --git a/test/powershell/Modules/PackageManagement/Get-Package.Tests.ps1 b/test/powershell/Modules/PackageManagement/Get-Package.Tests.ps1 index 7ca20d443..177f0ab63 100644 --- a/test/powershell/Modules/PackageManagement/Get-Package.Tests.ps1 +++ b/test/powershell/Modules/PackageManagement/Get-Package.Tests.ps1 @@ -12,23 +12,32 @@ # limitations under the License. # # ------------------ PackageManagement Test ---------------------------------------------- +ipmo "$PSScriptRoot\utility.psm1" + $nuget = "nuget" $source = "http://www.nuget.org/api/v2/" +$destination = "$env:tmp\GetPackageTests" + +# Bootstrap the provider +Get-PackageProvider -Name $nuget -Force # ------------------------------------------------------------------------------ # Actual Tests: -Describe "Get-package" -Tags "Feature" { +Describe "Get-package" -Tags @('BVT', 'DRT'){ # make sure that packagemanagement is loaded - It "EXPECTED: Get-package accepts array of strings for -providername parameter" -Skip { + import-packagemanagement + + It "EXPECTED: Get-package accepts array of strings for -providername parameter" { $x = (get-package -providername Programs,Msi) } } -Describe "Get-package with version parameter - valid scenarios" -Tags "Feature" { - $destination = Join-Path $TestDrive GetPackageTests +Describe "Get-package with version parameter - valid scenarios" -Tags @('BVT', 'DRT'){ + # make sure that packagemanagement is loaded + import-packagemanagement - It "Get-package supports -AllVersions parameter" -Skip { + It "Get-package supports -AllVersions parameter" { $outputWithAllVersions = (Get-Package -providername Programs,Msi -AllVersions) $outputWithoutAllVersions = (Get-Package -providername Programs,Msi) $outputWithAllVersions.count -ge $outputWithoutAllVersions.count | should be $true @@ -64,19 +73,21 @@ Describe "Get-package with version parameter - valid scenarios" -Tags "Feature" } } -Describe "Get-package with version parameter - Error scenarios" -Tags "Feature" { +Describe "Get-package with version parameter - Error scenarios" -Tags @('BVT', 'DRT'){ + # make sure that packagemanagement is loaded + import-packagemanagement It "Get-package -AllVersions -- Cannot be used with other version parameters" { $Error.Clear() - Get-Package -AllVersions -RequiredVersion 1.0 -MinimumVersion 2.0 -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "AllVersionsCannotBeUsedWithOtherVersionParameters,Microsoft.PowerShell.PackageManagement.Cmdlets.GetPackage" + $msg = powershell 'Get-Package -AllVersions -RequiredVersion 1.0 -MinimumVersion 2.0 -warningaction:silentlycontinue -ea silentlycontinue; $ERROR[0].FullyQualifiedErrorId' + $msg | should be "AllVersionsCannotBeUsedWithOtherVersionParameters,Microsoft.PowerShell.PackageManagement.Cmdlets.GetPackage" } It "Get-package -RequiredVersion -- Cannot be used with Min/Max version parameters" { $Error.Clear() - Get-Package -RequiredVersion 1.0 -MinimumVersion 2.0 -MaximumVersion 3.0 -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "VersionRangeAndRequiredVersionCannotBeSpecifiedTogether,Microsoft.PowerShell.PackageManagement.Cmdlets.GetPackage" + $msg = powershell 'Get-Package -RequiredVersion 1.0 -MinimumVersion 2.0 -MaximumVersion 3.0 -warningaction:silentlycontinue -ea silentlycontinue; $ERROR[0].FullyQualifiedErrorId' + $msg | should be "VersionRangeAndRequiredVersionCannotBeSpecifiedTogether,Microsoft.PowerShell.PackageManagement.Cmdlets.GetPackage" } -} +} \ No newline at end of file diff --git a/test/powershell/Modules/PackageManagement/Get-PackageProvider.Tests.ps1 b/test/powershell/Modules/PackageManagement/Get-PackageProvider.Tests.ps1 index b0b775058..360332446 100644 --- a/test/powershell/Modules/PackageManagement/Get-PackageProvider.Tests.ps1 +++ b/test/powershell/Modules/PackageManagement/Get-PackageProvider.Tests.ps1 @@ -12,21 +12,25 @@ # limitations under the License. # # ------------------ PackageManagement Test ---------------------------------------------- +ipmo "$PSScriptRoot\utility.psm1" + # ------------------------------------------------------------------------------ # Actual Tests: -Describe "get-packageprovider" -Tags "Feature" { +Describe "get-packageprovider" -Tags @('BVT', 'DRT'){ + # make sure that packagemanagement is loaded + import-packagemanagement It "lists package providers installed" { - $x = (get-packageprovider -name "nuget").name | should match "nuget" + $x = (get-packageprovider -name "nuget" -ForceBootstrap).name | should match "nuget" } It "lists package providers installed" { $x = (get-packageprovider -name "nuget" -verbose -Force).name | should match "nuget" } - It "EXPECTED: Gets The 'Programs' Package Provider" -Skip { + It "EXPECTED: Gets The 'Programs' Package Provider" { $x = (get-packageprovider -name "Programs").name | should match "Programs" } @@ -36,23 +40,23 @@ Describe "get-packageprovider" -Tags "Feature" { It "EXPECTED: returns an error when asking for a provider that does not exist" { $Error.Clear() - get-packageprovider -name NOT_EXISTS -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "UnknownProviderFromActivatedList,Microsoft.PowerShell.PackageManagement.Cmdlets.GetPackageProvider" + $msg = powershell 'get-packageprovider -name NOT_EXISTS -warningaction:silentlycontinue -ea silentlycontinue; $ERROR[0].FullyQualifiedErrorId' + $msg | should be "UnknownProviderFromActivatedList,Microsoft.PowerShell.PackageManagement.Cmdlets.GetPackageProvider" } It "EXPECTED: returns an error when asking for multiple providers that do not exist" { $Error.Clear() - get-packageprovider -name NOT_EXISTS,NOT_EXISTS2 -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "UnknownProviderFromActivatedList,Microsoft.PowerShell.PackageManagement.Cmdlets.GetPackageProvider" + $msg = powershell 'get-packageprovider -name NOT_EXISTS,NOT_EXISTS2 -warningaction:silentlycontinue -ea silentlycontinue; $ERROR[0].FullyQualifiedErrorId' + $msg | should be "UnknownProviderFromActivatedList,Microsoft.PowerShell.PackageManagement.Cmdlets.GetPackageProvider" } It "EXPECTED: returns an error when asking for multiple providers that do not exist -list" { $Error.Clear() - get-packageprovider -name NOT_EXISTS,NOT_EXISTS2 -ListAvailable -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "UnknownProviders,Microsoft.PowerShell.PackageManagement.Cmdlets.GetPackageProvider" + $msg = powershell 'get-packageprovider -name NOT_EXISTS,NOT_EXISTS2 -ListAvailable -warningaction:silentlycontinue -ea silentlycontinue; $ERROR[0].FullyQualifiedErrorId' + $msg | should be "UnknownProviders,Microsoft.PowerShell.PackageManagement.Cmdlets.GetPackageProvider" } - It "EXPECTED: returns swidtag conformed object for powershell-based provider" -Skip { + It "EXPECTED: returns swidtag conformed object for powershell-based provider" { $onegettest = (Get-PackageProvider OneGetTest -ListAvailable | Where-Object {$_.Version.ToString() -eq "9.9.0.0"} | Select -First 1) $onegettest.Links.Count | should be 3 @@ -72,7 +76,24 @@ Describe "get-packageprovider" -Tags "Feature" { } -Describe "Get-PackageProvider with list" -Tags "Feature" { + +Describe "happy" -Tags @('BVT', 'DRT'){ + # make sure that packagemanagement is loaded + import-packagemanagement + + It "looks for packages in bootstrap" { + (find-package -provider bootstrap).Length | write-host + } + + It "does something else" { + $false | should be $false + } +} + + +Describe "Get-PackageProvider with list" -Tags @('BVT', 'DRT'){ + # make sure that packagemanagement is loaded + import-packagemanagement It "lists package providers installed" { $x = (Get-PackageProvider).Count -gt 1 | should be $true @@ -80,22 +101,21 @@ Describe "Get-PackageProvider with list" -Tags "Feature" { } It "List two providers" { - (get-packageprovider -name "NuGet" -ListAvailable).name | should match "NuGet" + (get-packageprovider -name "OneGetTest" -ListAvailable).name | should match "OneGetTest" (get-packageprovider -name "PowerShellGet" -ListAvailable).name | should match "PowerShellGet" - $providers = get-packageprovider -Name NuGet, PowerShellGet -ListAvailable + $providers = get-packageprovider -Name OneGetTest, PowerShellGet -ListAvailable - $providers | ?{ $_.name -eq "NuGet" } | should not BeNullOrEmpty + $providers | ?{ $_.name -eq "OneGetTest" } | should not BeNullOrEmpty $providers | ?{ $_.name -eq "PowerShellGet" } | should not BeNullOrEmpty } It "List two providers with wildcard chars" { - $providers = get-packageprovider -Name *Get -ListAvailable + $providers = get-packageprovider -Name OneGetTest* -ListAvailable - $providers | ?{ $_.name -eq "NuGet" } | should not BeNullOrEmpty - - # should have both nuget and powershellget - $providers.Count -ge 2 | should be $true + $providers | ?{ $_.name -eq "OneGetTest" } | should not BeNullOrEmpty + #all versions of the OneGetTest provider should be displayed + $providers.Count -ge 3 | should be $true } } diff --git a/test/powershell/Modules/PackageManagement/Import-PackageProvider.Tests.ps1 b/test/powershell/Modules/PackageManagement/Import-PackageProvider.Tests.ps1 index ec742f721..60b7f5cd2 100644 --- a/test/powershell/Modules/PackageManagement/Import-PackageProvider.Tests.ps1 +++ b/test/powershell/Modules/PackageManagement/Import-PackageProvider.Tests.ps1 @@ -12,15 +12,22 @@ # limitations under the License. # # ------------------ PackageManagement Test ---------------------------------------------- +ipmo "$PSScriptRoot\utility.psm1" -#$ProgramModulePath = "$Env:ProgramFiles\WindowsPowerShell\Modules" +$ProgramProviderInstalledPath = "$Env:ProgramFiles\PackageManagement\ProviderAssemblies" + +$LocalAppData = [Environment]::GetFolderPath("LocalApplicationData") +$UserProviderInstalledPath = "$($LocalAppData)\PackageManagement\ProviderAssemblies" + +$ProgramModulePath = "$Env:ProgramFiles\WindowsPowerShell\Modules" + +$mydocument = [Environment]::GetFolderPath("MyDocuments") +$UserModuleFolder = "$($mydocument)\WindowsPowerShell\Modules" $InternalGallery = "https://dtlgalleryint.cloudapp.net/api/v2/" $InternalSource = 'OneGetTestSource' -<# -SKIP FOR NOW SINCE POWERSHELLGET NOT WORKING YET -make sure the package repository exists +#make sure the package repository exists $a=Get-PackageSource -ForceBootstrap| select Name, Location, ProviderName $found = $false @@ -36,11 +43,13 @@ foreach ($item in $a) } Register-PackageSource -Name $InternalSource -Location $InternalGallery -ProviderName 'PowerShellGet' -Trusted -ForceBootstrap -ErrorAction SilentlyContinue -#> + # ------------------------------------------------------------------------------ # Actual Tests: -Describe "import-packageprovider" -Tags "Feature" { +Describe "import-packageprovider" -Tags @('BVT', 'DRT'){ + # make sure that packagemanagement is loaded + import-packagemanagement It "Import -force 'PowerShellGet', a builtin package provider, Expect succeed" { #avoid popup for installing nuget-any.exe @@ -49,7 +58,7 @@ Describe "import-packageprovider" -Tags "Feature" { } - It "Import a PowerShell package provider Expect succeed" -Skip { + It "Import a PowerShell package provider Expect succeed" { (get-packageprovider -name "OneGetTest" -list).name | should match "OneGetTest" $x = PowerShell '(Import-PackageProvider OneGetTest -WarningAction SilentlyContinue).Name' $x | should match "OneGetTest" @@ -58,7 +67,7 @@ Describe "import-packageprovider" -Tags "Feature" { $x | should match "OneGetTest" } - It "Import 'OneGetTestProvider' CSharp package provider with filePath from programs folder, Expect succeed" -Skip { + It "Import 'OneGetTestProvider' CSharp package provider with filePath from programs folder, Expect succeed" { $path = "$($ProgramProviderInstalledPath)\Microsoft.PackageManagement.OneGetTestProvider.dll" $path | should Exist @@ -72,7 +81,7 @@ Describe "import-packageprovider" -Tags "Feature" { } - It "Import 'PSChained1Provider' PowerShell package provider with filePath from programfiles folder, Expect succeed" -Skip { + It "Import 'PSChained1Provider' PowerShell package provider with filePath from programfiles folder, Expect succeed" { $path = "$($ProgramModulePath)\PSChained1Provider.psm1" $path | should Exist @@ -86,7 +95,7 @@ Describe "import-packageprovider" -Tags "Feature" { } - It "Import a CSharp package provider with filePath from user folder -force, Expect succeed" -Skip { + It "Import a CSharp package provider with filePath from user folder -force, Expect succeed" { $path = "$($UserProviderInstalledPath)\Microsoft.PackageManagement.OneGetTestProvider.dll" $path | should Exist @@ -98,7 +107,7 @@ Describe "import-packageprovider" -Tags "Feature" { $a.Name | should match "OneGetTestProvider" } - It "Import a PowerShell package provider with filePath from user folder -force, Expect succeed" -Skip { + It "Import a PowerShell package provider with filePath from user folder -force, Expect succeed" { $path = "$($UserModuleFolder)\PSChained1Provider.psm1" $path | should Exist @@ -111,7 +120,7 @@ Describe "import-packageprovider" -Tags "Feature" { $a.Name | should match "PSChained1Provider" } - It "Import a PowerShell package provider with -force, Expect succeed" -Skip { + It "Import a PowerShell package provider with -force, Expect succeed" { $path = "$($UserModuleFolder)\PSChained1Provider.psm1" $path | should Exist @@ -142,7 +151,7 @@ Describe "import-packageprovider" -Tags "Feature" { $theError.FullyQualifiedErrorId | should be "FailedToImportProvider,Microsoft.PowerShell.PackageManagement.Cmdlets.ImportPackageProvider" } - It "Import 'OneGetTest' PowerShell package provider that has multiple versions, Expect succeed" -Skip { + It "Import 'OneGetTest' PowerShell package provider that has multiple versions, Expect succeed" { #check all version of OneGetTest is listed $x = get-packageprovider "OneGetTest" -ListAvailable @@ -159,75 +168,79 @@ Describe "import-packageprovider" -Tags "Feature" { -Describe "import-packageprovider Error Cases" -Tags "Feature" { +Describe "import-packageprovider Error Cases" -Tags @('BVT', 'DRT'){ + # make sure that packagemanagement is loaded + import-packagemanagement It "Expected error when importing wildcard chars 'OneGetTest*" { $Error.Clear() - import-packageprovider -name OneGetTest* -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "InvalidParameter,Microsoft.PowerShell.PackageManagement.Cmdlets.ImportPackageProvider" + $msg = powershell 'import-packageprovider -name OneGetTest* -warningaction:silentlycontinue -ea silentlycontinue; $ERROR[0].FullyQualifiedErrorId' + $msg | should be "InvalidParameter,Microsoft.PowerShell.PackageManagement.Cmdlets.ImportPackageProvider" } It "EXPECTED: returns an error when inputing a bad version format" { $Error.Clear() - import-packageprovider -name Gistprovider -RequiredVersion BOGUSVERSION -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "InvalidVersion,Microsoft.PowerShell.PackageManagement.Cmdlets.ImportPackageProvider" + $msg = powershell 'import-packageprovider -name Gistprovider -RequiredVersion BOGUSVERSION -warningaction:silentlycontinue -ea silentlycontinue; $ERROR[0].FullyQualifiedErrorId' + $msg | should be "InvalidVersion,Microsoft.PowerShell.PackageManagement.Cmdlets.ImportPackageProvider" } It "EXPECTED: returns an error when asking for a provider that does not exist" { $Error.Clear() - import-packageprovider -name NOT_EXISTS -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "NoMatchFoundForCriteria,Microsoft.PowerShell.PackageManagement.Cmdlets.ImportPackageProvider" + $msg = powershell 'import-packageprovider -name NOT_EXISTS -warningaction:silentlycontinue -ea silentlycontinue; $ERROR[0].FullyQualifiedErrorId' + $msg | should be "NoMatchFoundForCriteria,Microsoft.PowerShell.PackageManagement.Cmdlets.ImportPackageProvider" } - It "EXPECTED: returns an error when asking for a provider with file full path and version" -Skip { + It "EXPECTED: returns an error when asking for a provider with file full path and version" { $Error.Clear() - import-packageprovider -name "$($ProgramModulePath)\PSChained1Provider.psm1" -RequiredVersion 9.9.9 -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "FullProviderFilePathVersionNotAllowed,Microsoft.PowerShell.PackageManagement.Cmdlets.ImportPackageProvider" + $msg = powershell {import-packageprovider -name "$($ProgramModulePath)\PSChained1Provider.psm1" -RequiredVersion 9.9.9 -warningaction:silentlycontinue -ea silentlycontinue; $ERROR[0].FullyQualifiedErrorId} + $msg | should be "FullProviderFilePathVersionNotAllowed,Microsoft.PowerShell.PackageManagement.Cmdlets.ImportPackageProvider" } It "EXPECTED: returns an error when asking for a provider with RequiredVersoin and MinimumVersion" { $Error.Clear() - import-packageprovider -name PowerShellGet -RequiredVersion 1.0 -MinimumVersion 2.0 -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "VersionRangeAndRequiredVersionCannotBeSpecifiedTogether,Microsoft.PowerShell.PackageManagement.Cmdlets.ImportPackageProvider" + $msg = powershell 'import-packageprovider -name PowerShellGet -RequiredVersion 1.0 -MinimumVersion 2.0 -warningaction:silentlycontinue -ea silentlycontinue; $ERROR[0].FullyQualifiedErrorId' + $msg | should be "VersionRangeAndRequiredVersionCannotBeSpecifiedTogether,Microsoft.PowerShell.PackageManagement.Cmdlets.ImportPackageProvider" } It "EXPECTED: returns an error when asking for a provider with RequiredVersoin and MaximumVersion" { $Error.Clear() - import-packageprovider -name PowerShellGet -RequiredVersion 1.0 -MaximumVersion 2.0 -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "VersionRangeAndRequiredVersionCannotBeSpecifiedTogether,Microsoft.PowerShell.PackageManagement.Cmdlets.ImportPackageProvider" + $msg = powershell 'import-packageprovider -name PowerShellGet -RequiredVersion 1.0 -MaximumVersion 2.0 -warningaction:silentlycontinue -ea silentlycontinue; $ERROR[0].FullyQualifiedErrorId' + $msg | should be "VersionRangeAndRequiredVersionCannotBeSpecifiedTogether,Microsoft.PowerShell.PackageManagement.Cmdlets.ImportPackageProvider" } It "EXPECTED: returns an error when asking for a provider with a MinimumVersion greater than MaximumVersion" { $Error.Clear() - import-packageprovider -name PowerShellGet -MaximumVersion 1.0 -MinimumVersion 2.0 -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "MinimumVersionMustBeLessThanMaximumVersion,Microsoft.PowerShell.PackageManagement.Cmdlets.ImportPackageProvider" + $msg = powershell 'import-packageprovider -name PowerShellGet -MaximumVersion 1.0 -MinimumVersion 2.0 -warningaction:silentlycontinue -ea silentlycontinue; $ERROR[0].FullyQualifiedErrorId' + $msg | should be "MinimumVersionMustBeLessThanMaximumVersion,Microsoft.PowerShell.PackageManagement.Cmdlets.ImportPackageProvider" } It "EXPECTED: returns an error when asking for a provider with MinimumVersion that does not exist" { $Error.Clear() - Import-packageprovider -name OneGetTest -MinimumVersion 20.2 -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "NoMatchFoundForCriteria,Microsoft.PowerShell.PackageManagement.Cmdlets.ImportPackageProvider" + $msg = powershell 'Import-packageprovider -name OneGetTest -MinimumVersion 20.2 -warningaction:silentlycontinue -ea silentlycontinue; $ERROR[0].FullyQualifiedErrorId' + $msg | should be "NoMatchFoundForCriteria,Microsoft.PowerShell.PackageManagement.Cmdlets.ImportPackageProvider" } It "EXPECTED: returns an error when asking for a provider with MaximumVersion that does not exist" { $Error.Clear() - Import-packageprovider -name OneGetTest -MaximumVersion 0.2 -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "NoMatchFoundForCriteria,Microsoft.PowerShell.PackageManagement.Cmdlets.ImportPackageProvider" + $msg = powershell 'Import-packageprovider -name OneGetTest -MaximumVersion 0.2 -warningaction:silentlycontinue -ea silentlycontinue; $ERROR[0].FullyQualifiedErrorId' + $msg | should be "NoMatchFoundForCriteria,Microsoft.PowerShell.PackageManagement.Cmdlets.ImportPackageProvider" } It "EXPECTED: returns an error when asking for a provider that has name with wildcard and version" { $Error.Clear() - Import-packageprovider -name "OneGetTest*" -RequiredVersion 4.5 -force -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "MultipleNamesWithVersionNotAllowed,Microsoft.PowerShell.PackageManagement.Cmdlets.ImportPackageProvider" + $msg = powershell 'Import-packageprovider -name "OneGetTest*" -RequiredVersion 4.5 -force -warningaction:silentlycontinue -ea silentlycontinue; $ERROR[0].FullyQualifiedErrorId' + $msg | should be "MultipleNamesWithVersionNotAllowed,Microsoft.PowerShell.PackageManagement.Cmdlets.ImportPackageProvider" } } -Describe "Import-PackageProvider with OneGetTest that has 3 versions: 1.1, 3.5, and 9.9." -Tags "Feature" { +Describe "Import-PackageProvider with OneGetTest that has 3 versions: 1.1, 3.5, and 9.9." -Tags @('BVT', 'DRT') { + # make sure that packagemanagement is loaded + import-packagemanagement - It "EXPECTED: success 'import OneGetTest -requiredVersion 3.5'" -Skip { + It "EXPECTED: success 'import OneGetTest -requiredVersion 3.5'" { powershell '(Import-packageprovider -name OneGetTest -requiredVersion 3.5 -WarningAction SilentlyContinue).Version.ToString()' | should match "3.5.0.0" # test that if we call a function with error, powershell does not hang for the provider @@ -247,24 +260,24 @@ Describe "Import-PackageProvider with OneGetTest that has 3 versions: 1.1, 3.5, } } - It "EXPECTED: success 'Import OneGetTest -requiredVersion 3.5 and then 9.9 -force'" -Skip { + It "EXPECTED: success 'Import OneGetTest -requiredVersion 3.5 and then 9.9 -force'" { $a = powershell {(Import-packageprovider -name OneGetTest -RequiredVersion 3.5) > $null; (Import-packageprovider -name OneGetTest -requiredVersion 9.9 -force)} $a.Version.ToString()| should match "9.9.0.0" } - It "EXPECTED: success 'import OneGetTest with MinimumVersion and MaximumVersion'" -Skip { + It "EXPECTED: success 'import OneGetTest with MinimumVersion and MaximumVersion'" { powershell '(Import-packageprovider -name OneGetTest -MinimumVersion 1.2 -MaximumVersion 5.0 -WarningAction SilentlyContinue).Version.ToString()' | should match "3.5.0.0" } - It "EXPECTED: success 'OneGetTest with MaximumVersion'" -Skip { + It "EXPECTED: success 'OneGetTest with MaximumVersion'" { powershell '(Import-packageprovider -name OneGetTest -MaximumVersion 3.5 -WarningAction SilentlyContinue).Version.ToString()' | should match "3.5.0.0" } - It "EXPECTED: success 'OneGetTest with MinimumVersion'" -Skip { + It "EXPECTED: success 'OneGetTest with MinimumVersion'" { powershell '(Import-packageprovider -name OneGetTest -MinimumVersion 2.2 -WarningAction SilentlyContinue).Version.ToString()' | should match "9.9.0.0" } - It "EXPECTED: success 'OneGetTest Find-Package with Progress'" -Skip { + It "EXPECTED: success 'OneGetTest Find-Package with Progress'" { $ps = [PowerShell]::Create() $ps.AddScript("Import-PackageProvider -Name OneGetTest -RequiredVersion 9.9; Find-Package -ProviderName OneGetTest") $ps.Invoke() @@ -306,7 +319,7 @@ Describe "Import-PackageProvider with OneGetTest that has 3 versions: 1.1, 3.5, $ps.Streams.Progress[7].PercentComplete | should be 25 } - It "EXPECTED: success 'OneGetTest Find-Package returns correct TagId'" -Skip { + It "EXPECTED: success 'OneGetTest Find-Package returns correct TagId'" { $ps = [PowerShell]::Create() $ps.AddScript("Import-PackageProvider -Name OneGetTest -RequiredVersion 9.9; Find-Package -ProviderName OneGetTest") $result = $ps.Invoke() | Select -First 1 @@ -314,7 +327,7 @@ Describe "Import-PackageProvider with OneGetTest that has 3 versions: 1.1, 3.5, $result.TagId | should match "MyVeryUniqueTagId" } - It "EXPECTED: success 'OneGetTest Get-Package returns correct package object using swidtag'" -Skip { + It "EXPECTED: success 'OneGetTest Get-Package returns correct package object using swidtag'" { $ps = [PowerShell]::Create() $null = $ps.AddScript("`$null = Import-PackageProvider -Name OneGetTest -RequiredVersion 9.9; Get-Package -ProviderName OneGetTest") $result = $ps.Invoke() @@ -324,7 +337,7 @@ Describe "Import-PackageProvider with OneGetTest that has 3 versions: 1.1, 3.5, ($result | Select -Last 1).TagId | should match "jWhat-jWhere-jWho-jQuery" } - It "EXPECTED: success 'OneGetTest Get-Package returns correct progress message'" -Skip { + It "EXPECTED: success 'OneGetTest Get-Package returns correct progress message'" { $ps = [PowerShell]::Create() $null = $ps.AddScript("`$null = Import-PackageProvider -Name OneGetTest -RequiredVersion 9.9; Get-Package -ProviderName OneGetTest") $result = $ps.Invoke() @@ -344,57 +357,59 @@ Describe "Import-PackageProvider with OneGetTest that has 3 versions: 1.1, 3.5, } } -Describe "Import-PackageProvider with OneGetTestProvider that has 2 versions: 4.5, 6.1" -Tags "Feature" { - # install onegettestprovider - # Not working yet since powershellget not working - # Install-PackageProvider -Name OneGetTestProvider -RequiredVersion 4.5.0.0 -Source $InternalGallery - # Install-PackageProvider -Name OneGetTestProvider -RequiredVersion 6.1.0.0 -Source $InternalGallery +Describe "Import-PackageProvider with OneGetTestProvider that has 2 versions: 4.5, 6.1" -Tags @('BVT', 'DRT') { + # make sure that packagemanagement is loaded + import-packagemanagement - It "EXPECTED: Get-PackageProvider -ListAvailable succeeds" -Pending { + # install onegettestprovider + Install-PackageProvider -Name OneGetTestProvider -RequiredVersion 4.5.0.0 -Source $InternalGallery + Install-PackageProvider -Name OneGetTestProvider -RequiredVersion 6.1.0.0 -Source $InternalGallery + + It "EXPECTED: Get-PackageProvider -ListAvailable succeeds" { $providers = Get-PackageProvider -ListAvailable ($providers | Where-Object {$_.Name -eq 'OneGetTest'}).Count | should match 3 ($providers | Where-Object {$_.Name -eq 'OneGetTestProvider'}).Count -ge 2 | should be $true } - It "EXPECTED: Get-PackageProvider -ListAvailable succeeds even after importing gist provider" -Pending { - Install-PackageProvider GistProvider -Source $InternalGallery + It "EXPECTED: Get-PackageProvider -ListAvailable succeeds even after importing gist provider" { + Install-PackageProvider GistProvider -Source $InternalGallery Import-PackageProvider Gist $providers = Get-PackageProvider -ListAvailable ($providers | Where-Object {$_.Name -eq 'OneGetTest'}).Count | should match 3 ($providers | Where-Object {$_.Name -eq 'OneGetTestProvider'}).Count -ge 2 | should be $true } - It "EXPECTED: success 'import OneGetTestProvider -requiredVersion 4.5'" -Pending { + It "EXPECTED: success 'import OneGetTestProvider -requiredVersion 4.5'" { Import-PackageProvider -Name OneGetTestProvider -RequiredVersion 4.5 -Force (Get-PackageProvider OneGetTestProvider).Version.ToString() | should match '4.5.0.0' } - It "EXPECTED: success 'import OneGetTestProvider with MinimumVersion and MaximumVersion'" -Pending { + It "EXPECTED: success 'import OneGetTestProvider with MinimumVersion and MaximumVersion'" { Import-packageprovider -name OneGetTestProvider -MinimumVersion 4.6 -MaximumVersion 6.2 -Force (Get-PackageProvider OneGetTestProvider).Version.ToString() | should match '6.1.0.0' } - It "EXPECTED: success 'import OneGetTestProvider with MaximumVersion'" -Pending { + It "EXPECTED: success 'import OneGetTestProvider with MaximumVersion'" { Import-packageprovider -name OneGetTestProvider -MaximumVersion 4.6 -Force (Get-PackageProvider OneGetTestProvider).Version.ToString() | should match '4.5.0.0' } - It "EXPECTED: success 'OneGetTestProvider with MinimumVersion'" -Pending { + It "EXPECTED: success 'OneGetTestProvider with MinimumVersion'" { Import-packageprovider -name OneGetTestProvider -MinimumVersion 6.0.5 -Force (Get-PackageProvider OneGetTestProvider).Version -ge [version]'6.1.0.0' | should be $true } - It "EXPECTED: success 'Import OneGetTestProvider -requiredVersion 4.5 and then 6.1 -force'" -Pending { + It "EXPECTED: success 'Import OneGetTestProvider -requiredVersion 4.5 and then 6.1 -force'" { Import-PackageProvider -Name OneGetTestProvider -RequiredVersion 4.5 -Force; Import-PackageProvider -Name OneGetTestProvider -RequiredVersion 6.1 -Force; (Get-PackageProvider OneGetTestProvider).Version.ToString() | should match '6.1.0.0' } - It "EXPECTED: success 'Import OneGetTestProvider -MinimumVersion 4.5 and then MaximumVersion 5.0 -force'" -Pending { + It "EXPECTED: success 'Import OneGetTestProvider -MinimumVersion 4.5 and then MaximumVersion 5.0 -force'" { Import-PackageProvider -Name OneGetTestProvider -MinimumVersion 4.5 -Force; (Get-PackageProvider OneGetTestProvider).Version -ge [version]'6.1.0.0' | should be $true Import-PackageProvider -Name OneGetTestProvider -MaximumVersion 5.0 -Force; (Get-PackageProvider OneGetTestProvider).Version.ToString() | should match '4.5.0.0' } -} +} \ No newline at end of file diff --git a/test/powershell/Modules/PackageManagement/Install-PackageProvider.Tests.ps1 b/test/powershell/Modules/PackageManagement/Install-PackageProvider.Tests.ps1 index d4d0ef2cf..efbbdefe4 100644 --- a/test/powershell/Modules/PackageManagement/Install-PackageProvider.Tests.ps1 +++ b/test/powershell/Modules/PackageManagement/Install-PackageProvider.Tests.ps1 @@ -12,14 +12,15 @@ # limitations under the License. # # ------------------ PackageManagement Test ----------------------------------- +ipmo "$PSScriptRoot\utility.psm1" $InternalGallery = "https://dtlgalleryint.cloudapp.net/api/v2/" $InternalGallery2 = "http://dtlgalleryint.cloudapp.net/api/v2/" $InternalSource = 'OneGetTestSource' $InternalSource2 = 'OneGetTestSource2' $ProviderFolder = "$env:ProgramFiles\PackageManagement\ProviderAssemblies" +$destination = "$env:tmp\installpp" #make sure the package repository exists -<# Cannot run these yet since powershellget not working yet $a=Get-PackageSource -ForceBootstrap| select Name, Location, ProviderName $found = $false @@ -36,14 +37,13 @@ foreach ($item in $a) Register-PackageSource -Name $InternalSource -Location $InternalGallery -ProviderName 'PowerShellGet' -Trusted -ForceBootstrap -ErrorAction SilentlyContinue Register-PackageSource -Name $InternalSource2 -Location $InternalGallery2 -ProviderName 'PowerShellGet' -ForceBootstrap -ErrorAction SilentlyContinue -#> # ------------------------------------------------------------------------------ # Actual Tests: -Describe "install-packageprovider" -Tags "Feature" { - - <# +Describe "install-packageprovider" -Tags @('BVT', 'DRT') { + # make sure that packagemanagement is loaded + import-packagemanagement BeforeEach { $m= Get-InstalledModule -Name myalbum -ErrorAction SilentlyContinue -WarningAction SilentlyContinue @@ -52,9 +52,15 @@ Describe "install-packageprovider" -Tags "Feature" { Remove-Item -Path $m.InstalledLocation -Recurse -force -ErrorAction SilentlyContinue -WarningAction SilentlyContinue -Verbose } } - #> - It "install-packageprovider, Expect succeed" -Pending { + AfterAll { + #make sure we are using the latest Nuget provider + Install-PackageProvider -name nuget -force + } + + It "install-packageprovider, Expect succeed" { + #avoid popup for installing nuget-any.exe + Find-PackageProvider -force $a = (install-PackageProvider -name gistprovider -force -source $InternalSource).name $a -contains "gistprovider" | should be $true "gistprovider" @@ -79,7 +85,7 @@ Describe "install-packageprovider" -Tags "Feature" { } - It "install-packageprovider from bootstrap web site, Expect succeed" -Skip { + It "install-packageprovider from bootstrap web site, Expect succeed" { $a = (Install-PackageProvider -Name nuget -RequiredVersion 2.8.5.127 -Force).name $a | should match "nuget" @@ -90,7 +96,7 @@ Describe "install-packageprovider" -Tags "Feature" { $nugetBootstrapped.Links[0].Relationship | should match "installationmedia" } - It "find | install-packageprovider -name array, Expect succeed" -Pending { + It "find | install-packageprovider -name array, Expect succeed" { $names=@("gistprovider", "TSDProvider") # @@ -99,7 +105,23 @@ Describe "install-packageprovider" -Tags "Feature" { $a -contains "TSDProvider" | should be $true } - It "find | install-packageprovider nuget should imported and installed, Expect succeed" -Skip { + It "Install zip packages" { + try { + $env:BootstrapProviderTestfeedUrl = "https://onegetblob.blob.core.windows.net/test/providers.nuget.testfeed.swidtag" + + $installed = Install-PackageProvider nuget -force + + $installed.Name -contains "nuget" | should be $true + $installed.Name -contains "packagelist" | should be $true + + (Test-Path $env:ProgramFiles\PackageManagement\ProviderAssemblies\nuget\*\en-us\*.resources*) | should be $true + } + finally { + $env:BootstrapProviderTestfeedUrl = "" + } + } + + It "find | install-packageprovider nuget should imported and installed, Expect succeed" { $a = Find-PackageProvider -name NuGet -RequiredVersion 2.8.5.202 | install-PackageProvider -force $a.Name | Should match "NuGet" @@ -107,20 +129,20 @@ Describe "install-packageprovider" -Tags "Feature" { } - It "find | install-packageprovider nuget should imported and installed, Expect succeed" -Skip { + It "find | install-packageprovider nuget should imported and installed, Expect succeed" { $a = install-PackageProvider -name NuGet -force $a | ?{ $_.name -eq "NuGet" } | should not BeNullOrEmpty $a | ?{ $_.Version -gt "2.8.5.202" } | should not BeNullOrEmpty } - It "install-packageprovider myalbum should imported and installed, Expect succeed" -Pending { + It "find | install-packageprovider myalbum should imported and installed, Expect succeed" { $a = Install-PackageProvider -name MyAlbum -Source $InternalSource -force $a | ?{ $_.name -eq "MyAlbum" } | should not BeNullOrEmpty } - It "find | install-packageprovider myalbum should imported and installed, Expect succeed" -Pending { + It "find | install-packageprovider myalbum should imported and installed, Expect succeed" { $a = Find-PackageProvider -name MyAlbum -Source $InternalSource -RequiredVersion 0.1.2 | install-PackageProvider -force $a | ?{ $_.name -eq "MyAlbum" } | should not BeNullOrEmpty @@ -128,8 +150,11 @@ Describe "install-packageprovider" -Tags "Feature" { } } -<# Don't need this test since we are not boostraping -Describe "install-packageprovider with local source" -Tags "Feature" { + + +Describe "install-packageprovider with local source" -Tags @('BVT', 'DRT') { + # make sure that packagemanagement is loaded + import-packagemanagement BeforeAll{ if( test-path $destination ) { @@ -240,12 +265,20 @@ Describe "install-packageprovider with local source" -Tags "Feature" { } } -#> -Describe "Install-Save-Package with multiple sources" -Tags "Feature" { - $destination = Join-Path $TestDrive "installpp" +Describe "Install-Save-Package with multiple sources" -Tags @('BVT', 'DRT'){ + # make sure packagemanagement is loaded + import-packagemanagement + BeforeAll{ + #make sure we are using the latest Nuget provider + install-PackageProvider -name nuget -force + } + AfterAll{ + #make sure we are using the latest Nuget provider + Install-PackageProvider -name nuget -force + } - It "install-package with array of registered sources with a single provider, Expect succeed" -Pending { + It "install-package with array of registered sources with a single provider, Expect succeed" { #powershellget is the provider selected $x= install-package TSDProvider -force -Source @($InternalSource, $InternalSource2) @@ -263,17 +296,17 @@ Describe "Install-Save-Package with multiple sources" -Tags "Feature" { $x= install-package jquery -force -Source @('foooobarrrr', 'https://www.nuget.org/api/v2') -ProviderName @('PowershellGet', 'NuGet') $x | ?{ $_.name -eq "jquery" } | should not BeNullOrEmpty - #$x | ?{ $_.Source -eq "https://www.nuget.org/api/v2" } | should not BeNullOrEmpty + $x | ?{ $_.Source -eq "https://www.nuget.org/api/v2" } | should not BeNullOrEmpty } - It "install-save-package matches with multiple providers with single source, Expect succeed" -Pending { + It "install-save-package matches with multiple providers with single source, Expect succeed" { try { Register-PackageSource -Name foo -Location $InternalGallery -ProviderName 'PowerShellGet' -Trusted -ErrorAction SilentlyContinue Register-PackageSource -Name bar -Location $InternalGallery -ProviderName 'NuGet' -ErrorAction SilentlyContinue if (test-path "$destination") { - Remove-Item $destination -force -Recurse + rm $destination -force -Recurse } @@ -291,7 +324,7 @@ Describe "Install-Save-Package with multiple sources" -Tags "Feature" { (test-path "$destination\TSDProvider*") | should be $true if (test-path "$destination\TSDProvider*") { - Remove-Item $destination\TSDProvider* -force -Recurse + rm $destination\TSDProvider* -force -Recurse } } finally @@ -302,7 +335,7 @@ Describe "Install-Save-Package with multiple sources" -Tags "Feature" { } } - It "install-save-package does not match with any providers with single source, Expect fail" -Pending { + It "install-save-package does not match with any providers with single source, Expect fail" { try { @@ -328,7 +361,7 @@ Describe "Install-Save-Package with multiple sources" -Tags "Feature" { } } - It "install-save-package when the multiple providers find a package but no providers specified, Expect fail" -Pending { + It "install-save-package when the multiple providers find a package but no providers specified, Expect fail" { try { @@ -354,15 +387,14 @@ Describe "Install-Save-Package with multiple sources" -Tags "Feature" { } } - # Skip as we don't have chocolatey anymore - It "install-save-package with multiple names, providers, Expect succeed" -Skip { + It "install-save-package with multiple names, providers, Expect succeed" { try { Register-PackageSource -Name foobar -Location http://www.nuget.org/api/v2 -ProviderName 'NuGet' -ErrorAction SilentlyContinue if (test-path "$destination") { - Remove-Item $destination -force -Recurse + rm $destination -force -Recurse } @@ -379,7 +411,7 @@ Describe "Install-Save-Package with multiple sources" -Tags "Feature" { (test-path "$destination\jquery*") | should be $true if (test-path "$destination\jquery*") { - Remove-Item $destination\jquery* -force -Recurse + rm $destination\jquery* -force -Recurse } } finally @@ -389,8 +421,7 @@ Describe "Install-Save-Package with multiple sources" -Tags "Feature" { } - # Skip as no chocolatey - It "install-save-package with multiple names, providers and sources, Expect succeed" -Skip { + It "install-save-package with multiple names, providers and sources, Expect succeed" { # Contoso and Contososerver can be found from $InternalGallery - No ambiguity. @@ -398,7 +429,7 @@ Describe "Install-Save-Package with multiple sources" -Tags "Feature" { if (test-path "$destination") { - Remove-Item $destination -force -Recurse + rm $destination -force -Recurse } @@ -417,14 +448,14 @@ Describe "Install-Save-Package with multiple sources" -Tags "Feature" { (test-path "$destination\Contoso*") | should be $true if (test-path "$destination\Contoso*") { - Remove-Item $destination\Contoso* -force -Recurse + rm $destination\Contoso* -force -Recurse } } - It "save-package with array of registered sources, Expect succeed" -Pending { + It "save-package with array of registered sources, Expect succeed" { if (test-path "$destination") { - Remove-Item $destination -force -Recurse + rm $destination -force -Recurse } $x= save-package TSDProvider -force -Source @($InternalSource, $InternalSource2) -path $destination -ProviderName @('PowershellGet', 'NuGet') @@ -433,13 +464,13 @@ Describe "Install-Save-Package with multiple sources" -Tags "Feature" { (test-path "$destination\TSDProvider*") | should be $true if (test-path "$destination\TSDProvider*") { - Remove-Item $destination\TSDProvider* -force -Recurse + rm $destination\TSDProvider* -force -Recurse } } - It "save-package with array of sources, Expect succeed" -Skip { + It "save-package with array of sources, Expect succeed" { if (test-path "$destination") { - Remove-Item $destination -force -Recurse + rm $destination -force -Recurse } $x= save-package jquery -force -Source @('fffffbbbbb', 'https://www.nuget.org/api/v2') -path $destination -ProviderName @('Nuget', 'Chocolatey') @@ -449,11 +480,11 @@ Describe "Install-Save-Package with multiple sources" -Tags "Feature" { (test-path "$destination\jquery*") | should be $true if (test-path "$destination\jquery*") { - Remove-Item $destination\jquery* -force -Recurse + rm $destination\jquery* -force -Recurse } } } - Describe "install-packageprovider with Whatif" -Tags "Feature" { + Describe "install-packageprovider with Whatif" -Tags @('BVT', 'DRT'){ # make sure that packagemanagement is loaded #import-packagemanagement @@ -468,8 +499,12 @@ Describe "Install-Save-Package with multiple sources" -Tags "Feature" { Remove-Item $tempFile -ErrorAction SilentlyContinue -WarningAction SilentlyContinue } } + AfterAll{ + #make sure we are using the latest Nuget provider + Install-PackageProvider -name nuget -force + } - It "install-packageprovider -name nuget with whatif, Expect succeed" -Skip { + It "install-packageprovider -name nuget with whatif, Expect succeed" { if($PSCulture -eq 'en-US'){ @@ -489,7 +524,7 @@ Describe "Install-Save-Package with multiple sources" -Tags "Feature" { } } - It "install-packageprovider -name gistprovider with whatif, Expect succeed" -Pending { + It "install-packageprovider -name gistprovider with whatif, Expect succeed" { if($PSCulture -eq 'en-US'){ # Start Transcript @@ -509,19 +544,28 @@ Describe "Install-Save-Package with multiple sources" -Tags "Feature" { } } -Describe "install-packageprovider with Scope" -Tags "Feature" { - # PENDING a lot of these tests because jobs are broken on OPS - +Describe "install-packageprovider with Scope" -Tags @('BVT', 'DRT'){ BeforeAll { - if ($IsWindows) - { - $userName = "smartguy" - $password = "password%1" - #net user $userName /delete | Out-Null - net user $userName $password /add - $secesurestring = ConvertTo-SecureString $password -AsPlainText -Force - $credential = new-object -typename System.Management.Automation.PSCredential -argumentlist $userName, $secesurestring - } + import-packagemanagement + $userName = "smartguy" + $password = "password%1" + #net user $userName /delete | Out-Null + net user $userName $password /add + $secesurestring = ConvertTo-SecureString $password -AsPlainText -Force + $credential = new-object -typename System.Management.Automation.PSCredential -argumentlist $userName, $secesurestring + } + + AfterAll { + # Delete the user profile + net user $userName /delete | Out-Null + <#$userProfilePath = (Get-WmiObject -Class Win32_UserProfile | Where-Object {$_.LocalPath -match $userName}) + + if($path -and (Test-Path $userProfilePath.LocalPath)) { + Remove-Item $path -Force -Recurse -ErrorAction SilentlyContinue -verbose + }#> + + #make sure we are using the latest Nuget provider + Install-PackageProvider -name nuget -force } AfterEach { @@ -532,18 +576,17 @@ Describe "install-packageprovider with Scope" -Tags "Feature" { Remove-Item -Path $m.InstalledLocation -Recurse -force -ErrorAction SilentlyContinue -WarningAction SilentlyContinue -Verbose } } - - It "install-packageprovider without scope in a non-admin console, expect fail" -Pending { + It "install-packageprovider without scope in a non-admin console, expect fail" { $Error.Clear() - $job=Start-Job -ScriptBlock { Install-PackageProvider -Name gistprovider -force -requiredVersion 2.8.5.127} -Credential $credential + $job=Start-Job -ScriptBlock { Install-PackageProvider -Name nuget -force -requiredVersion 2.8.5.127} -Credential $credential Receive-Job -Wait -Job $job -ErrorVariable theError 2>&1 $theError.FullyQualifiedErrorId | should be "InstallRequiresCurrentUserScopeParameterForNonAdminUser,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackageProvider" } - It "install-packageprovider without scope in a non-admin console, expect fail" -Pending { + It "install-packageprovider without scope in a non-admin console, expect fail" { $Error.Clear() @@ -553,7 +596,7 @@ Describe "install-packageprovider with Scope" -Tags "Feature" { $theError.FullyQualifiedErrorId | should be "InstallRequiresCurrentUserScopeParameterForNonAdminUser,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackageProvider" } - It "install-packageprovider with AllUsers scope in a non-admin console, expect fail" -Pending { + It "install-packageprovider with AllUsers scope in a non-admin console, expect fail" { $Error.Clear() $job=Start-Job -ScriptBlock { Install-PackageProvider -Name gistprovider -force -scope AllUsers} -Credential $credential @@ -563,7 +606,7 @@ Describe "install-packageprovider with Scope" -Tags "Feature" { } - It "install-packageprovider CurrentUser scope in a non-admin console, expect succeed" -Pending { + It "install-packageprovider CurrentUser scope in a non-admin console, expect succeed" { $Error.Clear() $job=Start-Job -ScriptBlock { @@ -589,7 +632,7 @@ Describe "install-packageprovider with Scope" -Tags "Feature" { $a | ?{ $_.name -eq "tsdprovider" } | should not BeNullOrEmpty } - It "find and install-packageprovider without scope in a non-admin console, expect fail" -Pending { + It "find and install-packageprovider without scope in a non-admin console, expect fail" { $Error.Clear() $job=Start-Job -ScriptBlock { Find-PackageProvider -Name gistprovider | Install-PackageProvider -force} -Credential $credential @@ -599,7 +642,7 @@ Describe "install-packageprovider with Scope" -Tags "Feature" { } - It "find and install-packageprovider CurrentUser scope in a non-admin console, expect succeed" -Pending { + It "find and install-packageprovider CurrentUser scope in a non-admin console, expect succeed" { $Error.Clear() $job=Start-Job -ScriptBlock { Find-PackageProvider -Name tsdprovider | Install-PackageProvider -force -scope CurrentUser} -Credential $credential @@ -608,8 +651,9 @@ Describe "install-packageprovider with Scope" -Tags "Feature" { $a | ?{ $_.name -eq "tsdprovider" } | should not BeNullOrEmpty } } -Describe "install-PackageProvider with Versions" -Tags "Feature" { +Describe "install-PackageProvider with Versions" -Tags @('BVT', 'DRT') { # make sure that packagemanagement is loaded + import-packagemanagement <# Nuget 2.8.5.127 2.8.5.122 @@ -617,8 +661,11 @@ Describe "install-PackageProvider with Versions" -Tags "Feature" { 2.8.5.101 2.8.5.24#> - It "EXPECTED: success 'install, import, and get nuget package provider'" -Pending { - # Have to change from using nuget to gist when we enable this test + AfterAll{ + #make sure we are using the latest Nuget provider + Install-PackageProvider -name nuget -force + } + It "EXPECTED: success 'install, import, and get nuget package provider'" { (install-packageprovider -name Nuget -requiredVersion 2.8.5.122 -force).Version.ToString() | should match "2.8.5.122" $x = powershell {(import-packageprovider -name nuget -requiredVersion 2.8.5.122 -force > $null); get-packageprovider -name nuget} @@ -626,7 +673,7 @@ Describe "install-PackageProvider with Versions" -Tags "Feature" { $x | ?{ $_.Version.ToString() -eq "2.8.5.122" } | should not BeNullOrEmpty } - It "Install, import, and get a powershell package provider-required version" -Pending { + It "Install, import, and get a powershell package provider-required version" { $a = (install-PackageProvider -name gistprovider -force -requiredversion 1.5 -source $InternalSource) $a.Name -contains "gistprovider" | should be $true $a.Version -contains "1.5" | should be $true @@ -637,17 +684,15 @@ Describe "install-PackageProvider with Versions" -Tags "Feature" { $x | ?{ $_.Version.ToString() -eq "1.5.0.0" } | should not BeNullOrEmpty } - It "EXPECTED: success 'install a provider with MinimumVersion and MaximumVersion'" -Pending { - # Have to change from using nuget to gist when we enable this test + It "EXPECTED: success 'install a provider with MinimumVersion and MaximumVersion'" { (install-packageprovider -name nuget -MinimumVersion 2.8.5.101 -MaximumVersion 2.8.5.123 -force).Version.ToString() | should match "2.8.5.122" } - It "EXPECTED: success 'install a provider with MaximumVersion'" -Pending { - # Have to change from using nuget to gist when we enable this test + It "EXPECTED: success 'install a provider with MaximumVersion'" { (install-packageprovider -name nuget -MaximumVersion 2.8.5.122 -force).Version.ToString() | should match "2.8.5.122" } - It "EXPECTED: success 'install a provider with MaximumVersion'" -Pending { + It "EXPECTED: success 'install a provider with MaximumVersion'" { $a = (install-packageprovider -name gistprovider -force -Source $InternalGallery).Version.ToString() $b = (install-packageprovider -name gistprovider -MinimumVersion 0.6 -force -Source $InternalSource).Version.ToString() @@ -656,9 +701,11 @@ Describe "install-PackageProvider with Versions" -Tags "Feature" { } -Describe "Get-package with mulitiple providers" -Tags "Feature" { +Describe "Get-package with mulitiple providers" -Tags @('BVT', 'DRT'){ + # make sure that packagemanagement is loaded + import-packagemanagement - It "Get-package with multiple providers" -Pending { + It "Get-package with multiple providers" { $a = Install-package -Name TSDProvider -Source $InternalSource -ProviderName PowerShellGet -Force $b = install-package -name TSDProvider -Source $InternalGallery -ProviderName NuGet -Force @@ -677,28 +724,30 @@ Describe "Get-package with mulitiple providers" -Tags "Feature" { } -Describe "install-packageprovider Error Cases" -Tags "Feature" { +Describe "install-packageprovider Error Cases" -Tags @('BVT', 'DRT') { + # make sure that packagemanagement is loaded + import-packagemanagement AfterAll { Unregister-PackageSource -Name OneGetTestSource -Verbose -ErrorAction SilentlyContinue Unregister-PackageSource -Name OneGetTestSource2 -Verbose -ErrorAction SilentlyContinue + #make sure we are using the latest Nuget provider + Install-PackageProvider -name nuget -force } BeforeAll { - <# - #commented out as powershellget is not working yet #make sure we are using the latest Nuget provider + Install-PackageProvider -name nuget -force Register-PackageSource -Name $InternalSource -Location $InternalGallery -ProviderName 'PowerShellGet' -Trusted -ForceBootstrap -ErrorAction SilentlyContinue Register-PackageSource -Name $InternalSource2 -Location $InternalGallery2 -ProviderName 'PowerShellGet' -ForceBootstrap -ErrorAction SilentlyContinue - #> } - It "install-packageprovider -name with wildcards, Expect error" -Pending { + It "install-packageprovider -name with wildcards, Expect error" { $Error.Clear() install-PackageProvider -name gist* -force -source $InternalGallery -warningaction:silentlycontinue -ErrorVariable wildcardError -ErrorAction SilentlyContinue $wildcardError.FullyQualifiedErrorId| should be "WildCardCharsAreNotSupported,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackageProvider" } - It "install-packageprovider - EXPECTED: returns an error when multiples sources contain the same package provider" -Pending { + It "install-packageprovider - EXPECTED: returns an error when multiples sources contain the same package provider" { $Error.Clear() $providers = find-packageprovider -name gistprovider $providers | ?{ $_.Source -match $InternalSource } | should not BeNullOrEmpty @@ -708,7 +757,7 @@ Describe "install-packageprovider Error Cases" -Tags "Feature" { $theError.FullyQualifiedErrorId| should BeNullOrEmpty } - It "install-package - EXPECTED: returns an error when multiples sources contain the same package provider" -Pending { + It "install-package - EXPECTED: returns an error when multiples sources contain the same package provider" { $Error.Clear() $providers = find-package -name gistprovider $providers | ?{ $_.Source -match $InternalSource } | should not BeNullOrEmpty @@ -718,7 +767,7 @@ Describe "install-packageprovider Error Cases" -Tags "Feature" { $theError2.FullyQualifiedErrorId| should BeNullOrEmpty } - It "save-package - EXPECTED: returns an error when multiples sources contain the same package provider" -Pending { + It "save-package - EXPECTED: returns an error when multiples sources contain the same package provider" { $Error.Clear() $providers = find-package -name gistprovider $providers | ?{ $_.Source -match $InternalSource } | should not BeNullOrEmpty @@ -735,45 +784,45 @@ Describe "install-packageprovider Error Cases" -Tags "Feature" { It "EXPECTED: returns an error when inputing a bad version format" { $Error.Clear() - install-packageprovider -name nuget -RequiredVersion BOGUSVERSION -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "InvalidVersion,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackageProvider" + $msg = powershell 'install-packageprovider -name nuget -RequiredVersion BOGUSVERSION -warningaction:silentlycontinue -ea silentlycontinue; $ERROR[0].FullyQualifiedErrorId' + $msg | should be "InvalidVersion,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackageProvider" } It "EXPECTED: returns an error when asking for a provider that does not exist" { $Error.Clear() - install-packageprovider -name NOT_EXISTS -Scope CurrentUser -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "NoMatchFoundForProvider,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackageProvider" + $msg = powershell 'install-packageprovider -name NOT_EXISTS -warningaction:silentlycontinue -ea silentlycontinue; $ERROR[0].FullyQualifiedErrorId' + $msg | should be "NoMatchFoundForProvider,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackageProvider" } It "EXPECTED: returns an error when asking for a provider with RequiredVersoin and MinimumVersion" { $Error.Clear() - install-packageprovider -name NOT_EXISTS -Scope CurrentUser -RequiredVersion 1.0 -MinimumVersion 2.0 -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "VersionRangeAndRequiredVersionCannotBeSpecifiedTogether,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackageProvider" + $msg = powershell 'install-packageprovider -name NOT_EXISTS -RequiredVersion 1.0 -MinimumVersion 2.0 -warningaction:silentlycontinue -ea silentlycontinue; $ERROR[0].FullyQualifiedErrorId' + $msg | should be "VersionRangeAndRequiredVersionCannotBeSpecifiedTogether,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackageProvider" } It "EXPECTED: returns an error when asking for a provider with RequiredVersoin and MaximumVersion" { $Error.Clear() - install-packageprovider -name NOT_EXISTS -Scope CurrentUser -RequiredVersion 1.0 -MaximumVersion 2.0 -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "VersionRangeAndRequiredVersionCannotBeSpecifiedTogether,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackageProvider" + $msg = powershell 'install-packageprovider -name NOT_EXISTS -RequiredVersion 1.0 -MaximumVersion 2.0 -warningaction:silentlycontinue -ea silentlycontinue;$ERROR[0].FullyQualifiedErrorId' + $msg | should be "VersionRangeAndRequiredVersionCannotBeSpecifiedTogether,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackageProvider" } It "EXPECTED: returns an error when asking for a provider with a MinimumVersion greater than MaximumVersion" { $Error.Clear() - install-packageprovider -name nuget -Scope CurrentUser -MaximumVersion 1.0 -MinimumVersion 2.0 -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "NoMatchFoundForProvider,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackageProvider" + $msg = powershell 'install-packageprovider -name nuget -MaximumVersion 1.0 -MinimumVersion 2.0 -warningaction:silentlycontinue -ea silentlycontinue;$ERROR[0].FullyQualifiedErrorId' + $msg | should be "NoMatchFoundForProvider,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackageProvider" } It "EXPECTED: returns an error when asking for a provider with MinimumVersion that does not exist" { $Error.Clear() - install-packageprovider -name gistprovider -MinimumVersion 20.2 -warningaction:silentlycontinue -Scope CurrentUser -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "NoMatchFoundForProvider,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackageProvider" + $msg = powershell 'install-packageprovider -name gistprovider -MinimumVersion 20.2 -warningaction:silentlycontinue -ea silentlycontinue;$ERROR[0].FullyQualifiedErrorId' + $msg | should be "NoMatchFoundForProvider,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackageProvider" } It "EXPECTED: returns an error when asking for a provider with MaximumVersion that does not exist" { $Error.Clear() - install-packageprovider -name gistprovider -Scope CurrentUser -MaximumVersion 0.1 -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "NoMatchFoundForProvider,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackageProvider" + $msg = powershell 'install-packageprovider -name gistprovider -MaximumVersion 0.1 -warningaction:silentlycontinue -ea silentlycontinue;$ERROR[0].FullyQualifiedErrorId' + $msg | should be "NoMatchFoundForProvider,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackageProvider" } } diff --git a/test/powershell/Modules/PackageManagement/Nuget.Tests.ps1 b/test/powershell/Modules/PackageManagement/Nuget.Tests.ps1 index 5c7caa81e..df46a382f 100644 --- a/test/powershell/Modules/PackageManagement/Nuget.Tests.ps1 +++ b/test/powershell/Modules/PackageManagement/Nuget.Tests.ps1 @@ -12,6 +12,8 @@ # limitations under the License. # # ------------------ PackageManagement Test ---------------------------------------------- +ipmo "$PSScriptRoot\utility.psm1" + # ------------------------------------------------------------------------------ # Actual Tests: @@ -24,18 +26,37 @@ $workingMaximumVersions = {"2.0", "2.5", "3.0"}; $packageNames = @("Azurecontrib", "AWSSDK", "TestLib"); $minimumVersions = @("1.0", "1.3", "1.5"); $maximumVersions = @("1.8", "2.1", "2.3"); +$destination = "$env:tmp\nugettests" +$relativetestpath = "$env:tmp\relativepathtestnuget" +$dependenciesSource = "$env:temp\PackageManagementDependencies" $dtlgallery = "https://dtlgalleryint.cloudapp.net/api/v2/" $providerName ="Microsoft-Windows-PowerShell" $vstsFeed = "https://powershellgettest.pkgs.visualstudio.com/DefaultCollection/_packaging/psgettestfeed/nuget/v2" $vstsFeedWithSlash = "https://powershellgettest.pkgs.visualstudio.com/DefaultCollection/_packaging/psgettestfeed/nuget/v2/" -#$proxyPath = "$env:tmp\ProxyConsoleProgram\Microsoft.HttpForwarder.Console.exe" +$proxyPath = "$env:tmp\ProxyConsoleProgram\Microsoft.HttpForwarder.Console.exe" $password = ConvertTo-SecureString "4bwvgxrbzvlxc7xgv22eehlix3enmrdwblrxkirnrc3uak23naoa" -AsPlainText -Force $vstsCredential = New-Object System.Management.Automation.PSCredential "quoct", $password +Get-ChildItem -Path $dependenciesSource -Recurse -Include *.nupkg | % { $_.IsReadOnly = $false } +if( test-path $destination ) { + rmdir -recurse -force $destination -ea silentlycontinue +} +mkdir $destination -ea silentlycontinue + $pkgSources = @("NUGETTEST101", "NUGETTEST202", "NUGETTEST303"); $nuget = "nuget" +# set to this feed to bootstrap the testing version +$env:BootstrapProviderTestfeedUrl = "https://onegetblob.blob.core.windows.net/test/providers.zippedtest.nuget.testfeed.swidtag" + +#bootstrap +Install-PackageProvider -Name $nuget -Force + +$nugetVersion = (Get-PackageProvider $nuget).Version + +"Nuget version is $nugetVersion" + # returns true if the test for the current nuget version should be skipped or not # Example: if we want to skip test for any nuget version below 2.8.5.205, we will use # SkipVersion -maxVersion 2.8.5.205 @@ -52,43 +73,63 @@ function SkipVersion([version]$minVersion,[version]$maxVersion) { return $true } -Describe "Find, Get, Save, and Install-Package with Culture" -Tags "Feature" { +Describe "Installing NuGet packages from the public feed" { + try { + $env:BootstrapProviderTestfeedUrl = [string]::Empty + + $currentPublicFeedVersion = [version]"2.8.5.205" + + $nugetFromPublicFeed = Install-PackageProvider -Name $nuget -Force + ($nugetFromPublicFeed.Version -eq $currentPublicFeedVersion) | should be $true + } + finally { + $env:BootstrapProviderTestfeedUrl = "https://onegetblob.blob.core.windows.net/test/providers.nuget.testfeed.swidtag" + + $currentTestFeedVersion = [version]"2.8.5.206" + + $nugetFromTestFeed = Install-PackageProvider -Name $nuget -Force + ($nugetFromTestFeed.Version -eq $currentTestFeedVersion) | should be $true + } +} + +Describe "Find, Get, Save, and Install-Package with Culture" -Tags @('BVT', 'DRT'){ + # make sure that packagemanagement is loaded + import-packagemanagement - <# (get-packageprovider -name "OneGetTest" -list).name | should match "OneGetTest" $x = PowerShell '(Import-PackageProvider -name OneGetTest -RequiredVersion 9.9 -WarningAction SilentlyContinue -force ).Name' $x | should match "OneGetTest" - #> + - it "EXPECTED: Find a package should not show Culture" -Skip { + it "EXPECTED: Find a package should not show Culture" { $packages = Find-Package -ProviderName OneGetTest -DisplayCulture $packages.Culture | Should Not BeNullOrEmpty $packages.Name | Should Not BeNullOrEmpty } - it "EXPECTED: Find a package with a DisplayCulture" -Skip { + it "EXPECTED: Find a package with a DisplayCulture" { $packages = Find-Package -DisplayCulture $packages.Culture | Should Not BeNullOrEmpty $packages.Name | Should Not BeNullOrEmpty } - it "EXPECTED: Get a package should not show Culture" -Skip { + it "EXPECTED: Get a package should not show Culture" { $packages = Get-Package -DisplayCulture -ProviderName OneGetTest $packages.Culture | Should Not BeNullOrEmpty $packages.Name | Should Not BeNullOrEmpty } - it "EXPECTED: Install a package with a DisplayCulture" -Skip { + it "EXPECTED: Install a package with a DisplayCulture" { $packages = install-Package -ProviderName OneGetTest -name jquery -force -DisplayCulture $packages.Culture | Should Not BeNullOrEmpty $packages.Name | Should Not BeNullOrEmpty } - it "EXPECTED: Save a package with a DisplayCulture" -Skip { + it "EXPECTED: Save a package with a DisplayCulture" { $packages = save-Package -ProviderName OneGetTest -name jquery -DisplayCulture -path $destination $packages.Culture | Should Not BeNullOrEmpty @@ -96,11 +137,13 @@ Describe "Find, Get, Save, and Install-Package with Culture" -Tags "Feature" { } } -Describe "Event Test" -Tags "Feature" { +Describe "Event Test" -Tags @('BVT', 'DRT'){ + # make sure that packagemanagement is loaded + import-packagemanagement - it "EXPECTED: install a package should raise event" -Skip:(-not $IsWindows) { + it "EXPECTED: install a package should raise event" { - Install-Package EntityFramework -ProviderName nuget -requiredVersion 6.1.3 -Destination $TestDrive -source 'http://www.nuget.org/api/v2/' -force + Install-Package EntityFramework -ProviderName nuget -requiredVersion 6.1.3 -Destination $env:tmp -source 'http://www.nuget.org/api/v2/' -force $retryCount= 5 while($retryCount -gt 0) @@ -111,7 +154,7 @@ Describe "Event Test" -Tags "Feature" { { if($events) { - $events[0].Message | Should Match "Package=EntityFramework" + $events[0].Message | Should Match "Package=jQuery" break } } @@ -143,7 +186,7 @@ Describe "Event Test" -Tags "Feature" { } - it "EXPECTED: install a package should report destination" -Skip { + it "EXPECTED: install a package should report destination" { Import-PackageProvider OneGetTest -Force Install-Package Bla -ProviderName OneGetTest -Force @@ -190,10 +233,10 @@ Describe "Event Test" -Tags "Feature" { } - it "EXPECTED: uninstall a package should raise event" -Skip:(-not $IsWindows) { + it "EXPECTED: uninstall a package should raise event" { - Install-Package EntityFramework -ProviderName nuget -requiredVersion 6.1.3 -Destination $TestDrive -source 'http://www.nuget.org/api/v2/' -force - UnInstall-Package EntityFramework -ProviderName nuget -Destination $TestDrive + Install-Package EntityFramework -ProviderName nuget -requiredVersion 6.1.3 -Destination $env:tmp -source 'http://www.nuget.org/api/v2/' -force + UnInstall-Package EntityFramework -ProviderName nuget -Destination $env:tmp $retryCount= 5 while($retryCount -gt 0) @@ -204,7 +247,7 @@ Describe "Event Test" -Tags "Feature" { { if($events) { - $events[0].Message | Should Match "Package=EntityFramework" + $events[0].Message | Should Match "Package=jQuery" break } } @@ -236,9 +279,9 @@ Describe "Event Test" -Tags "Feature" { } - it "EXPECTED: save a package should raise event" -Skip:(-not $IsWindows) { + it "EXPECTED: save a package should raise event" { - save-Package EntityFramework -ProviderName nuget -path $TestDrive -requiredVersion 6.1.3 -source 'http://www.nuget.org/api/v2/' -force + save-Package EntityFramework -ProviderName nuget -path $env:tmp -requiredVersion 6.1.3 -source 'http://www.nuget.org/api/v2/' -force $retryCount= 5 while($retryCount -gt 0) @@ -249,7 +292,7 @@ Describe "Event Test" -Tags "Feature" { { if($events) { - $events[0].Message | Should Match "Package=EntityFramework" + $events[0].Message | Should Match "Package=jQuery" break } } @@ -281,12 +324,16 @@ Describe "Event Test" -Tags "Feature" { } } -Describe "Find-Package" -Tags @('Feature','SLOW'){ - it "EXPECTED: Find a package with a location created via new-psdrive" -Skip:(-not $IsWindows) { +Describe "Find-Package" -Tags @('BVT', 'DRT'){ + # make sure that packagemanagement is loaded + import-packagemanagement + + it "EXPECTED: Find a package with a location created via new-psdrive" { + $Error.Clear() - New-PSDrive -Name xx -PSProvider FileSystem -Root $TestDrive -warningaction:silentlycontinue -ea silentlycontinue > $null; find-package -name "fooobarrr" -provider nuget -source xx:\ -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should Not Be "SourceNotFound,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackage" - $ERROR[0].FullyQualifiedErrorId | should be "NoMatchFoundForCriteria,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackage" + $msg = powershell 'New-PSDrive -Name xx -PSProvider FileSystem -Root $env:tmp -warningaction:silentlycontinue -ea silentlycontinue > $null; find-package -name "fooobarrr" -provider nuget -source xx:\ -warningaction:silentlycontinue -ea silentlycontinue;$ERROR[0].FullyQualifiedErrorId' + $msg | should Not Be "SourceNotFound,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackage" + $msg | should be "NoMatchFoundForCriteria,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackage" } It "EXPECTED: Finds 'Zlib' Package" { @@ -332,7 +379,7 @@ Describe "Find-Package" -Tags @('Feature','SLOW'){ (find-package -name "TestPackage" -provider $nuget -source $fwlink -forcebootstrap).name | should match "TestPackage" } - It "EXPECTED: Finds work with dependencies loop" -Skip { + It "EXPECTED: Finds work with dependencies loop" { (find-package -name "ModuleWithDependenciesLoop" -provider $nuget -source "$dependenciesSource\SimpleDependenciesLoop").name | should match "ModuleWithDependenciesLoop" } @@ -357,7 +404,7 @@ Describe "Find-Package" -Tags @('Feature','SLOW'){ } - It "EXPECTED: Finds package with Credential" -Pending { + It "EXPECTED: Finds package with Credential" { $credPackage = Find-Package Contoso -Credential $vstsCredential -Source $vstsFeed -ProviderName $Nuget $credPackage.Count | should be 1 $credPackage.Name | should match "Contoso" @@ -369,8 +416,8 @@ Describe "Find-Package" -Tags @('Feature','SLOW'){ } It "EXPECTED: Cannot find unlisted package" { - find-package -provider $nuget -source $dtlgallery -name hellops -erroraction silentlycontinue - $Error[0].FullyQualifiedErrorId | should be "NoMatchFoundForCriteria,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackage" + $msg = powershell "find-package -provider $nuget -source $dtlgallery -name hellops -erroraction silentlycontinue; `$Error[0].FullyQualifiedErrorId" + $msg | should be "NoMatchFoundForCriteria,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackage" } It "EXPECTED: Cannot find unlisted package with all versions parameter" { @@ -409,8 +456,8 @@ Describe "Find-Package" -Tags @('Feature','SLOW'){ It "EXPECTED: Cannot find unlisted package with maximum versions" { # error out because all the versions below 0.6 are unlisted - find-package -provider $nuget -source $dtlgallery -name gistprovider -maximumversion 0.6 -erroraction silentlycontinue - $Error[0].FullyQualifiedErrorId | should be "NoMatchFoundForCriteria,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackage" + $msg = powershell "find-package -provider $nuget -source $dtlgallery -name gistprovider -maximumversion 0.6 -erroraction silentlycontinue; `$Error[0].FullyQualifiedErrorId" + $msg | should be "NoMatchFoundForCriteria,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackage" } It "EXPECTED: Cannot find unlisted package with minimum versions" { @@ -476,19 +523,20 @@ Describe "Find-Package" -Tags @('Feature','SLOW'){ } It "EXPECTED: -FAILS- Find-Package with wrong source should not error out about dynamic parameter" { - find-package -source WrongSource -name zlib -erroraction silentlycontinue -Contains PackageManagement - $Error[0].FullyQualifiedErrorId | should be "SourceNotFound,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackage" + $msg = powershell "find-package -source WrongSource -name zlib -erroraction silentlycontinue -Contains PackageManagement; `$Error[0].FullyQualifiedErrorId" + $msg | should be "SourceNotFound,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackage" } It "EXPECTED: -FAILS- Find-Package with wrong source and wrong dynamic parameter" { - find-package -source WrongSource -name zlib -erroraction silentlycontinue -WrongDynamicParameter PackageManagement - $Error[0].FullyQualifiedErrorId | should be "SourceNotFound,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackage" + $msg = powershell "find-package -source WrongSource -name zlib -erroraction silentlycontinue -WrongDynamicParameter PackageManagement; `$Error[0].FullyQualifiedErrorId" + $msg | should be "SourceNotFound,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackage" } } -Describe Save-Package -Tags "Feature" { +Describe Save-Package -Tags @('BVT', 'DRT'){ # make sure packagemanagement is loaded - $destination = $TestDrive + import-packagemanagement + It "EXPECTED success: save-package path should be created with -force " { $dest = "$destination\NeverEverExists" @@ -497,10 +545,10 @@ Describe Save-Package -Tags "Feature" { $package.Name | should be "TSDProvider" (test-path "$dest\TSDProvider*") | should be $true if (test-path "$dest\TSDProvider*") { - Remove-Item $dest\TSDProvider* -force + rm $dest\TSDProvider* -force } if (test-path "$dest") { - Remove-Item $dest -force + rm $dest -force } } @@ -511,21 +559,21 @@ Describe Save-Package -Tags "Feature" { $package.Name | should be "TSDProvider" (test-path "$destination\TSDProvider*") | should be $true if (test-path "$destination\TSDProvider*") { - Remove-Item $destination\TSDProvider* -force + rm $destination\TSDProvider* -force } } - It "EXPECTED success: save-package -LiteralPath" -Pending:(!$IsWindows) { + It "EXPECTED success: save-package -LiteralPath" { $dest = "$destination\NeverEverExists" $package = save-package -LiteralPath $dest -ProviderName nuget -Source $dtlgallery -name TSDProvider -force $package.Name | should be "TSDProvider" (test-path "$dest\TSDProvider*") | should be $true if (test-path "$dest\TSDProvider*") { - Remove-Item $dest\TSDProvider* -force + rm $dest\TSDProvider* -force } if (test-path "$dest") { - Remove-Item $dest -force + rm $dest -force } } @@ -535,20 +583,20 @@ Describe Save-Package -Tags "Feature" { $package.Name | should be "TSDProvider" (test-path "$destination\TSDProvider*") | should be $true if (test-path "$destination\TSDProvider*") { - Remove-Item $destination\TSDProvider* -force + rm $destination\TSDProvider* -force } } It "save-package -name with wildcards, Expect error" { $Error.Clear() $package = save-package -path $destination -name DOESNOTEXIST* -warningaction:silentlycontinue -ErrorVariable wildcardError -ErrorAction SilentlyContinue - $wildcardError.FullyQualifiedErrorId | should be "WildCardCharsAreNotSupported,Microsoft.PowerShell.PackageManagement.Cmdlets.SavePackage" + $wildcardError.FullyQualifiedErrorId| should be "WildCardCharsAreNotSupported,Microsoft.PowerShell.PackageManagement.Cmdlets.SavePackage" } - it "EXPECTED: Saves 'Zlib' Package To Packages Directory" -Pending { + it "EXPECTED: Saves 'Zlib' Package To Packages Directory" { $version = "1.2.8.8" $expectedPackages = @("zlib", "zlib.v120.windesktop.msvcstl.dyn.rt-dyn", "zlib.v140.windesktop.msvcstl.dyn.rt-dyn") - $newDestination = Join-Path $TestDrive "nugetinstallation" + $newDestination = "$env:tmp\nugetinstallation" try { $packages = Save-Package -Name "zlib" -ProviderName $nuget -Source $source -RequiredVersion $version -ForceBootstrap -Path $destination @@ -592,24 +640,23 @@ Describe Save-Package -Tags "Feature" { } if (Test-Path $destination\zlib*) { - Remove-Item $destination\zlib* + rm $destination\zlib* } } } - it "EXPECTED: Saves 'Zlib' Package to Packages Directory and install it without dependencies" -Pending { + it "EXPECTED: Saves 'Zlib' Package to Packages Directory and install it without dependencies" { $version = "1.2.8.8" - $newDestination = "$TestDrive\newdestination\nugetinstallation" + $newDestination = "$env:tmp\nugetinstallation" try { (save-package -name "zlib" -provider $nuget -source $source -Path $destination -RequiredVersion $version) (test-path $destination\zlib*) | should be $true remove-item $destination\zlib.v1* -force -Recurse -ErrorAction SilentlyContinue - $Error.Clear() - install-package -name zlib -provider $nuget -source $destination -destination $newDestination -force -RequiredVersion $version -ErrorAction SilentlyContinue - $Error[0].FullyQualifiedErrorId | should match "UnableToFindDependencyPackage,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackage" + $msg = powershell "install-package -name zlib -provider $nuget -source $destination -destination $newDestination -force -RequiredVersion $version -ErrorAction SilentlyContinue; `$Error[0].FullyQualifiedErrorId" + $msg | should match "UnableToFindDependencyPackage,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackage" (Test-Path "$newDestination\zlib*") | should be $false } finally { @@ -618,13 +665,13 @@ Describe Save-Package -Tags "Feature" { } if (Test-Path $destination\zlib*) { - Remove-Item $destination\zlib* + rm $destination\zlib* } } } - It "EXPECTED: Saves work with dependencies loop" -Skip { + It "EXPECTED: Saves work with dependencies loop" { try { $msg = powershell "save-package -name ModuleWithDependenciesLoop -provider $nuget -source `"$dependenciesSource\SimpleDependenciesLoop`" -path $destination -ErrorAction SilentlyContinue -WarningAction SilentlyContinue; `$Error[0].FullyQualifiedErrorId" $msg | should match "ProviderFailToDownloadFile,Microsoft.PowerShell.PackageManagement.Cmdlets.SavePackage" @@ -632,7 +679,7 @@ Describe Save-Package -Tags "Feature" { } finally { if (Test-Path $destination\ModuleWithDependenciesLoop*) { - Remove-Item $destination\ModuleWithDependenciesLoop* + rm $destination\ModuleWithDependenciesLoop* } } } @@ -644,12 +691,12 @@ Describe Save-Package -Tags "Feature" { } finally { if (Test-Path $destination\TestPackage*) { - Remove-Item $destination\TestPackage* + rm $destination\TestPackage* } } } - It "EXPECTED: Saves 'awssdk' package which has more than 200 versions" -Pending { + It "EXPECTED: Saves 'awssdk' package which has more than 200 versions" { (save-package -name "awssdk" -provider $nuget -source $source -Path $destination) (test-path $destination\awssdk*) | should be $true if (Test-Path $destination\awssdk*) { @@ -657,17 +704,16 @@ Describe Save-Package -Tags "Feature" { } } - It "EXPECTED: Saves package with Credential" -Pending { - #TODO: Need to fix this. Already opened an issue on GitHub + It "EXPECTED: Saves package with Credential" { Save-Package Contoso -Credential $vstsCredential -Source $vstsFeed -ProviderName $Nuget -Path $destination (Test-Path $destination\contoso*) | should be $true if (Test-Path $destination\contoso*) { - Remove-Item $destination\contoso* + rm $destination\contoso* } } - it "EXPECTED: Saves Various Packages With Various Version Parameters To Packages Directory" -Pending { + it "EXPECTED: Saves Various Packages With Various Version Parameters To Packages Directory" { foreach ($x in $packageNames) { foreach ($y in $minimumVersions) { foreach ($z in $maximumVersions) { @@ -681,11 +727,11 @@ Describe Save-Package -Tags "Feature" { } } - It "EXPECTED: Saves 'Zlib' Package After Having The Provider Piped" -Pending { + It "EXPECTED: Saves 'Zlib' Package After Having The Provider Piped" { (find-package -name "zlib" -provider $nuget -source $source | save-package -Path $destination) (Test-Path -Path $destination\zlib*) | should be $true if (Test-Path -Path $destination\zlib*) { - Remove-Item $destination\zlib* + rm $destination\zlib* } } @@ -726,10 +772,10 @@ Describe Save-Package -Tags "Feature" { } } -Describe "save-package with Whatif" -Tags "Feature" { +Describe "save-package with Whatif" -Tags @('BVT', 'DRT'){ # make sure that packagemanagement is loaded #import-packagemanagement - $tempDir = Join-Path $TestDrive "nugettesttempfolder" + $tempDir = "$env:temp\nugettesttempfolder" BeforeEach{ $tempFile = [System.IO.Path]::GetTempFileName() @@ -737,7 +783,7 @@ Describe "save-package with Whatif" -Tags "Feature" { if (-not (Test-Path $tempDir)) { - new-item -type directory $tempDir | Out-Null + md $tempDir | Out-Null } } @@ -774,10 +820,9 @@ Describe "save-package with Whatif" -Tags "Feature" { } -Describe "install-package with Whatif" -Tags "Feature" { +Describe "install-package with Whatif" -Tags @('BVT', 'DRT'){ # make sure that packagemanagement is loaded #import-packagemanagement - $installationPath = Join-Path $TestDrive "InstallationPath" BeforeEach{ $tempFile = [System.IO.Path]::GetTempFileName() @@ -793,43 +838,50 @@ Describe "install-package with Whatif" -Tags "Feature" { } It "install-package -name nuget with whatif, Expect succeed" { - - if($PSCulture -eq 'en-US'){ - # Start Transcript - Start-Transcript -Path $tempFile + if($PSCulture -eq 'en-US'){ + # Start Transcript + Start-Transcript -Path $tempFile - install-Package -name jquery -force -source $source -ProviderName NuGet -destination $installationPath -warningaction:silentlycontinue -ErrorAction SilentlyContinue -whatif + install-Package -name jquery -force -source $source -ProviderName NuGet -destination c:\foof -warningaction:silentlycontinue -ErrorAction SilentlyContinue -whatif - # Stop Transcript and get content of transcript file - Stop-Transcript - $transcriptContent = Get-Content $tempFile + # Stop Transcript and get content of transcript file + Stop-Transcript + $transcriptContent = Get-Content $tempFile - $transcriptContent | where { $_.Contains( $whatif ) } | should be $true - Test-Path $installationPath | should be $false + $transcriptContent | where { $_.Contains( $whatif ) } | should be $true + Test-Path C:\foof | should be $false - Remove-Item $whatif -ErrorAction SilentlyContinue -WarningAction SilentlyContinue + + Remove-Item $whatif -ErrorAction SilentlyContinue -WarningAction SilentlyContinue } } It "install-package -name nuget with whatif where package has a dependencies, Expect succeed" { {install-Package -name zlib -source https://www.nuget.org/api/v2/ ` - -ProviderName NuGet -destination $installationPath -whatif} | should not throw + -ProviderName NuGet -destination c:\foof -whatif} | should not throw } } -Describe "install-package with Scope" -tags "Feature" { +Describe "install-package with Scope" -Tags @('BVT', 'DRT'){ + BeforeAll { + import-packagemanagement + $userName = "smartguy" + $password = "password%1" + net user $userName $password /add + $secesurestring = ConvertTo-SecureString $password -AsPlainText -Force + $credential = new-object -typename System.Management.Automation.PSCredential -argumentlist $userName, $secesurestring + } + + AfterAll { + # Delete the user profile + net user $userName /delete | Out-Null + } it "EXPECTED Success: Get and Install-Package without Scope without destination" { - if ($IsWindows) - { - $ProgramFiles = [System.Environment]::GetEnvironmentVariable("ProgramFiles") - $UserInstalledLocation = "$($ProgramFiles)\Nuget\Packages" - } - else - { - $UserInstalledLocation = "$HOME\.local\share\PackageManagement\NuGet\Packages" - } + $ProgramFiles = [Environment]::GetFolderPath("ProgramFiles") + $UserInstalledLocation = "$($ProgramFiles)\Nuget\Packages" + if (Test-Path $UserInstalledLocation) { Remove-Item -Recurse -Force -Path $UserInstalledLocation -ErrorAction SilentlyContinue @@ -848,15 +900,9 @@ Describe "install-package with Scope" -tags "Feature" { it "EXPECTED Success: Get and Install-Package AllUsers Scope Without destination" { - if ($IsWindows) - { - $ProgramFiles = [System.Environment]::GetEnvironmentVariable("ProgramFiles") - $UserInstalledLocation = "$($ProgramFiles)\Nuget\Packages" - } - else - { - $UserInstalledLocation = "$HOME\.local\share\PackageManagement\NuGet\Packages" - } + $ProgramFiles = [Environment]::GetFolderPath("ProgramFiles") + $UserInstalledLocation = "$($ProgramFiles)\Nuget\Packages" + if (Test-Path $UserInstalledLocation) { Remove-Item -Recurse -Force -Path $UserInstalledLocation -ErrorAction SilentlyContinue @@ -875,15 +921,9 @@ Describe "install-package with Scope" -tags "Feature" { it "EXPECTED Success: Get and Install-Package -Scope CurrentUser with destination" { - if ($IsWindows) - { - $userProfile = [System.Environment]::GetEnvironmentVariable("LocalApplicationData") - $UserInstalledLocation = "$($userProfile)\PackageManagement\Nuget\Packages" - } - else - { - $UserInstalledLocation = "$HOME\.local\share\PackageManagement\NuGet\Packages" - } + $userProfile = [Environment]::GetFolderPath("LocalApplicationData") + $UserInstalledLocation = "$($userProfile)\PackageManagement\Nuget\Packages" + if (Test-Path $UserInstalledLocation) { Remove-Item -Recurse -Force -Path $UserInstalledLocation -ErrorAction SilentlyContinue @@ -900,9 +940,7 @@ Describe "install-package with Scope" -tags "Feature" { (Test-Path "$UserInstalledLocation\GistProvider*") | should be $true } - # Start job not working yet - - It "install-package CurrentUser scope in a non-admin console, expect succeed" -Pending { + It "install-package CurrentUser scope in a non-admin console, expect succeed" { $Error.Clear() $job=Start-Job -ScriptBlock {Param ([Parameter(Mandatory = $True)] [string]$dtlgallery) install-package -ProviderName nuget -source $dtlgallery -name gistprovider -RequiredVersion 0.6 -force -scope CurrentUser} -Credential $credential -ArgumentList $dtlgallery @@ -910,7 +948,7 @@ Describe "install-package with Scope" -tags "Feature" { $a.Name | should match 'gistprovider' } - It "install-package without scope in a non-admin console, expect fail" -Pending { + It "install-package without scope in a non-admin console, expect fail" { $Error.Clear() @@ -922,21 +960,22 @@ Describe "install-package with Scope" -tags "Feature" { $theError.FullyQualifiedErrorId | should be "InstallRequiresCurrentUserScopeParameterForNonAdminUser,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackage" } - It "install-package with AllUsers scope in a non-admin console, expect fail" -Pending { + It "install-package with AllUsers scope in a non-admin console, expect fail" { $Error.Clear() $job=Start-Job -ScriptBlock {install-package -ProviderName nuget -source http://nuget.org/api/v2 -name jquery -force -scope AllUsers} -Credential $credential Receive-Job -Wait -Job $job -ErrorVariable theError2 2>&1 $theError2.FullyQualifiedErrorId | should be "InstallRequiresCurrentUserScopeParameterForNonAdminUser,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackage" - } + + } } -Describe Install-Package -Tags "Feature" { - $destination = Join-Path $TestDrive "NugetPackages" - $relativetestpath = Join-Path $TestDrive "RelativeTestPath" +Describe Install-Package -Tags @('BVT', 'DRT'){ + # make sure packagemanagement is loaded + import-packagemanagement - it "EXPECTED: Installs 'Zlib' Package To Packages Directory" -Pending { + it "EXPECTED: Installs 'Zlib' Package To Packages Directory" { $version = "1.2.8.8" (install-package -name "zlib" -provider $nuget -source $source -destination $destination -force -RequiredVersion $version) (test-path $destination\zlib.1.2*) | should be $true @@ -948,7 +987,7 @@ Describe Install-Package -Tags "Feature" { } } - It "EXPECTED: Install package with credential" -Pending { + It "EXPECTED: Install package with credential" { try { Install-Package -Name Contoso -Provider $nuget -Source $vstsFeed -Credential $vstsCredential -Destination $destination -Force Test-Path $destination\Contoso* | should be $true @@ -960,7 +999,7 @@ Describe Install-Package -Tags "Feature" { } } - It "install-package -name with wildcards, Expect error" { + It "install-packageprovider -name with wildcards, Expect error" { $Error.Clear() install-Package -name gist* -force -source $source -warningaction:silentlycontinue -ErrorVariable wildcardError -ErrorAction SilentlyContinue $wildcardError.FullyQualifiedErrorId| should be "WildCardCharsAreNotSupported,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackage" @@ -979,13 +1018,13 @@ Describe Install-Package -Tags "Feature" { } } - it "EXPECTED: Fails to install a module with simple dependencies loop" -Skip { + it "EXPECTED: Fails to install a module with simple dependencies loop" { $msg = powershell "Install-Package ModuleWithDependenciesLoop -ProviderName nuget -Source `"$dependenciesSource\SimpleDependenciesLoop`" -Destination $destination -ErrorAction SilentlyContinue; `$Error[0].FullyQualifiedErrorId" $msg | should be "DependencyLoopDetected,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackage" } - it "EXPECTED: Fails to install a module with a big dependencies loop" -Skip { + it "EXPECTED: Fails to install a module with a big dependencies loop" { $msg = powershell "Install-Package ModuleA -ProviderName nuget -source `"$dependenciesSource\BigDependenciesLoop`" -Destination $destination -ErrorAction SilentlyContinue;`$Error[0].FullyQualifiedErrorId" $msg | should be "DependencyLoopDetected,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackage" } @@ -1056,7 +1095,7 @@ Describe Install-Package -Tags "Feature" { } } - it "EXPECTED: Installs 'awssdk' Package which has more than 200 versions To Packages Directory" -Pending { + it "EXPECTED: Installs 'awssdk' Package which has more than 200 versions To Packages Directory" { (install-package -name "awssdk" -provider $nuget -source $source -destination $destination -maximumversion 2.3 -force) (test-path $destination\awssdk*) | should be $true if (Test-Path $destination\awssdk*) { @@ -1064,7 +1103,7 @@ Describe Install-Package -Tags "Feature" { } } - it "EXPECTED: Installs Various Packages With Various Version Parameters To Packages Directory" -Pending { + it "EXPECTED: Installs Various Packages With Various Version Parameters To Packages Directory" { foreach ($x in $packageNames) { foreach ($y in $minimumVersions) { foreach ($z in $maximumVersions) { @@ -1078,7 +1117,7 @@ Describe Install-Package -Tags "Feature" { } } - It "EXPECTED: Installs 'Zlib' Package After Having The Provider Piped" -Pending { + It "EXPECTED: Installs 'Zlib' Package After Having The Provider Piped" { (find-package -name "zlib" -provider $nuget -source $source | install-package -destination $destination -force) (Test-Path -Path $destination\zlib*) | should be $true if (Test-Path -Path $destination\zlib*) { @@ -1115,8 +1154,9 @@ Describe Install-Package -Tags "Feature" { } } -Describe Get-Package -Tags "Feature" { - $destination = Join-Path $TestDrive "NuGetPackages" +Describe Get-Package -Tags @('BVT', 'DRT'){ + # make sure packagemanagement is loaded + import-packagemanagement it "EXPECTED: Gets The 'Adept.NugetRunner' Package After Installing" { (install-package -name "adept.nugetrunner" -provider $nuget -source $source -destination $destination -force) @@ -1167,8 +1207,9 @@ Describe Get-Package -Tags "Feature" { } } -Describe Uninstall-Package -Tags "Feature" { - $destination = Join-Path $TestDrive "NuGetPackages" +Describe Uninstall-Package -Tags @('BVT', 'DRT'){ + # make sure packagemanagement is loaded + import-packagemanagement it "EXPECTED: Uninstalls The Right version of 'Jquery'" { @@ -1266,8 +1307,8 @@ Describe Uninstall-Package -Tags "Feature" { Uninstall-Package -Name $packageName -Provider $nuget -AllVersions -Destination $destination # Get-Package must not return any packages - since we just uninstalled allversions of the package - Get-Package -Name "adept.nugetrunner" -Provider $nuget -Destination $destination -AllVersions -warningaction:silentlycontinue -ea silentlycontinue - $ERROR[0].FullyQualifiedErrorId | should be "NoMatchFound,Microsoft.PowerShell.PackageManagement.Cmdlets.GetPackage" + $msg = powershell 'Get-Package -Name "adept.nugetrunner" -Provider $nuget -Destination $destination -AllVersions -warningaction:silentlycontinue -ea silentlycontinue; $ERROR[0].FullyQualifiedErrorId' + $msg | should be "NoMatchFound,Microsoft.PowerShell.PackageManagement.Cmdlets.GetPackage" if (Test-Path $destination\adept.nugetrunner*) { (Remove-Item -Recurse -Force -Path $destination\adept.nugetrunner*) @@ -1277,23 +1318,25 @@ Describe Uninstall-Package -Tags "Feature" { It "uninstall-package -name with wildcards, Expect error" { $Error.Clear() $package = uninstall-package -name packagemanagement* -warningaction:silentlycontinue -ErrorVariable wildcardError -ErrorAction SilentlyContinue - $wildcardError.FullyQualifiedErrorId | should be "WildCardCharsAreNotSupported,Microsoft.PowerShell.PackageManagement.Cmdlets.UninstallPackage" + $wildcardError.FullyQualifiedErrorId| should be "WildCardCharsAreNotSupported,Microsoft.PowerShell.PackageManagement.Cmdlets.UninstallPackage" } It "uninstall-package -name with whitespaces only, Expect error" { $Error.Clear() $package = uninstall-package -name " " -warningaction:silentlycontinue -ErrorVariable wildcardError -ErrorAction SilentlyContinue - $wildcardError.FullyQualifiedErrorId | should be "WhitespacesAreNotSupported,Microsoft.PowerShell.PackageManagement.Cmdlets.UninstallPackage" + $wildcardError.FullyQualifiedErrorId| should be "WhitespacesAreNotSupported,Microsoft.PowerShell.PackageManagement.Cmdlets.UninstallPackage" } } -Describe Get-PackageProvider -Tags "Feature" { +Describe Get-PackageProvider -Tags @('BVT', 'DRT'){ + # make sure that packagemanagement is loaded + import-packagemanagement - it "EXPECTED: Gets The 'Nuget' Package Provider" -Skip { + it "EXPECTED: Gets The 'Nuget' Package Provider" { (get-packageprovider -name $nuget -force).name | should be $nuget } - it "EXPECTED: Should not raise pending reboot operations" -Skip { + it "EXPECTED: Should not raise pending reboot operations" { $count = (get-itemproperty "hklm:\system\currentcontrolset\control\session manager").PendingFileRenameOperations.Count $providers = powershell "get-packageprovider" $countAfter = (get-itemproperty "hklm:\system\currentcontrolset\control\session manager").PendingFileRenameOperations.Count @@ -1301,8 +1344,9 @@ Describe Get-PackageProvider -Tags "Feature" { } } -Describe Get-PackageSource -Tags "Feature" { - $destination = Join-Path $TestDrive "NuGetPackages" +Describe Get-PackageSource -Tags @('BVT', 'DRT'){ + # make sure that packagemanagement is loaded + import-packagemanagement BeforeAll{ #make sure the package repository exists @@ -1314,9 +1358,10 @@ Describe Get-PackageSource -Tags "Feature" { UnRegister-PackageSource -Name 'NugetTemp2' -ErrorAction SilentlyContinue -WarningAction SilentlyContinue } - It "find-install-get-package Expect succeed" { - find-package jquery -source NugetTemp2 -provider nuget | install-package -destination $destination -force - (Test-Path $destination\jQuery*) | should be $true + It "find-install-get-package Expect succeed" { + + find-package jquery | install-package -destination $destination -force -ForceBootstrap + (Test-Path $destination\jquery*) | should be $true $a=get-package -Destination $destination -Name jquery $a | where { $_.Name -eq 'jQuery' } | should be $true } @@ -1346,10 +1391,12 @@ Describe Get-PackageSource -Tags "Feature" { } } -Describe Register-PackageSource -Tags "Feature" { - $Destination = Join-Path $TestDrive "NUgettest" +Describe Register-PackageSource -Tags @('BVT', 'DRT'){ + # make sure that packagemanagement is loaded + import-packagemanagement - it "EXPECTED: Register a package source with a location created via new-psdrive" -Skip { + + it "EXPECTED: Register a package source with a location created via new-psdrive" { New-PSDrive -Name xx -PSProvider FileSystem -Root $destination (register-packagesource -name "psdriveTest" -provider $nuget -location xx:\).name | should be "psdriveTest" (unregister-packagesource -name "psdriveTest" -provider $nuget) @@ -1368,7 +1415,7 @@ Describe Register-PackageSource -Tags "Feature" { } } - it "EXPECTED: Registers a package source that requires a credential with skipvalidate" -Pending { + it "EXPECTED: Registers a package source that requires a credential with skipvalidate" { (register-packagesource -name "psgettestfeed" -provider $nuget -location $vstsFeed -SKipValidate) try { (Find-Package -Source "psgettestfeed" -Name ContosoClient -Credential $vstsCredential).Name | should be "ContosoClient" @@ -1382,7 +1429,7 @@ Describe Register-PackageSource -Tags "Feature" { } - it "EXPECTED: Registers a package source that requires a credential" -Pending { + it "EXPECTED: Registers a package source that requires a credential" { (register-packagesource -name "psgettestfeed" -provider $nuget -location $vstsFeed -Credential $vstsCredential) try { (Find-Package -Source "psgettestfeed" -Name ContosoClient -Credential $vstsCredential).Name | should be "ContosoClient" @@ -1395,12 +1442,11 @@ Describe Register-PackageSource -Tags "Feature" { } } - it "EXPECTED: PackageSource persists" -Skip { + it "EXPECTED: PackageSource persists" { $persist = "persistsource" $pssource = "http://www.powershellgallery.com/api/v2/" $redirectedOutput = "$env:tmp\nugettests\redirectedOutput.txt" $redirectedError = "$env:tmp\nugettests\redirectedError.txt" - try { Start-Process powershell -ArgumentList "register-packagesource -name $persist -location $pssource -provider $nuget" -wait Start-Process powershell -ArgumentList "get-packagesource -name $persist -provider $nuget" -wait -RedirectStandardOutput $redirectedOutput -RedirectStandardError $redirectedError @@ -1437,8 +1483,8 @@ Describe Register-PackageSource -Tags "Feature" { } it "EXPECTED: Registers an invalid package source" { - register-packagesource -name `"BingProvider`" -provider $nuget -location `"http://www.example.com/`" -erroraction silentlycontinue - $Error[0].FullyQualifiedErrorId | should be 'SourceLocationNotValid,Microsoft.PowerShell.PackageManagement.Cmdlets.RegisterPackageSource' + $msg = powershell "register-packagesource -name `"BingProvider`" -provider $nuget -location `"http://www.example.com/`" -erroraction silentlycontinue; `$Error[0].FullyQualifiedErrorId" + $msg | should be 'SourceLocationNotValid,Microsoft.PowerShell.PackageManagement.Cmdlets.RegisterPackageSource' } it "EXPECTED: Registers Multiple Package Sources" { @@ -1454,7 +1500,9 @@ Describe Register-PackageSource -Tags "Feature" { } } -Describe Unregister-PackageSource -Tags "Feature" { +Describe Unregister-PackageSource -Tags @('BVT', 'DRT'){ + # make sure that packagemanagement is loaded + import-packagemanagement it "EXPECTED: Unregisters The 'NugetTest.org' Package Source" { (register-packagesource -name "nugettest.org" -provider $nuget -location $source) @@ -1476,7 +1524,9 @@ Describe Unregister-PackageSource -Tags "Feature" { } } -Describe Set-PackageSource -Tags "Feature" { +Describe Set-PackageSource -Tags @('BVT', 'DRT'){ + # make sure that packagemanagement is loaded + import-packagemanagement it "EXPECTED: Sets The 'NugetTest' Package Source to 'NugetTest2'" { (register-packagesource -name "nugettest" -provider $nuget -location "https://www.nuget.org/api/v2") @@ -1484,7 +1534,7 @@ Describe Set-PackageSource -Tags "Feature" { (unregister-packagesource -name "nugettest2" -provider $nuget) } - it "EXPECTED: Set a package source that requires a credential" -Pending { + it "EXPECTED: Set a package source that requires a credential" { (register-packagesource -name "psgettestfeed" -provider $nuget -location $vstsFeed -Credential $vstsCredential) try { (Set-PackageSource -Name "psgettestfeed" -provider $nuget -NewName "psgettestfeed2" -Credential $vstsCredential) @@ -1518,25 +1568,29 @@ Describe Set-PackageSource -Tags "Feature" { } } -Describe Check-ForCorrectError -Tags "Feature" { +Describe Check-ForCorrectError -Tags @('BVT', 'DRT'){ + # make sure that packagemanagement is loaded + import-packagemanagement it "EXPECTED: returns a correct error for find-package with dynamic parameter when package source is wrong" { $Error.Clear() - find-package -provider $nuget -source http://wrongsource/api/v2 -FilterOnTag tag -ea silentlycontinue - $Error[0].FullyQualifiedErrorId | should be "SourceNotFound,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackage" + $msg = powershell "find-package -provider $nuget -source http://wrongsource/api/v2 -FilterOnTag tag -ea silentlycontinue; `$Error[0].FullyQualifiedErrorId" + $msg | should be "SourceNotFound,Microsoft.PowerShell.PackageManagement.Cmdlets.FindPackage" } it "EXPECTED: returns a correct error for install-package with dynamic parameter when package source is wrong" { $Error.Clear() - install-package -provider $nuget -source http://wrongsource/api/v2 zlib -Destination C:\destination -ea silentlycontinue - $Error[0].FullyQualifiedErrorId | should be "SourceNotFound,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackage" + $msg = powershell "install-package -provider $nuget -source http://wrongsource/api/v2 zlib -Destination C:\destination -ea silentlycontinue; `$Error[0].FullyQualifiedErrorId" + $msg | should be "SourceNotFound,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackage" } } -Describe Test-Proxy -Tags "Feature" { +Describe Test-Proxy -Tags @('BVT', 'DRT') { + # make sure that packagemanagent is loaded + import-packagemanagement - It "EXPECTED: Register package source using proxy" -Skip { + It "EXPECTED: Register package source using proxy" { try { $processId = (Start-Process $proxyPath -PassThru).Id (register-packagesource -name "nugettest7" -provider $nuget -location "https://www.nuget.org/api/v2" -Proxy http://localhost:8080).Name | should be "nugettest7" @@ -1549,7 +1603,7 @@ Describe Test-Proxy -Tags "Feature" { } } - It "EXPECTED: Cannot register using wrong proxy" -Skip { + It "EXPECTED: Cannot register using wrong proxy" { try { $processId = (Start-Process $proxyPath -PassThru).Id $packageSource = register-packagesource -name "nugettest7" -provider $nuget -location "https://www.nuget.org/api/v2" -Proxy http://localhost:8060 -ErrorAction SilentlyContinue @@ -1561,7 +1615,7 @@ Describe Test-Proxy -Tags "Feature" { } } - It "EXPECTED: Set package source using proxy" -Skip { + It "EXPECTED: Set package source using proxy" { try { $processId = (Start-Process $proxyPath -PassThru).Id (register-packagesource -name "nugettest7" -provider $nuget -location "https://www.nuget.org/api/v2" -Proxy http://localhost:8080).Name | should be "nugettest7" @@ -1573,7 +1627,7 @@ Describe Test-Proxy -Tags "Feature" { } } - It "EXPECTED: Cannot set package source using wrong proxy" -Skip { + It "EXPECTED: Cannot set package source using wrong proxy" { try { $processId = (Start-Process $proxyPath -PassThru).Id (register-packagesource -name "nugettest7" -provider $nuget -location "https://www.nuget.org/api/v2" -Proxy http://localhost:8080).Name | should be "nugettest7" @@ -1586,7 +1640,7 @@ Describe Test-Proxy -Tags "Feature" { } } - It "EXPECTED: cannot connect using the wrong proxy" -Skip { + It "EXPECTED: cannot connect using the wrong proxy" { try { $processId = (Start-Process $proxyPath -PassThru).Id $packages = Find-Package -Provider NuGet -Proxy http://localhost:8060 -ErrorAction SilentlyContinue @@ -1597,7 +1651,7 @@ Describe Test-Proxy -Tags "Feature" { } } - It "EXPECTED: cannot connect if the server is not on the list allowed by proxy" -Skip { + It "EXPECTED: cannot connect if the server is not on the list allowed by proxy" { try { $processId = (Start-Process $proxyPath -PassThru).Id $packages = Find-Package -Provider NuGet -Proxy http://localhost:8080 -Source $dtlgallery -ErrorAction SilentlyContinue @@ -1608,7 +1662,7 @@ Describe Test-Proxy -Tags "Feature" { } } - It "EXPECTED: find packages using the correct proxy" -Skip { + It "EXPECTED: find packages using the correct proxy" { try { $processId = (Start-Process $proxyPath -PassThru).Id $jquery = Find-Package -Provider NuGet -Proxy http://localhost:8080 -Source $source -Name jquery @@ -1620,4 +1674,4 @@ Describe Test-Proxy -Tags "Feature" { } } -} +} \ No newline at end of file