8000 Make PowerShell able to enable logging of script block execution on Unix platforms by daxian-dbw · Pull Request #5791 · PowerShell/PowerShell · GitHub
[go: up one dir, main page]

Skip to content

Make PowerShell able to enable logging of script block execution on Unix platforms #5791

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 13 commits into from
Jan 8, 2018

Conversation

daxian-dbw
Copy link
Member
@daxian-dbw daxian-dbw commented Jan 4, 2018

PR Summary

Fix #5695

Enable ScriptBlockLogging on Linux/macOS by moving the GroupPolicy configurations to the configuration file PowerShellProperties.json. Including the following tasks:

  1. Enable the logging via MshLog.cs on Unix platforms. (the 1st commit)
  2. Refactor PropertyAccessor.cs. (the 2nd commit)
    • Remove the unneeded base type
    • Rename 'ConfigPropertyAccessor' to PowerShellConfig
    • Move PowerShellConfig to the namespace System.Management.Automation.Configuration
  3. Rename the enum PropertyScope to ConfigScope. (the 3rd commit)
  4. Rename file PropertyAccessor.cs to PSConfiguration.cs. (the 4th commit)
  5. Refactor GroupPolicy setting related code to use the configuration file. (the 5th commit)
    • Followings are the policy settings that are moved to the configuration file.
      • ScriptExecution settings (used in SecuritySupport.cs)
      • ScriptBlockLogging settings (used in CompiledScriptBlock.cs)
      • ModuleLogging settings (used in ModuleCmdletBase.cs)
      • ProtectedEventLogging settings (used in CompiledScriptBlock.cs)
      • Transcription settings (used in MshHostUserInterface.cs)
      • UpdatableHelp setting (used in UpdatableHelpSystem.cs)
      • ConsoleSessionConfiguration settings (used in CommandLineParameterParser.cs)
    • In PSConfiguration.cs, updated ReadValueFromFile<T> to make it flexible to allow a custom JsonObject parsing implementation delegate passed in.
    • In PSConfiguration.cs, added GetPowerShellPolicies(ConfigScope scope) and make DefaultSourcePath setting part of the new policy settings because it is part of the group policy on windows powershell.
    • In Utils.cs, replace the method GetGroupPolicySetting with T GetPolicySetting<T>(ConfigScope[] preferenceOrder) where T : PolicyBase. The old method was for reading from Registry, while the new one is for reading from configuration file.
    • Changes in other files are the corresponding changes due to GetGroupPolicySetting being replaced.
  6. Add xUnit tests to test reading policy settings from the configuration files in different scenarios. (the 6th commit)
    • The xUnit tests are running in parallel by default. Tests for reading policy settings manipulate the configuration file and thus are in conflict with other xUnit tests. So the existing xUnit tests are moved to the namespace PSTests.Parallel and the new tests are moved to PSTests.Sequential and the corresponding build scripts are updated to run sequential xUnit tests first and then run other xUnit tests in parallel.
  7. A minor change to fix an issue in xUnit test and another minor change to SysLogProvider to make ScriptBlock logging not ignored on Unix platforms. (the 7th commit)
  8. Re-enable GPO support on Windows. On Windows, we first query GPO from registry, if the required policy is not defined, then we query policies from the configuration file. (the 9th commit)
  9. Rename PowerShellProperties.json to powershell.config.json. (the 10th commit)

An example of the configuration file powershell.config.json

{
  "Microsoft.PowerShell:ExecutionPolicy": "RemoteSigned",
  "PowerShellPolicies": {
    "ScriptExecution": {
      "ExecutionPolicy": "RemoteSigned",
      "EnableScripts": true
    },
    "ScriptBlockLogging": {
      "EnableScriptBlockInvocationLogging": true,
      "EnableScriptBlockLogging": true
    },
    "ModuleLogging": {
      "EnableModuleLogging": false,
      "ModuleNames": [
        "PSReadline",
        "PowerShellGet"
      ]
    },
    "ProtectedEventLogging": {
      "EnableProtectedEventLogging": false,
      "EncryptionCertificate": [
        "Joe"
      ]
    },
    "Transcription": {
      "EnableTranscripting": true,
      "EnableInvocationHeader": true,
      "OutputDirectory": "F:\\tmp\\new"
    },
    "UpdatableHelp": {
      "DefaultSourcePath": "f:\\temp"
    },
    "ConsoleSessionConfiguration": {
      "EnableConsoleSessionConfiguration": false,
      "ConsoleSessionConfigurationName": "name"
    }
  },
  "LogLevel": "verbose"
}

Limitation that needs to be documented

On Unix platform, the default logging level filter is information, while the logging of script block execution writes out verbose level logging. So the configuration entry "LogLevel": "verbose" is needed along with the settings in "ScriptBlockLogging". This needs to be documented.

Documentation needed

We need documentation to clarify how logging works in PowerShell. Not sure if we already have some docs about it. Issue MicrosoftDocs/PowerShell-Docs#2017 is opened.

PR Checklist

Note: Please mark anything not applicable to this PR NA.

@daxian-dbw
Copy link
Member Author

There are a lot of changes in this PR. When reviewing this PR, I recommend you review each commit because I intentionally group logically related changes into separate commits.

@lzybkr lzybkr removed their request for review January 4, 2018 21:03
private static string GetConfigurationNameFromGroupPolicy()
{
// Current user policy takes precedence.
var groupPolicySettings = Utils.GetGroupPolicySetting(s_groupPolicyBase, s_consoleSessionConfigurationKey, Utils.RegCurrentUserThenLocalMachine);
if (groupPolicySettings != null)
var consoleSessionSetting = Utils.GetPolicySetting<ConsoleSessionConfiguration>(Utils.CurrentUserThenSystemWideConfig);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

With this change, the Windows PowerShell GPO settings don't apply to PSCore6, correct? This seems correct to me, but is a breaking change. We should label this PR as such. cc @joeyaiello

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, GPO settings in Registry won't apply to PowerShell Core. I have added the breaking change label. Thanks for catching that.

Copy link
Member
@TravisEz13 TravisEz13 Jan 4, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This does not seem correct to me. @Indhukrishna DSC has had feedback that seems to indicate that they expect GPO to apply.

Copy link
Member 8000 Author
@daxian-dbw daxian-dbw Jan 5, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I will start to work on enabling GPO as well on windows. The preference order of the settings should be config file --> GPO, meaning if a policy setting is defined in the config file, then use it; if it's not defined in the config file, query registry. This way, you can have control whether you want the GPO settings to take effect.

Copy link
Collaborator
@iSazonov iSazonov Jan 5, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Common rule is that Computer GPO is high priority, then User GPO, then computer wide config, then user config. It is critical rule and security related.

Update.
Software\Policies\Microsoft\Windows\PowerShell - here Policies assume that it is high priority and should overlap other configs - users can not change its.
Software\Microsoft\Windows\PowerShell - it is a normal config corresponding to a text config file. This setting can be set manually by user or by using Group Policy Preferences (GPP). I think it should be low priority over a text config file (looks as changing defaults or set recommended defaults that the user can change by a config file).

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

For the policy related settings, we are having a debate on which one should take preference. I will talk to @TravisEz13 later today about it.
For non-policy related settings, we shouldn't use registry settings anymore but only refer to the config file.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The conclusion is: on windows, we query group policies from registry first, and if the requested policy is not defined in GP, then we query from the configuration file.
New commit has been pushed to enable this.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

For non-policy related settings, we shouldn't use registry settings anymore but only refer to the config file.

I don't agree - GPO is great Enterprise feature and Domain Admins should have full and flexible control on PowerShell. We could discuss this in a Issue (as I mention below too).

Copy link
Member Author
@daxian-dbw daxian-dbw Jan 7, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I mean "non-policy related settings", like the settings in "SOFTWARE\Microsoft\PowerShell" today. They are not group policies.

@daxian-dbw daxian-dbw added the Breaking-Change breaking change that may affect users label Jan 4, 2018
Copy link
Member
@SteveL-MSFT SteveL-MSFT left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Still reviewing

/// {
/// "DefaultSourcePath" : "path to local updatable help location"
/// }
/// Corresponding settings of the original Group Policies
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If we're moving GPO support, we shouldn't mention "original Group Policies", just call it "PowerShell Policies"

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Since we now re-enabled the GPO support on Windows, I will leave this comment unchanged.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Correct

@@ -269,7 +269,7 @@ internal static int ReadRegistryInt(string policyValueName, int defaultValue)
RegistryKey key;
try
{
key = Registry.LocalMachine.OpenSubKey(Utils.GetRegistryConfigurationPrefix());
key = Registry.LocalMachine.OpenSubKey("SOFTWARE\\Microsoft\\PowerShell\\1\\ShellIds");
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this path should be a const somewhere

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This code is in a #if !CORECLR ... #endif block. I leave the registry key path here only for reference, so that when we clean up this !CORECLR block, we know what the key is.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ok

{
if (!scriptBlock.HasLogged || InternalTestHooks.ForceScriptBlockLogging)
{
// If script block logging is explicitly disabled, or it's from a trusted
// file or internal, skip logging.
if (ScriptBlockLoggingExplicitlyDisabled() ||
if (logSetting?.EnableScriptBlockLogging == false ||
scriptBlock.ScriptBlockData.IsProductCode)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why isn't the IsProductCode check in the outer if statement since it's never logged when set.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Theoretically, this can be re-written as

if ((force && logSetting?.EnableScriptBlockLogging != false) || logSetting?.EnableScriptBlockLogging == true)
{
    if ((!scriptBlock.HasLogged || InternalTestHooks.ForceScriptBlockLogging) && !scriptBlock.ScriptBlockData.IsProductCode)
    {
        ....
    }
}

Or even more aggressively, these two if blocks can be merged into one. But this doesn't look very readable, so I think I'm fine with the original code.

{
if (!scriptBlock.HasLogged || InternalTestHooks.ForceScriptBlockLogging)
{
// If script block logging is explicitly disabled, or it's from a trusted
// file or internal, skip logging.
if (ScriptBlockLoggingExplicitlyDisabled() ||
if (logSetting?.EnableScriptBlockLogging == false ||
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This behavior change may be confusing without some documentation.
We've essentially now have 3 logging states, on, off, and warnings. When the setting is not defined, scripts that have suspicious content are logged.

I suggest a doc change to clarify this.

Copy link
Member Author
@daxian-dbw daxian-dbw Jan 5, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There is no behavior change, the check logSetting?.EnableScriptBlockLogging == false is to make sure that the EnableScriptBlockLogging is explicitly set to false in the config file. If you look at the original implementation of ScriptBlockLoggingExplicitlyDisabled(), it returns true only if the registry key EnableScriptBlockLogging exists and its value is explicitly 0.

I agree to have docs to clarify how logging works in PowerShell. Not sure if we already have some docs about it.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@daxian-dbw Could you please add this in PR description for future docs?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, a documentation section is added to PR description.

{
object enableModuleLoggingValue = null;
if (groupPolicySettings.TryGetValue("EnableModuleLogging", out enableModuleLoggingValue))
if (moduleLogging.EnableModuleLogging == false)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do we really need multiple return paths? Why not if (... == false) else if (... == true) and set status in both cases.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I didn't change the original code, will update it to set status in both cases.

@@ -921,7 +921,7 @@ internal static TranscriptionOption GetSystemTranscriptOption(TranscriptionOptio
{
if (systemTranscript == null)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This lock is not used consistently with other usages. if the intent is to return the updated or original value, the lock should also encapsulate both the "if (transcription != null)" block and the implied else block.

As written, there is a possible race between this path and StopAllTranscribing

Copy link
Member Author
@daxian-dbw daxian-dbw Jan 5, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I didn't change the original code. I guess you are right, this method could return a TranscriptionOption object or null depending on whether StopAllTranscribing set systemTranscript to null before return systemTranscript; in this method. But I'm not familiar enough with the transcribing code to know if that could be a problem.

Can you open an issue tracking this comment? We can look at the transcribing code more closely when addressing that issue.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

internal sealed class ScriptExecution : PolicyBase
{
public string ExecutionPolicy { get; set; }
public bool? EnableScripts { get; set; }
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not sure I understand the value of having this nullable. EnableScripts == null is same as EnableScripts == true, correct? Same question for the nullable properties below where they should have a default value and being null is the same as the default value.

Copy link
Member Author
@daxian-dbw daxian-dbw Jan 5, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

EnableScripts == null means this setting is not defined in the config file, so it's up to powershell to define the default behavior. EnableScripts == true means it's defined in the config file and the value is true. Likewise, EnableScripts == false means it's defined in the config file and the value is false.

It's the same in registry -- a key is not defined, which means the application needs to use the pre-defined behavior; when the key is defined, the value will be either 1 or 0.

Copy link
Member Author
@daxian-dbw daxian-dbw Jan 5, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

An example is the use of EnableScriptBlockLogging in LogScriptBlockCreation(ScriptBlock scriptBlock, bool force)

  • when it's explicitly set to 'true' (1 in registry), we always do script block logging;
  • when it's not defined, we do script block logging when force == true
  • when it's explicitly set to 'false' (0 in registry), we always disable script block logging, even if force == true.

Copy link
10670 Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ok, the force case makes sense that there is a difference with null. Thanks.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't like the nullable too. I see no reason to emulate registry keys. If now we use static classes it is more readable and maintainable to set defaults explicitly. Force works with this too.

Copy link
Member Author
@daxian-dbw daxian-dbw Jan 6, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think it's mimicking registry keys, but a requirement to represent three states: enabled, disabled and undefined. Without bool?, if EnableScriptBlockLogging is not specified in the config file while EnableScriptBlockInvocationLogging is specified, then the deserialized ScriptBlockLogging object will have EnableScriptBlockLogging set to false (the default value), which will be interpreted as "script block logging" is explicitly disabled.

The EnableScriptBlockLogging example is from existing code, I didn't change the logic. If it turns out we don't need the bool? type in future, we can always change it since it's internal.

// Sets the per-user configuration directory
// Note: This directory may or may not exist depending upon the
// execution scenario. Writes will attempt to create the directory
// if it does not already exist.
//
appDataConfigDirectory = Utils.GetUserConfigurationDirectory();
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We can install PowerShell Core side-by-side with other PowerShell Core-s. So we should have configs for "default" system wide installation and for "local" for every user installation.
Also it seems we should have GPO option - "Force GPO for Side-By-Side PowerShell installations" - by default we should apply GPO only for system wide PowerShell installation.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Based on internal discussion today, the current plan is to have PSCore6 GPO settings separate from Windows PowerShell. For now, we don't plan to have side-by-side GPO settings per version of PSCore6 until there is customer need for it. New admx will be published later for the PSCore6 settings (which will be the same as Windows PowerShell, but reside in a different location in registry).

Copy link
Collaborator
@iSazonov iSazonov Jan 6, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

GPO is Enterprise feature. GPO should allow Domain Admins get full control on PowerShell. I full trust MSFT experts but I'd prefer discuss GPO in a Issue. Also we forget about AppLocker.
I'd as Domain Admin prefer don't separate PowerShell Core GPO - it is better by default use Windows PowerShell setting until PowerShell Core GPOs is set explicitly otherwise users can ignore corporate policies.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@iSazonov since PSCore6 is not inbox in Windows and doesn't replace Windows PowerShell, we shouldn't use the same settings. PSCore6 in this case is no different from any 3rd party app.

@daxian-dbw daxian-dbw added the Area-Maintainers-Documentation specific to documentation in this repo label Jan 5, 2018
var settings = new JsonSerializerSettings() { TypeNameHandling = TypeNameHandling.None, MaxDepth = 10 };
var serializer = JsonSerializer.Create(settings);

var configData = serializer.Deserialize<JObject>(jsonReader);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Has a security review been done on this code? Is it possible for the deserializer to create arbitrary types or run arbitrary code? If so is it possible to apply a schema to mitigate? This could be a possible security hole when we (re) implement PowerShell white listing protection. Can you add a comment about this possible vulnerability and create an issue to track?

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

is it possible to apply a schema to mitigate

We have a PR for Test-Json - it can help here.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@PaulHigin the use of JsonSerailizer here is the same as in ConverFrom/ConverTo-Json cmdlets. I will add a comment and create an issue.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I had a closer look at the usage, and think it should be safe. The usage here can only convert values to the limited types: string, bool, string[], bool?, and sub types of PolicyBase.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@daxian-dbw If that is the case then we should be Ok. Thanks.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do PowerShell silently eat wrong config options without the schema check? It is bad UX.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

PowerShell currently doesn't do schema check on the config file, which needs to be addressed. I opened #5809 with 3 tasks. Feel free to bring up more to discuss.

// Create the CurrentUser config directory if it doesn't exist
Directory.CreateDirectory(currentUserConfigDirectory);
}

systemWideConfigFile = Path.Combine(systemWideConfigDirectory, "PowerShellProperties.json");
currentUserConfigFile = Path.Combine(currentUserConfigDirectory, "PowerShellProperties.json");
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I believe Properties should be replaced with Config.
PowerShellConfig.json or PowerShell.Config.json or PowerShell.config.json

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't like this file name either. I will see if I can rename it.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pushed new commit to rename the file. The file name is now powershell.config.json.

/// Lock used to enable multiple concurrent readers and singular write locks within a
/// single process.
/// TODO: This solution only works for IO from a single process. A more robust solution is needed to enable ReaderWriterLockSlim behavior between processes.
/// Lock used to enable multiple concurrent readers and singular write locks within a single process.
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We have lock (s_cachedPolicies) in Utils.cs - maybe that's enough?

Copy link
Member Author
@daxian-dbw daxian-dbw Jan 5, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There are other settings except for the policy related ones and they may query the config file simultaneously, so this lock is needed.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think we could find a way to use only one global lock - if we want to have consistency, it doesn't matter how and what settings change.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The querying for GP setting is a hot code path, especially for the script block logging, every script block execution will query for it. The lock s_cachedPolicies is to make sure that when multiple threads are querying for GP settings at the same time, only one thread will actually hit and read the configuration file.

On windows, group policy settings from registry takes precedence over the configuration file.
If a policy is not defined in GP, then we query from configuration file.
@@ -921,7 +921,7 @@ internal static TranscriptionOption GetSystemTranscriptOption(TranscriptionOptio
{
if (systemTranscript == null)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

/// <summary>
/// Get a specific kind of policy setting from the configuration file.
/// </summary>
internal static T GetPolicySettingFromConfigFile<T>(ConfigScope[] preferenceOrder) where T : PolicyBase, new()
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Shouldn't this be private?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, it should. Will update.

/// <summary>
/// Get a specific kind of policy setting from the group policy registry key.
/// </summary>
internal static T GetPolicySettingFromGPO<T>(ConfigScope[] preferenceOrder) where T : PolicyBase, new()
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This should be private, right?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, it should. Will update.

@@ -29,7 +29,7 @@ internal sealed class PowerShellConfig

private string psHomeConfigDirectory;
private string appDataConfigDirectory;
private const string configFileName = "PowerShellProperties.json";
private const string configFileName = "powershell.config.json";
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Opened MicrosoftDocs/PowerShell-Docs#2017 to track the documentation update.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Note that about_logging.md needs to be updated regardless since it refers to 'PowerShellProperties.json'.

{nameof(UpdatableHelp), @"Software\Policies\Microsoft\PowerShellCore\UpdatableHelp"},
{nameof(ConsoleSessionConfiguration), @"Software\Policies\Microsoft\PowerShellCore\ConsoleSessionConfiguration"}
};
private readonly static ConcurrentDictionary<Tuple<ConfigScope, string>, PolicyBase> s_cachedPoliciesFromRegistry =
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Really, we should register for GP change notifications and clear the cache. Not a regression, so, can you add a comment or file an issue: https://msdn.microsoft.com/en-us/library/windows/desktop/aa374404(v=vs.85).aspx

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Issue #5804 is opened to track this.

@daxian-dbw
Copy link
Member Author

@dantraMSFT @SteveL-MSFT @iSazonov @TravisEz13 I think all comments have been addressed (code updated, or question answered, or issue opened). Can you please take another look to see if the PR is ready to merge?


/// <summary>
/// The GroupPolicy related settings used in PowerShell are as follows in Registry:
/// - Software\Policies\Microsoft\Windows\PowerShell -- { EnableScripts (0 or 1); ExecutionPolicy (string) }
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Needs to be updated as we're putting it under ...\Microsoft\PowerShellCore now

Copy link
Member Author
@daxian-dbw daxian-dbw Jan 8, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Will do. Done.

case nameof(Transcription): result = policies.Transcription; break;
case nameof(UpdatableHelp): result = policies.UpdatableHelp; break;
case nameof(ConsoleSessionConfiguration): result = policies.ConsoleSessionConfiguration; break;
default: Diagnostics.Assert(false, "Unreachable code"); break;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Perhaps have the same assert message as line 656 below?

Copy link
Member Author
< 10000 div class="ml-5">

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done.

@SteveL-MSFT SteveL-MSFT added this to the 6.0.0-GA milestone Jan 8, 2018
Copy link
Member
@TravisEz13 TravisEz13 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We should add GPO tests at some point.

@daxian-dbw
Copy link
Member Author

Thanks all for the reviews!

@daxian-dbw daxian-dbw merged commit d261e1f into PowerShell:master Jan 8, 2018
@daxian-dbw daxian-dbw deleted the event branch January 8, 2018 20:03
@SteveL-MSFT
Copy link
Member

@TravisEz13 can you open an issue to track the GPO tests?

TravisEz13 pushed a commit to TravisEz13/PowerShell that referenced this pull request Jan 9, 2018
…werShell Core (PowerShell#5791)

Make PowerShell Core reads group policy settings from different registry keys (Windows only) and the configuration files (both Windows and Unix).
- On Windows, move to different GPO registry keys.
- On both Windows and Unix, read GPO related settings from the configuration file `powershell.config.json`.
- On Windows, the policy settings in registry take precedence over the configuration file.
- Enable policy controlled logging and transcription on Unix.
@TravisEz13 TravisEz13 mentioned this pull request Jan 9, 2018
TravisEz13 pushed a commit that referenced this pull request Jan 9, 2018
…werShell Core (#5791)

Make PowerShell Core reads group policy settings from different registry keys (Windows only) and the configuration files (both Windows and Unix).
- On Windows, move to different GPO registry keys.
- On both Windows and Unix, read GPO related settings from the configuration file `powershell.config.json`.
- On Windows, the policy settings in registry take precedence over the configuration file.
- Enable policy controlled logging and transcription on Unix.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Area-Maintainers-Documentation specific to documentation in this repo Breaking-Change breaking change that may affect users
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Logging of script block execution cannot be enabled on Unix
6 participants
0