Add source files for Microsoft.PowerShell.LocalAccounts [SD:709776]
Commit 15b1623
This commit is contained in:
parent
1829beb917
commit
802630c261
|
@ -0,0 +1,297 @@
|
|||
#region Using directives
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Management.Automation;
|
||||
using System.Security.Principal;
|
||||
|
||||
using System.Management.Automation.SecurityAccountsManager;
|
||||
using System.Management.Automation.SecurityAccountsManager.Extensions;
|
||||
|
||||
using Microsoft.PowerShell.LocalAccounts;
|
||||
using System.Diagnostics.CodeAnalysis;
|
||||
#endregion
|
||||
|
||||
|
||||
namespace Microsoft.PowerShell.Commands
|
||||
{
|
||||
/// <summary>
|
||||
/// The Add-LocalGroupMember cmdlet adds one or more users or groups to a local
|
||||
/// group.
|
||||
/// </summary>
|
||||
[Cmdlet(VerbsCommon.Add, "LocalGroupMember",
|
||||
SupportsShouldProcess = true,
|
||||
HelpUri = "http://go.microsoft.com/fwlink/?LinkId=717987")]
|
||||
[Alias("algm")]
|
||||
public class AddLocalGroupMemberCommand : PSCmdlet
|
||||
{
|
||||
#region Instance Data
|
||||
private Sam sam = null;
|
||||
#endregion Instance Data
|
||||
|
||||
#region Parameter Properties
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Group".
|
||||
/// Specifies a security group from the local Security Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ParameterSetName = "Group")]
|
||||
[ValidateNotNull]
|
||||
public Microsoft.PowerShell.Commands.LocalGroup Group
|
||||
{
|
||||
get { return this.group;}
|
||||
set { this.group = value; }
|
||||
}
|
||||
private Microsoft.PowerShell.Commands.LocalGroup group;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Member".
|
||||
/// Specifies one or more users or groups to add to this local group. You can
|
||||
/// identify users or groups by specifying their names or SIDs, or by passing
|
||||
/// Microsoft.PowerShell.Commands.LocalPrincipal objects.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 1,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true)]
|
||||
[ValidateNotNullOrEmpty]
|
||||
[SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays")]
|
||||
public Microsoft.PowerShell.Commands.LocalPrincipal[] Member
|
||||
{
|
||||
get { return this.member;}
|
||||
set { this.member = value; }
|
||||
}
|
||||
private Microsoft.PowerShell.Commands.LocalPrincipal[] member;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Name".
|
||||
/// Specifies a security group from the local Security Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ParameterSetName = "Default")]
|
||||
[ValidateNotNullOrEmpty]
|
||||
public string Name
|
||||
{
|
||||
get { return this.name;}
|
||||
set { this.name = value; }
|
||||
}
|
||||
private string name;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "SID".
|
||||
/// Specifies a security group from the local Security Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ParameterSetName = "SecurityIdentifier")]
|
||||
[ValidateNotNull]
|
||||
public System.Security.Principal.SecurityIdentifier SID
|
||||
{
|
||||
get { return this.sid;}
|
||||
set { this.sid = value; }
|
||||
}
|
||||
private System.Security.Principal.SecurityIdentifier sid;
|
||||
#endregion Parameter Properties
|
||||
|
||||
|
||||
#region Cmdlet Overrides
|
||||
/// <summary>
|
||||
/// BeginProcessing method.
|
||||
/// </summary>
|
||||
protected override void BeginProcessing()
|
||||
{
|
||||
sam = new Sam();
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// ProcessRecord method.
|
||||
/// </summary>
|
||||
protected override void ProcessRecord()
|
||||
{
|
||||
try
|
||||
{
|
||||
if (Group != null)
|
||||
ProcessGroup(Group);
|
||||
else if (Name != null)
|
||||
ProcessName(Name);
|
||||
else if (SID != null)
|
||||
ProcessSid(SID);
|
||||
}
|
||||
catch (GroupNotFoundException ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// EndProcessing method.
|
||||
/// </summary>
|
||||
protected override void EndProcessing()
|
||||
{
|
||||
if (sam != null)
|
||||
{
|
||||
sam.Dispose();
|
||||
sam = null;
|
||||
}
|
||||
}
|
||||
#endregion Cmdlet Overrides
|
||||
|
||||
#region Private Methods
|
||||
|
||||
/// <summary>
|
||||
/// Creates a list of <see cref="LocalPrincipal"/> objects
|
||||
/// ready to be processed by the cmdlet.
|
||||
/// </summary>
|
||||
/// <param name="groupId">
|
||||
/// Name or SID (as a string) of the group we'll be adding to.
|
||||
/// This string is used primarily for specifying the target
|
||||
/// in WhatIf scenarios.
|
||||
/// </param>
|
||||
/// <param name="member">
|
||||
/// LocalPrincipal object to be processed
|
||||
/// </param>
|
||||
/// <returns>
|
||||
/// A LocalPrincipal Object to be added to the group
|
||||
/// </returns>
|
||||
/// <remarks>
|
||||
/// <para>
|
||||
/// LocalPrincipal objects in the Member parameter may not be complete,
|
||||
/// particularly those created from a name or a SID string given to the
|
||||
/// Member cmdlet parameter. The object returned from this method contains
|
||||
/// , at the very least, a valid SID.
|
||||
/// </para>
|
||||
/// <para>
|
||||
/// Any Member objects provided by name or SID string will be looked up
|
||||
/// to ensure that such an object exists. If an object is not found,
|
||||
/// an error message is displayed by PowerShell and null will be returned
|
||||
/// </para>
|
||||
/// <para>
|
||||
/// This method also handles the WhatIf scenario. If the Cmdlet's
|
||||
/// <b>ShouldProcess</b> method returns false on any Member object,
|
||||
/// that object will not be included in the returned List.
|
||||
/// </para>
|
||||
/// </remarks>
|
||||
private LocalPrincipal MakePrincipal(string groupId, LocalPrincipal member)
|
||||
{
|
||||
LocalPrincipal principal = null;
|
||||
// if the member has a SID, we can use it directly
|
||||
if (member.SID != null)
|
||||
{
|
||||
principal = member;
|
||||
}
|
||||
else // otherwise it must have been constructed by name
|
||||
{
|
||||
SecurityIdentifier sid = this.TrySid(member.Name);
|
||||
|
||||
if (sid != null)
|
||||
{
|
||||
member.SID = sid;
|
||||
principal = member;
|
||||
}
|
||||
else
|
||||
{
|
||||
try
|
||||
{
|
||||
principal = sam.LookupAccount(member.Name);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
if (CheckShouldProcess(principal, groupId))
|
||||
return principal;
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Determine if a principal should be processed.
|
||||
/// Just a wrapper around Cmdlet.ShouldProcess, with localized string
|
||||
/// formatting.
|
||||
/// </summary>
|
||||
/// <param name="principal">Name of the principal to be added.</param>
|
||||
/// <param name="groupName">
|
||||
/// Name of the group to which the members will be added.
|
||||
/// </param>
|
||||
/// <returns>
|
||||
/// True if the principal should be processed, false otherwise.
|
||||
/// </returns>
|
||||
private bool CheckShouldProcess(LocalPrincipal principal, string groupName)
|
||||
{
|
||||
if (principal == null)
|
||||
return false;
|
||||
|
||||
string msg = StringUtil.Format(Strings.ActionAddGroupMember, principal.ToString());
|
||||
|
||||
return ShouldProcess(groupName, msg);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Add members to a group.
|
||||
/// </summary>
|
||||
/// <param name="group">
|
||||
/// A <see cref="LocalGroup"/> object representing the group to which
|
||||
/// the members will be added.
|
||||
/// </param>
|
||||
private void ProcessGroup(LocalGroup group)
|
||||
{
|
||||
string groupId = group.Name ?? group.SID.ToString();
|
||||
foreach (var member in this.Member)
|
||||
{
|
||||
LocalPrincipal principal = MakePrincipal(groupId, member);
|
||||
if (null != principal)
|
||||
{
|
||||
var ex = sam.AddLocalGroupMember(group, principal);
|
||||
if (null != ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Add members to a group specified by name.
|
||||
/// </summary>
|
||||
/// <param name="name">
|
||||
/// The name of the group to which the members will be added.
|
||||
/// </param>
|
||||
private void ProcessName(string name)
|
||||
{
|
||||
ProcessGroup(sam.GetLocalGroup(name));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Add members to a group specified by SID.
|
||||
/// </summary>
|
||||
/// <param name="groupSid">
|
||||
/// A <see cref="SecurityIdentifier"/> object identifying the group
|
||||
/// to which the members will be added.
|
||||
/// </param>
|
||||
private void ProcessSid(SecurityIdentifier groupSid)
|
||||
{
|
||||
foreach (var member in this.Member)
|
||||
{
|
||||
LocalPrincipal principal = MakePrincipal(groupSid.ToString(), member);
|
||||
if (null != principal)
|
||||
{
|
||||
var ex = sam.AddLocalGroupMember(groupSid, principal);
|
||||
if (null != ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#endregion Private Methods
|
||||
}//End Class
|
||||
|
||||
}//End namespace
|
||||
|
|
@ -0,0 +1,215 @@
|
|||
#region Using directives
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Management.Automation;
|
||||
|
||||
using System.Management.Automation.SecurityAccountsManager;
|
||||
using System.Management.Automation.SecurityAccountsManager.Extensions;
|
||||
|
||||
using Microsoft.PowerShell.LocalAccounts;
|
||||
using System.Diagnostics.CodeAnalysis;
|
||||
#endregion
|
||||
|
||||
|
||||
namespace Microsoft.PowerShell.Commands
|
||||
{
|
||||
/// <summary>
|
||||
/// The Disable-LocalUser cmdlet disables local user accounts. When a user
|
||||
/// account is disabled, the user is not permitted to log on. When a user
|
||||
/// account is enabled, the user is permitted to log on normally.
|
||||
/// </summary>
|
||||
[Cmdlet(VerbsLifecycle.Disable, "LocalUser",
|
||||
SupportsShouldProcess = true,
|
||||
HelpUri = "http://go.microsoft.com/fwlink/?LinkId=717986")]
|
||||
[Alias("dlu")]
|
||||
public class DisableLocalUserCommand : Cmdlet
|
||||
{
|
||||
#region Constants
|
||||
private const Enabling enabling = Enabling.Disable;
|
||||
#endregion Constants
|
||||
|
||||
#region Instance Data
|
||||
private Sam sam = null;
|
||||
#endregion Instance Data
|
||||
|
||||
#region Parameter Properties
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "InputObject".
|
||||
/// Specifies the of the local user accounts to disable in the local Security
|
||||
/// Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "InputObject")]
|
||||
[ValidateNotNullOrEmpty]
|
||||
[SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays")]
|
||||
public Microsoft.PowerShell.Commands.LocalUser[] InputObject
|
||||
{
|
||||
get { return this.inputobject; }
|
||||
set { this.inputobject = value; }
|
||||
}
|
||||
private Microsoft.PowerShell.Commands.LocalUser[] inputobject;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Name".
|
||||
/// Specifies the names of the local user accounts to disable in the local
|
||||
/// Security Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "Default")]
|
||||
[ValidateNotNullOrEmpty]
|
||||
[SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays")]
|
||||
public string[] Name
|
||||
{
|
||||
get { return this.name; }
|
||||
set { this.name = value; }
|
||||
}
|
||||
private string[] name;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "SID".
|
||||
/// Specifies the LocalUser accounts to disable by
|
||||
/// System.Security.Principal.SecurityIdentifier.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "SecurityIdentifier")]
|
||||
[ValidateNotNullOrEmpty]
|
||||
[SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays")]
|
||||
public System.Security.Principal.SecurityIdentifier[] SID
|
||||
{
|
||||
get { return this.sid;}
|
||||
set { this.sid = value; }
|
||||
}
|
||||
private System.Security.Principal.SecurityIdentifier[] sid;
|
||||
#endregion Parameter Properties
|
||||
|
||||
|
||||
#region Cmdlet Overrides
|
||||
/// <summary>
|
||||
/// BeginProcessing method.
|
||||
/// </summary>
|
||||
protected override void BeginProcessing()
|
||||
{
|
||||
sam = new Sam();
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// ProcessRecord method.
|
||||
/// </summary>
|
||||
protected override void ProcessRecord()
|
||||
{
|
||||
try
|
||||
{
|
||||
ProcessUsers();
|
||||
ProcessNames();
|
||||
ProcessSids();
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// EndProcessing method.
|
||||
/// </summary>
|
||||
protected override void EndProcessing()
|
||||
{
|
||||
if (sam != null)
|
||||
{
|
||||
sam.Dispose();
|
||||
sam = null;
|
||||
}
|
||||
}
|
||||
#endregion Cmdlet Overrides
|
||||
|
||||
#region Private Methods
|
||||
/// <summary>
|
||||
/// Process users requested by -Name
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// All arguments to -Name will be treated as names,
|
||||
/// even if a name looks like a SID.
|
||||
/// </remarks>
|
||||
private void ProcessNames()
|
||||
{
|
||||
if (Name != null)
|
||||
{
|
||||
foreach (var name in Name)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (CheckShouldProcess(name))
|
||||
sam.EnableLocalUser(sam.GetLocalUser(name), enabling);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process users requested by -SID
|
||||
/// </summary>
|
||||
private void ProcessSids()
|
||||
{
|
||||
if (SID != null)
|
||||
{
|
||||
foreach (var sid in SID)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (CheckShouldProcess(sid.ToString()))
|
||||
sam.EnableLocalUser(sid, enabling);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process users requested by -InputObject
|
||||
/// </summary>
|
||||
private void ProcessUsers()
|
||||
{
|
||||
if (InputObject != null)
|
||||
{
|
||||
foreach (var user in InputObject)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (CheckShouldProcess(user.Name))
|
||||
sam.EnableLocalUser(user, enabling);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private bool CheckShouldProcess(string target)
|
||||
{
|
||||
return ShouldProcess(target, Strings.ActionDisableUser);
|
||||
}
|
||||
#endregion Private Methods
|
||||
}//End Class
|
||||
|
||||
}//End namespace
|
||||
|
|
@ -0,0 +1,217 @@
|
|||
#region Using directives
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Management.Automation;
|
||||
|
||||
using System.Management.Automation.SecurityAccountsManager;
|
||||
using System.Management.Automation.SecurityAccountsManager.Extensions;
|
||||
|
||||
using Microsoft.PowerShell.LocalAccounts;
|
||||
using System.Diagnostics.CodeAnalysis;
|
||||
#endregion
|
||||
|
||||
|
||||
namespace Microsoft.PowerShell.Commands
|
||||
{
|
||||
/// <summary>
|
||||
/// The Enable-LocalUser cmdlet enables local user accounts. When a user account
|
||||
/// is disabled, the user is not permitted to log on. When a user account is
|
||||
/// enabled, the user is permitted to log on normally.
|
||||
/// </summary>
|
||||
[Cmdlet(VerbsLifecycle.Enable, "LocalUser",
|
||||
SupportsShouldProcess = true,
|
||||
HelpUri = "http://go.microsoft.com/fwlink/?LinkId=717985")]
|
||||
[Alias("elu")]
|
||||
public class EnableLocalUserCommand : Cmdlet
|
||||
{
|
||||
#region Constants
|
||||
private const Enabling enabling = Enabling.Enable;
|
||||
#endregion Constants
|
||||
|
||||
#region Instance Data
|
||||
private Sam sam = null;
|
||||
#endregion Instance Data
|
||||
|
||||
#region Parameter Properties
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "InputObject".
|
||||
/// Specifies the of the local user accounts to enable in the local Security
|
||||
/// Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "InputObject")]
|
||||
[ValidateNotNullOrEmpty]
|
||||
[SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays")]
|
||||
public Microsoft.PowerShell.Commands.LocalUser[] InputObject
|
||||
{
|
||||
get { return this.inputobject; }
|
||||
set { this.inputobject = value; }
|
||||
}
|
||||
private Microsoft.PowerShell.Commands.LocalUser[] inputobject;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Name".
|
||||
/// Specifies the local user accounts to enable in the local Security Accounts
|
||||
/// Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "Default")]
|
||||
[ValidateNotNullOrEmpty]
|
||||
[SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays")]
|
||||
public string[] Name
|
||||
{
|
||||
get { return this.name; }
|
||||
set { this.name = value; }
|
||||
}
|
||||
private string[] name;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "SID".
|
||||
/// Specifies the LocalUser accounts to enable by
|
||||
/// System.Security.Principal.SecurityIdentifier.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "SecurityIdentifier")]
|
||||
[ValidateNotNullOrEmpty]
|
||||
[SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays")]
|
||||
public System.Security.Principal.SecurityIdentifier[] SID
|
||||
{
|
||||
get { return this.sid;}
|
||||
set { this.sid = value; }
|
||||
}
|
||||
private System.Security.Principal.SecurityIdentifier[] sid;
|
||||
#endregion Parameter Properties
|
||||
|
||||
|
||||
|
||||
|
||||
#region Cmdlet Overrides
|
||||
/// <summary>
|
||||
/// BeginProcessing method.
|
||||
/// </summary>
|
||||
protected override void BeginProcessing()
|
||||
{
|
||||
sam = new Sam();
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// ProcessRecord method.
|
||||
/// </summary>
|
||||
protected override void ProcessRecord()
|
||||
{
|
||||
try
|
||||
{
|
||||
ProcessUsers();
|
||||
ProcessNames();
|
||||
ProcessSids();
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// EndProcessing method.
|
||||
/// </summary>
|
||||
protected override void EndProcessing()
|
||||
{
|
||||
if (sam != null)
|
||||
{
|
||||
sam.Dispose();
|
||||
sam = null;
|
||||
}
|
||||
}
|
||||
#endregion Cmdlet Overrides
|
||||
|
||||
#region Private Methods
|
||||
/// <summary>
|
||||
/// Process users requested by -Name
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// All arguments to -Name will be treated as names,
|
||||
/// even if a name looks like a SID.
|
||||
/// </remarks>
|
||||
private void ProcessNames()
|
||||
{
|
||||
if (Name != null)
|
||||
{
|
||||
foreach (var name in Name)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (CheckShouldProcess(name))
|
||||
sam.EnableLocalUser(sam.GetLocalUser(name), enabling);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process users requested by -SID
|
||||
/// </summary>
|
||||
private void ProcessSids()
|
||||
{
|
||||
if (SID != null)
|
||||
{
|
||||
foreach (var sid in SID)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (CheckShouldProcess(sid.ToString()))
|
||||
sam.EnableLocalUser(sid, enabling);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process users requested by -InputObject
|
||||
/// </summary>
|
||||
private void ProcessUsers()
|
||||
{
|
||||
if (InputObject != null)
|
||||
{
|
||||
foreach (var user in InputObject)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (CheckShouldProcess(user.Name))
|
||||
sam.EnableLocalUser(user, enabling);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private bool CheckShouldProcess(string target)
|
||||
{
|
||||
return ShouldProcess(target, Strings.ActionEnableUser);
|
||||
}
|
||||
#endregion Private Methods
|
||||
}//End Class
|
||||
|
||||
}//End namespace
|
||||
|
|
@ -0,0 +1,170 @@
|
|||
#region Using directives
|
||||
using System;
|
||||
using System.Management.Automation;
|
||||
using System.Security.Principal;
|
||||
|
||||
using System.Management.Automation.SecurityAccountsManager;
|
||||
using System.Management.Automation.SecurityAccountsManager.Extensions;
|
||||
using System.Diagnostics.CodeAnalysis;
|
||||
#endregion
|
||||
|
||||
|
||||
namespace Microsoft.PowerShell.Commands
|
||||
{
|
||||
/// <summary>
|
||||
/// The Get-LocalGroup cmdlet gets local groups from the Windows Security
|
||||
/// Accounts manager.
|
||||
/// </summary>
|
||||
[Cmdlet(VerbsCommon.Get, "LocalGroup",
|
||||
DefaultParameterSetName = "Default",
|
||||
HelpUri = "http://go.microsoft.com/fwlink/?LinkId=717974")]
|
||||
[Alias("glg")]
|
||||
public class GetLocalGroupCommand : Cmdlet
|
||||
{
|
||||
#region Instance Data
|
||||
private Sam sam = null;
|
||||
#endregion Instance Data
|
||||
|
||||
#region Parameter Properties
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Name".
|
||||
/// Specifies the local groups to get from the local Security Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "Default")]
|
||||
[ValidateNotNull]
|
||||
[SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays")]
|
||||
public string[] Name
|
||||
{
|
||||
get { return this.name; }
|
||||
set { this.name = value; }
|
||||
}
|
||||
private string[] name;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "SID".
|
||||
/// Specifies a local group from the local Security Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "SecurityIdentifier")]
|
||||
[ValidateNotNull]
|
||||
[SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays")]
|
||||
public System.Security.Principal.SecurityIdentifier[] SID
|
||||
{
|
||||
get { return this.sid;}
|
||||
set { this.sid = value; }
|
||||
}
|
||||
private System.Security.Principal.SecurityIdentifier[] sid;
|
||||
#endregion Parameter Properties
|
||||
|
||||
|
||||
|
||||
|
||||
#region Cmdlet Overrides
|
||||
/// <summary>
|
||||
/// BeginProcessing method.
|
||||
/// </summary>
|
||||
protected override void BeginProcessing()
|
||||
{
|
||||
sam = new Sam();
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// ProcessRecord method.
|
||||
/// </summary>
|
||||
protected override void ProcessRecord()
|
||||
{
|
||||
if (Name == null && SID == null)
|
||||
{
|
||||
foreach (var group in sam.GetAllLocalGroups())
|
||||
WriteObject(group);
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
ProcessNames();
|
||||
ProcessSids();
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// EndProcessing method.
|
||||
/// </summary>
|
||||
protected override void EndProcessing()
|
||||
{
|
||||
if (sam != null)
|
||||
{
|
||||
sam.Dispose();
|
||||
sam = null;
|
||||
}
|
||||
}
|
||||
#endregion Cmdlet Overrides
|
||||
|
||||
#region Private Methods
|
||||
/// <summary>
|
||||
/// Process groups requested by -Name
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// All arguments to -Name will be treated as names,
|
||||
/// even if a name looks like a SID.
|
||||
/// Groups may be specified using wildcards.
|
||||
/// </remarks>
|
||||
private void ProcessNames()
|
||||
{
|
||||
if (Name != null)
|
||||
{
|
||||
foreach (var name in Name)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (WildcardPattern.ContainsWildcardCharacters(name))
|
||||
{
|
||||
var pattern = new WildcardPattern(name, WildcardOptions.Compiled
|
||||
| WildcardOptions.IgnoreCase);
|
||||
|
||||
foreach (var group in sam.GetMatchingLocalGroups(n => pattern.IsMatch(n)))
|
||||
WriteObject(group);
|
||||
}
|
||||
else
|
||||
{
|
||||
WriteObject(sam.GetLocalGroup(name));
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process groups requested by -SID
|
||||
/// </summary>
|
||||
private void ProcessSids()
|
||||
{
|
||||
if (SID != null)
|
||||
{
|
||||
foreach (var sid in SID)
|
||||
{
|
||||
try
|
||||
{
|
||||
WriteObject(sam.GetLocalGroup(sid));
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
#endregion Private Methods
|
||||
}//End Class
|
||||
|
||||
}//End namespace
|
||||
|
|
@ -0,0 +1,229 @@
|
|||
#region Using directives
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Management.Automation;
|
||||
using System.Security.Principal;
|
||||
|
||||
using System.Management.Automation.SecurityAccountsManager;
|
||||
using System.Management.Automation.SecurityAccountsManager.Extensions;
|
||||
#endregion
|
||||
|
||||
|
||||
namespace Microsoft.PowerShell.Commands
|
||||
{
|
||||
/// <summary>
|
||||
/// The Get-LocalGroupMember cmdlet gets the members of a local group.
|
||||
/// </summary>
|
||||
[Cmdlet(VerbsCommon.Get, "LocalGroupMember",
|
||||
DefaultParameterSetName = "Default",
|
||||
HelpUri = "http://go.microsoft.com/fwlink/?LinkId=717988")]
|
||||
[Alias("glgm")]
|
||||
public class GetLocalGroupMemberCommand : Cmdlet
|
||||
{
|
||||
#region Instance Data
|
||||
private Sam sam = null;
|
||||
#endregion Instance Data
|
||||
|
||||
#region Parameter Properties
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Group".
|
||||
/// The security group from the local Security Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "Group")]
|
||||
[ValidateNotNull]
|
||||
public Microsoft.PowerShell.Commands.LocalGroup Group
|
||||
{
|
||||
get { return this.group;}
|
||||
set { this.group = value; }
|
||||
}
|
||||
private Microsoft.PowerShell.Commands.LocalGroup group;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Member".
|
||||
/// Specifies the name of the user or group that is a member of this group. If
|
||||
/// this parameter is not specified, all members of the specified group are
|
||||
/// returned. This accepts a name, SID, or wildcard string.
|
||||
/// </summary>
|
||||
[Parameter(Position = 1)]
|
||||
[ValidateNotNullOrEmpty]
|
||||
public string Member
|
||||
{
|
||||
get { return this.member;}
|
||||
set { this.member = value; }
|
||||
}
|
||||
private string member;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Name".
|
||||
/// The security group from the local Security Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "Default")]
|
||||
[ValidateNotNullOrEmpty]
|
||||
public string Name
|
||||
{
|
||||
get { return this.name;}
|
||||
set { this.name = value; }
|
||||
}
|
||||
private string name;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "SID".
|
||||
/// The security group from the local Security Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "SecurityIdentifier")]
|
||||
[ValidateNotNullOrEmpty]
|
||||
public System.Security.Principal.SecurityIdentifier SID
|
||||
{
|
||||
get { return this.sid;}
|
||||
set { this.sid = value; }
|
||||
}
|
||||
private System.Security.Principal.SecurityIdentifier sid;
|
||||
#endregion Parameter Properties
|
||||
|
||||
|
||||
#region Cmdlet Overrides
|
||||
/// <summary>
|
||||
/// BeginProcessing method.
|
||||
/// </summary>
|
||||
protected override void BeginProcessing()
|
||||
{
|
||||
sam = new Sam();
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// ProcessRecord method.
|
||||
/// </summary>
|
||||
protected override void ProcessRecord()
|
||||
{
|
||||
try
|
||||
{
|
||||
IEnumerable<LocalPrincipal> principals = null;
|
||||
|
||||
if (Group != null)
|
||||
principals = ProcessGroup(Group);
|
||||
else if (Name != null)
|
||||
principals = ProcessName(Name);
|
||||
else if (SID != null)
|
||||
principals = ProcessSid(SID);
|
||||
|
||||
if (principals != null)
|
||||
WriteObject(principals, true);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// EndProcessing method.
|
||||
/// </summary>
|
||||
protected override void EndProcessing()
|
||||
{
|
||||
if (sam != null)
|
||||
{
|
||||
sam.Dispose();
|
||||
sam = null;
|
||||
}
|
||||
}
|
||||
#endregion Cmdlet Overrides
|
||||
|
||||
#region Private Methods
|
||||
private IEnumerable<LocalPrincipal> ProcessesMembership(IEnumerable<LocalPrincipal> membership)
|
||||
{
|
||||
List<LocalPrincipal> rv;
|
||||
|
||||
// if no members are specified, return all of them
|
||||
if (Member == null)
|
||||
{
|
||||
//return membership;
|
||||
rv = new List<LocalPrincipal>(membership);
|
||||
}
|
||||
else
|
||||
{
|
||||
//var rv = new List<LocalPrincipal>();
|
||||
rv = new List<LocalPrincipal>();
|
||||
|
||||
if (WildcardPattern.ContainsWildcardCharacters(Member))
|
||||
{
|
||||
var pattern = new WildcardPattern(Member, WildcardOptions.Compiled
|
||||
| WildcardOptions.IgnoreCase);
|
||||
|
||||
foreach (var m in membership)
|
||||
if (pattern.IsMatch(sam.StripMachineName(m.Name)))
|
||||
rv.Add(m);
|
||||
}
|
||||
else
|
||||
{
|
||||
var sid = this.TrySid(Member);
|
||||
|
||||
if (sid != null)
|
||||
{
|
||||
foreach (var m in membership)
|
||||
{
|
||||
if (m.SID == sid)
|
||||
{
|
||||
rv.Add(m);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
foreach (var m in membership)
|
||||
{
|
||||
if (sam.StripMachineName(m.Name).Equals(Member, StringComparison.CurrentCultureIgnoreCase))
|
||||
{
|
||||
rv.Add(m);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (rv.Count == 0)
|
||||
{
|
||||
var ex = new PrincipalNotFoundException(member, member);
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// sort the resulting principals by mane
|
||||
rv.Sort((p1, p2) => string.Compare(p1.Name, p2.Name, StringComparison.CurrentCultureIgnoreCase));
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
private IEnumerable<LocalPrincipal> ProcessGroup(LocalGroup group)
|
||||
{
|
||||
return ProcessesMembership(sam.GetLocalGroupMembers(group));
|
||||
}
|
||||
|
||||
private IEnumerable<LocalPrincipal> ProcessName(string name)
|
||||
{
|
||||
return ProcessGroup(sam.GetLocalGroup(name));
|
||||
}
|
||||
|
||||
private IEnumerable<LocalPrincipal> ProcessSid(SecurityIdentifier groupSid)
|
||||
{
|
||||
return ProcessesMembership(sam.GetLocalGroupMembers(groupSid));
|
||||
}
|
||||
#endregion Private Methods
|
||||
}//End Class
|
||||
|
||||
}//End namespace
|
||||
|
|
@ -0,0 +1,172 @@
|
|||
#region Using directives
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Diagnostics.CodeAnalysis;
|
||||
using System.Management.Automation;
|
||||
|
||||
using System.Management.Automation.SecurityAccountsManager;
|
||||
using System.Management.Automation.SecurityAccountsManager.Extensions;
|
||||
#endregion
|
||||
|
||||
|
||||
namespace Microsoft.PowerShell.Commands
|
||||
{
|
||||
/// <summary>
|
||||
/// The Get-LocalUser cmdlet gets local user accounts from the Windows Security
|
||||
/// Accounts Manager. This includes local accounts that have been connected to a
|
||||
/// Microsoft account.
|
||||
/// </summary>
|
||||
[Cmdlet(VerbsCommon.Get, "LocalUser",
|
||||
DefaultParameterSetName = "Default",
|
||||
HelpUri = "http://go.microsoft.com/fwlink/?LinkId=717980")]
|
||||
[Alias("glu")]
|
||||
public class GetLocalUserCommand : Cmdlet
|
||||
{
|
||||
#region Instance Data
|
||||
private Sam sam = null;
|
||||
#endregion Instance Data
|
||||
|
||||
#region Parameter Properties
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Name".
|
||||
/// Specifies the local user accounts to get from the local Security Accounts
|
||||
/// Manager. This accepts a name or wildcard string.
|
||||
/// </summary>
|
||||
[Parameter(Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "Default")]
|
||||
[ValidateNotNull]
|
||||
[SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays")]
|
||||
public string[] Name
|
||||
{
|
||||
get { return this.name; }
|
||||
|
||||
set { this.name = value; }
|
||||
}
|
||||
private string[] name;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "SID".
|
||||
/// Specifies a user from the local Security Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "SecurityIdentifier")]
|
||||
[ValidateNotNull]
|
||||
[SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays")]
|
||||
public System.Security.Principal.SecurityIdentifier[] SID
|
||||
{
|
||||
get { return this.sid; }
|
||||
set { this.sid = value; }
|
||||
}
|
||||
private System.Security.Principal.SecurityIdentifier[] sid;
|
||||
#endregion Parameter Properties
|
||||
|
||||
|
||||
|
||||
#region Cmdlet Overrides
|
||||
/// <summary>
|
||||
/// BeginProcessing method.
|
||||
/// </summary>
|
||||
protected override void BeginProcessing()
|
||||
{
|
||||
sam = new Sam();
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// ProcessRecord method.
|
||||
/// </summary>
|
||||
protected override void ProcessRecord()
|
||||
{
|
||||
if (Name == null && SID == null)
|
||||
{
|
||||
foreach (var user in sam.GetAllLocalUsers())
|
||||
WriteObject(user);
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
ProcessNames();
|
||||
ProcessSids();
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// EndProcessing method.
|
||||
/// </summary>
|
||||
protected override void EndProcessing()
|
||||
{
|
||||
if (sam != null)
|
||||
{
|
||||
sam.Dispose();
|
||||
sam = null;
|
||||
}
|
||||
}
|
||||
#endregion Cmdlet Overrides
|
||||
|
||||
#region Private Methods
|
||||
/// <summary>
|
||||
/// Process users requested by -Name
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// All arguments to -Name will be treated as names,
|
||||
/// even if a name looks like a SID.
|
||||
/// Users may be specified using wildcards.
|
||||
/// </remarks>
|
||||
private void ProcessNames()
|
||||
{
|
||||
if (Name != null)
|
||||
{
|
||||
foreach (var nm in Name)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (WildcardPattern.ContainsWildcardCharacters(nm))
|
||||
{
|
||||
var pattern = new WildcardPattern(nm, WildcardOptions.Compiled
|
||||
| WildcardOptions.IgnoreCase);
|
||||
|
||||
foreach (var user in sam.GetMatchingLocalUsers(n => pattern.IsMatch(n)))
|
||||
WriteObject(user);
|
||||
}
|
||||
else
|
||||
{
|
||||
WriteObject(sam.GetLocalUser(nm));
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process users requested by -SID
|
||||
/// </summary>
|
||||
private void ProcessSids()
|
||||
{
|
||||
if (SID != null)
|
||||
{
|
||||
foreach (var s in SID)
|
||||
{
|
||||
try
|
||||
{
|
||||
WriteObject(sam.GetLocalUser(s));
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
#endregion Private Methods
|
||||
}//End Class
|
||||
|
||||
}//End namespace
|
||||
|
|
@ -0,0 +1,120 @@
|
|||
#region Using directives
|
||||
using System;
|
||||
using System.Management.Automation;
|
||||
|
||||
using System.Management.Automation.SecurityAccountsManager;
|
||||
using System.Management.Automation.SecurityAccountsManager.Extensions;
|
||||
|
||||
using Microsoft.PowerShell.LocalAccounts;
|
||||
#endregion
|
||||
|
||||
|
||||
namespace Microsoft.PowerShell.Commands
|
||||
{
|
||||
/// <summary>
|
||||
/// The New-LocalGroup Cmdlet can be used to create a new local security group
|
||||
/// in the Windows Security Accounts Manager.
|
||||
/// </summary>
|
||||
[Cmdlet(VerbsCommon.New, "LocalGroup",
|
||||
SupportsShouldProcess = true,
|
||||
HelpUri ="http://go.microsoft.com/fwlink/?LinkId=717990")]
|
||||
[Alias("nlg")]
|
||||
public class NewLocalGroupCommand : Cmdlet
|
||||
{
|
||||
#region Instance Data
|
||||
private Sam sam = null;
|
||||
#endregion Instance Data
|
||||
|
||||
#region Parameter Properties
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Description".
|
||||
/// A descriptive comment (48 characters).
|
||||
/// </summary>
|
||||
[Parameter(ValueFromPipelineByPropertyName = true)]
|
||||
[ValidateNotNull]
|
||||
[ValidateLength(0, 48)]
|
||||
public string Description
|
||||
{
|
||||
get { return this.description;}
|
||||
set { this.description = value; }
|
||||
}
|
||||
private string description;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Name".
|
||||
/// The group name for the local security group.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true)]
|
||||
[ValidateNotNullOrEmpty]
|
||||
[ValidateLength(1, 256)]
|
||||
public string Name
|
||||
{
|
||||
get { return this.name;}
|
||||
set { this.name = value; }
|
||||
}
|
||||
private string name;
|
||||
#endregion Parameter Properties
|
||||
|
||||
|
||||
|
||||
#region Cmdlet Overrides
|
||||
/// <summary>
|
||||
/// BeginProcessing method.
|
||||
/// </summary>
|
||||
protected override void BeginProcessing()
|
||||
{
|
||||
sam = new Sam();
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// ProcessRecord method.
|
||||
/// </summary>
|
||||
protected override void ProcessRecord()
|
||||
{
|
||||
try
|
||||
{
|
||||
if (CheckShouldProcess(Name))
|
||||
{
|
||||
var group = sam.CreateLocalGroup(new LocalGroup
|
||||
{
|
||||
Description = Description,
|
||||
Name = Name
|
||||
});
|
||||
|
||||
WriteObject(group);
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// EndProcessing method.
|
||||
/// </summary>
|
||||
protected override void EndProcessing()
|
||||
{
|
||||
if (sam != null)
|
||||
{
|
||||
sam.Dispose();
|
||||
sam = null;
|
||||
}
|
||||
}
|
||||
#endregion Cmdlet Overrides
|
||||
|
||||
#region Private Methods
|
||||
private bool CheckShouldProcess(string target)
|
||||
{
|
||||
return ShouldProcess(target, Strings.ActionNewGroup);
|
||||
}
|
||||
#endregion Private Methods
|
||||
}//End Class
|
||||
|
||||
}//End namespace
|
||||
|
|
@ -0,0 +1,277 @@
|
|||
#region Using directives
|
||||
using System;
|
||||
using System.Management.Automation;
|
||||
|
||||
using System.Management.Automation.SecurityAccountsManager;
|
||||
using System.Management.Automation.SecurityAccountsManager.Extensions;
|
||||
|
||||
using Microsoft.PowerShell.LocalAccounts;
|
||||
#endregion
|
||||
|
||||
|
||||
namespace Microsoft.PowerShell.Commands
|
||||
{
|
||||
/// <summary>
|
||||
/// The New-LocalUser cmdlet creates a new local user account.
|
||||
/// </summary>
|
||||
[Cmdlet(VerbsCommon.New, "LocalUser",
|
||||
DefaultParameterSetName = "Password",
|
||||
SupportsShouldProcess = true,
|
||||
HelpUri = "http://go.microsoft.com/fwlink/?LinkId=717981")]
|
||||
[Alias("nlu")]
|
||||
public class NewLocalUserCommand : PSCmdlet
|
||||
{
|
||||
#region Static Data
|
||||
// Names of object- and boolean-type parameters.
|
||||
// Switch parameters don't need to be included.
|
||||
private static string[] parameterNames = new string[]
|
||||
{
|
||||
"AccountExpires",
|
||||
"Description",
|
||||
"Disabled",
|
||||
"FullName",
|
||||
"Password",
|
||||
"UserMayNotChangePassword"
|
||||
};
|
||||
#endregion Static Data
|
||||
|
||||
#region Instance Data
|
||||
private Sam sam = null;
|
||||
#endregion Instance Data
|
||||
|
||||
#region Parameter Properties
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "AccountExpires".
|
||||
/// Specifies when the user account will expire.
|
||||
/// </summary>
|
||||
[Parameter(ValueFromPipelineByPropertyName = true)]
|
||||
public System.DateTime AccountExpires
|
||||
{
|
||||
get { return this.accountexpires;}
|
||||
set { this.accountexpires = value; }
|
||||
}
|
||||
private System.DateTime accountexpires;
|
||||
|
||||
// This parameter added by hand (copied from SetLocalUserCommand), not by Cmdlet Designer
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "AccountNeverExpires".
|
||||
/// Specifies that the account will not expire.
|
||||
/// </summary>
|
||||
[Parameter(ValueFromPipelineByPropertyName = true)]
|
||||
public System.Management.Automation.SwitchParameter AccountNeverExpires
|
||||
{
|
||||
get { return this.accountneverexpires;}
|
||||
set { this.accountneverexpires = value; }
|
||||
}
|
||||
private System.Management.Automation.SwitchParameter accountneverexpires;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Description".
|
||||
/// A descriptive comment for this user account (48 characters).
|
||||
/// </summary>
|
||||
[Parameter(ValueFromPipelineByPropertyName = true)]
|
||||
[ValidateNotNull]
|
||||
[ValidateLength(0, 48)]
|
||||
public string Description
|
||||
{
|
||||
get { return this.description;}
|
||||
set { this.description = value; }
|
||||
}
|
||||
private string description;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Disabled".
|
||||
/// Specifies whether this user account is enabled or disabled.
|
||||
/// </summary>
|
||||
[Parameter(ValueFromPipelineByPropertyName = true)]
|
||||
public System.Management.Automation.SwitchParameter Disabled
|
||||
{
|
||||
get { return this.disabled;}
|
||||
set { this.disabled = value; }
|
||||
}
|
||||
private System.Management.Automation.SwitchParameter disabled;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "FullName".
|
||||
/// Specifies the full name of the user account. This is different from the
|
||||
/// username of the user account.
|
||||
/// </summary>
|
||||
[Parameter(ValueFromPipelineByPropertyName = true)]
|
||||
[ValidateNotNull]
|
||||
public string FullName
|
||||
{
|
||||
get { return this.fullname;}
|
||||
set { this.fullname = value; }
|
||||
}
|
||||
private string fullname;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Name".
|
||||
/// Specifies the user name for the local user account. This can be a local user
|
||||
/// account or a local user account that is connected to a Microsoft Account.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true)]
|
||||
[ValidateNotNullOrEmpty]
|
||||
[ValidateLength(1, 20)]
|
||||
public string Name
|
||||
{
|
||||
get { return this.name;}
|
||||
set { this.name = value; }
|
||||
}
|
||||
private string name;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Password".
|
||||
/// Specifies the password for the local user account. A password can contain up
|
||||
/// to 127 characters.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
ParameterSetName = "Password",
|
||||
ValueFromPipelineByPropertyName = true)]
|
||||
[ValidateNotNull]
|
||||
public System.Security.SecureString Password
|
||||
{
|
||||
get { return this.password;}
|
||||
set { this.password = value; }
|
||||
}
|
||||
private System.Security.SecureString password;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "PasswordChangeableDate".
|
||||
/// Specifies that the new User account has no password.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
ParameterSetName = "NoPassword",
|
||||
ValueFromPipelineByPropertyName = true)]
|
||||
public System.Management.Automation.SwitchParameter NoPassword
|
||||
{
|
||||
get { return this.nopassword; }
|
||||
set { this.nopassword = value; }
|
||||
}
|
||||
private System.Management.Automation.SwitchParameter nopassword;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "PasswordNeverExpires".
|
||||
/// Specifies that the password will not expire.
|
||||
/// </summary>
|
||||
[Parameter(ParameterSetName = "Password",
|
||||
ValueFromPipelineByPropertyName = true)]
|
||||
public System.Management.Automation.SwitchParameter PasswordNeverExpires
|
||||
{
|
||||
get { return this.passwordneverexpires; }
|
||||
set { this.passwordneverexpires = value; }
|
||||
}
|
||||
private System.Management.Automation.SwitchParameter passwordneverexpires;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "UserMayNotChangePassword".
|
||||
/// Specifies whether the user is allowed to change the password on this
|
||||
/// account. The default value is True.
|
||||
/// </summary>
|
||||
[Parameter(ValueFromPipelineByPropertyName = true)]
|
||||
public System.Management.Automation.SwitchParameter UserMayNotChangePassword
|
||||
{
|
||||
get { return this.usermaynotchangepassword;}
|
||||
set { this.usermaynotchangepassword = value; }
|
||||
}
|
||||
private System.Management.Automation.SwitchParameter usermaynotchangepassword;
|
||||
#endregion Parameter Properties
|
||||
|
||||
|
||||
|
||||
#region Cmdlet Overrides
|
||||
/// <summary>
|
||||
/// BeginProcessing method.
|
||||
/// </summary>
|
||||
protected override void BeginProcessing()
|
||||
{
|
||||
if (this.HasParameter("AccountExpires") && AccountNeverExpires.IsPresent)
|
||||
{
|
||||
InvalidParametersException ex = new InvalidParametersException("AccountExpires", "AccountNeverExpires");
|
||||
ThrowTerminatingError(ex.MakeErrorRecord());
|
||||
}
|
||||
sam = new Sam();
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// ProcessRecord method.
|
||||
/// </summary>
|
||||
protected override void ProcessRecord()
|
||||
{
|
||||
try
|
||||
{
|
||||
if (CheckShouldProcess(Name))
|
||||
{
|
||||
var user = new LocalUser
|
||||
{
|
||||
Name = Name,
|
||||
Description = Description,
|
||||
Enabled = true,
|
||||
FullName = FullName,
|
||||
UserMayChangePassword = true
|
||||
};
|
||||
|
||||
foreach (var paramName in parameterNames)
|
||||
{
|
||||
if (this.HasParameter(paramName))
|
||||
{
|
||||
switch (paramName)
|
||||
{
|
||||
case "AccountExpires":
|
||||
user.AccountExpires = AccountExpires;
|
||||
break;
|
||||
|
||||
case "Disabled":
|
||||
user.Enabled = !Disabled;
|
||||
break;
|
||||
|
||||
case "UserMayNotChangePassword":
|
||||
user.UserMayChangePassword = !UserMayNotChangePassword;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (AccountNeverExpires.IsPresent)
|
||||
user.AccountExpires = null;
|
||||
|
||||
// Password will be null if NoPassword was given
|
||||
user = sam.CreateLocalUser(user, Password, PasswordNeverExpires.IsPresent);
|
||||
|
||||
WriteObject(user);
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// EndProcessing method.
|
||||
/// </summary>
|
||||
protected override void EndProcessing()
|
||||
{
|
||||
if (sam != null)
|
||||
{
|
||||
sam.Dispose();
|
||||
sam = null;
|
||||
}
|
||||
}
|
||||
#endregion Cmdlet Overrides
|
||||
|
||||
#region Private Methods
|
||||
private bool CheckShouldProcess(string target)
|
||||
{
|
||||
return ShouldProcess(target, Strings.ActionNewUser);
|
||||
}
|
||||
#endregion Private Methods
|
||||
}//End Class
|
||||
|
||||
}//End namespace
|
||||
|
|
@ -0,0 +1,208 @@
|
|||
#region Using directives
|
||||
using System;
|
||||
using System.Management.Automation;
|
||||
|
||||
using System.Management.Automation.SecurityAccountsManager;
|
||||
using System.Management.Automation.SecurityAccountsManager.Extensions;
|
||||
|
||||
using Microsoft.PowerShell.LocalAccounts;
|
||||
using System.Diagnostics.CodeAnalysis;
|
||||
#endregion
|
||||
|
||||
|
||||
namespace Microsoft.PowerShell.Commands
|
||||
{
|
||||
/// <summary>
|
||||
/// The Remove-LocalGroup cmdlet deletes a security group from the Windows
|
||||
/// Security Accounts manager.
|
||||
/// </summary>
|
||||
[Cmdlet(VerbsCommon.Remove, "LocalGroup",
|
||||
SupportsShouldProcess = true,
|
||||
HelpUri = "http://go.microsoft.com/fwlink/?LinkId=717975")]
|
||||
[Alias("rlg")]
|
||||
public class RemoveLocalGroupCommand : Cmdlet
|
||||
{
|
||||
#region Instance Data
|
||||
private Sam sam = null;
|
||||
#endregion Instance Data
|
||||
|
||||
#region Parameter Properties
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "InputObject".
|
||||
/// Specifies security groups from the local Security Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "InputObject")]
|
||||
[ValidateNotNullOrEmpty]
|
||||
[SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays")]
|
||||
public Microsoft.PowerShell.Commands.LocalGroup[] InputObject
|
||||
{
|
||||
get { return this.inputobject; }
|
||||
set { this.inputobject = value; }
|
||||
}
|
||||
private Microsoft.PowerShell.Commands.LocalGroup[] inputobject;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Name".
|
||||
/// Specifies the local groups to be deleted from the local Security Accounts
|
||||
/// Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "Default")]
|
||||
[ValidateNotNullOrEmpty]
|
||||
[SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays")]
|
||||
public string[] Name
|
||||
{
|
||||
get { return this.name; }
|
||||
set { this.name = value; }
|
||||
}
|
||||
private string[] name;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "SID".
|
||||
/// Specifies the LocalGroup accounts to remove by
|
||||
/// System.Security.Principal.SecurityIdentifier.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "SecurityIdentifier")]
|
||||
[ValidateNotNullOrEmpty]
|
||||
[SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays")]
|
||||
public System.Security.Principal.SecurityIdentifier[] SID
|
||||
{
|
||||
get { return this.sid; }
|
||||
set { this.sid = value; }
|
||||
}
|
||||
private System.Security.Principal.SecurityIdentifier[] sid;
|
||||
#endregion Parameter Properties
|
||||
|
||||
|
||||
#region Cmdlet Overrides
|
||||
/// <summary>
|
||||
/// BeginProcessing method.
|
||||
/// </summary>
|
||||
protected override void BeginProcessing()
|
||||
{
|
||||
sam = new Sam();
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// ProcessRecord method.
|
||||
/// </summary>
|
||||
protected override void ProcessRecord()
|
||||
{
|
||||
try
|
||||
{
|
||||
ProcessGroups();
|
||||
ProcessNames();
|
||||
ProcessSids();
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// EndProcessing method.
|
||||
/// </summary>
|
||||
protected override void EndProcessing()
|
||||
{
|
||||
if (sam != null)
|
||||
{
|
||||
sam.Dispose();
|
||||
sam = null;
|
||||
}
|
||||
}
|
||||
#endregion Cmdlet Overrides
|
||||
|
||||
#region Private Methods
|
||||
/// <summary>
|
||||
/// Process groups requested by -Name
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// All arguments to -Name will be treated as names,
|
||||
/// even if a name looks like a SID.
|
||||
/// </remarks>
|
||||
private void ProcessNames()
|
||||
{
|
||||
if (Name != null)
|
||||
{
|
||||
foreach (var name in Name)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (CheckShouldProcess(name))
|
||||
sam.RemoveLocalGroup(sam.GetLocalGroup(name));
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process groups requested by -SID
|
||||
/// </summary>
|
||||
private void ProcessSids()
|
||||
{
|
||||
if (SID != null)
|
||||
{
|
||||
foreach (var sid in SID)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (CheckShouldProcess(sid.ToString()))
|
||||
sam.RemoveLocalGroup(sid);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process groups given through -InputObject
|
||||
/// </summary>
|
||||
private void ProcessGroups()
|
||||
{
|
||||
if (InputObject != null)
|
||||
{
|
||||
foreach (var group in InputObject)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (CheckShouldProcess(group.Name))
|
||||
sam.RemoveLocalGroup(group);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private bool CheckShouldProcess(string target)
|
||||
{
|
||||
return ShouldProcess(target, Strings.ActionRemoveGroup);
|
||||
}
|
||||
#endregion Private Methods
|
||||
}//End Class
|
||||
|
||||
}//End namespace
|
||||
|
|
@ -0,0 +1,295 @@
|
|||
#region Using directives
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Management.Automation;
|
||||
using System.Security.Principal;
|
||||
|
||||
using System.Management.Automation.SecurityAccountsManager;
|
||||
using System.Management.Automation.SecurityAccountsManager.Extensions;
|
||||
|
||||
using Microsoft.PowerShell.LocalAccounts;
|
||||
using System.Diagnostics.CodeAnalysis;
|
||||
#endregion
|
||||
|
||||
|
||||
namespace Microsoft.PowerShell.Commands
|
||||
{
|
||||
/// <summary>
|
||||
/// The Remove-LocalGroupMember cmdlet removes one or more members (users or
|
||||
/// groups) from a local security group.
|
||||
/// </summary>
|
||||
[Cmdlet(VerbsCommon.Remove, "LocalGroupMember",
|
||||
SupportsShouldProcess = true,
|
||||
HelpUri = "http://go.microsoft.com/fwlink/?LinkId=717989")]
|
||||
[Alias("rlgm")]
|
||||
public class RemoveLocalGroupMemberCommand : PSCmdlet
|
||||
{
|
||||
#region Instance Data
|
||||
private Sam sam = null;
|
||||
#endregion Instance Data
|
||||
|
||||
#region Parameter Properties
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Group".
|
||||
/// Specifies a security group from the local Security Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ParameterSetName = "Group")]
|
||||
[ValidateNotNull]
|
||||
public Microsoft.PowerShell.Commands.LocalGroup Group
|
||||
{
|
||||
get { return this.group;}
|
||||
set { this.group = value; }
|
||||
}
|
||||
private Microsoft.PowerShell.Commands.LocalGroup group;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Member".
|
||||
/// Specifies one or more users or groups to remove from this local group. You can
|
||||
/// identify users or groups by specifying their names or SIDs, or by passing
|
||||
/// Microsoft.PowerShell.Commands.LocalPrincipal objects.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 1,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true)]
|
||||
[ValidateNotNullOrEmpty]
|
||||
[SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays")]
|
||||
public Microsoft.PowerShell.Commands.LocalPrincipal[] Member
|
||||
{
|
||||
get { return this.member;}
|
||||
set { this.member = value; }
|
||||
}
|
||||
private Microsoft.PowerShell.Commands.LocalPrincipal[] member;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Name".
|
||||
/// The security group from the local Security Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ParameterSetName = "Default")]
|
||||
[ValidateNotNullOrEmpty]
|
||||
public string Name
|
||||
{
|
||||
get { return this.name;}
|
||||
set { this.name = value; }
|
||||
}
|
||||
private string name;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "SID".
|
||||
/// Specifies a security group from the local Security Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ParameterSetName = "SecurityIdentifier")]
|
||||
[ValidateNotNull]
|
||||
public System.Security.Principal.SecurityIdentifier SID
|
||||
{
|
||||
get { return this.sid;}
|
||||
set { this.sid = value; }
|
||||
}
|
||||
private System.Security.Principal.SecurityIdentifier sid;
|
||||
#endregion Parameter Properties
|
||||
|
||||
|
||||
#region Cmdlet Overrides
|
||||
/// <summary>
|
||||
/// BeginProcessing method.
|
||||
/// </summary>
|
||||
protected override void BeginProcessing()
|
||||
{
|
||||
sam = new Sam();
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// ProcessRecord method.
|
||||
/// </summary>
|
||||
protected override void ProcessRecord()
|
||||
{
|
||||
try
|
||||
{
|
||||
if (Group != null)
|
||||
ProcessGroup(Group);
|
||||
else if (Name != null)
|
||||
ProcessName(Name);
|
||||
else if (SID != null)
|
||||
ProcessSid(SID);
|
||||
}
|
||||
catch (GroupNotFoundException ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// EndProcessing method.
|
||||
/// </summary>
|
||||
protected override void EndProcessing()
|
||||
{
|
||||
if (sam != null)
|
||||
{
|
||||
sam.Dispose();
|
||||
sam = null;
|
||||
}
|
||||
}
|
||||
#endregion Cmdlet Overrides
|
||||
|
||||
#region Private Methods
|
||||
|
||||
/// <summary>
|
||||
/// Creates a list of <see cref="LocalPrincipal"/> objects
|
||||
/// ready to be processed by the cmdlet.
|
||||
/// </summary>
|
||||
/// <param name="groupId">
|
||||
/// Name or SID (as a string) of the group we'll be removing from.
|
||||
/// This string is used primarily for specifying the target
|
||||
/// in WhatIf scenarios.
|
||||
/// </param>
|
||||
/// <param name="member">
|
||||
/// LocalPrincipal object to be processed
|
||||
/// </param>
|
||||
/// <returns>
|
||||
/// LocalPrincipal object processed and ready to be removed
|
||||
/// </returns>
|
||||
/// <remarks>
|
||||
/// <para>
|
||||
/// LocalPrincipal object in the Member parameter may not be complete,
|
||||
/// particularly those created from a name or a SID string given to the
|
||||
/// Member cmdlet parameter. The object returned from this method contains at the very least, contain a valid SID.
|
||||
/// </para>
|
||||
/// <para>
|
||||
/// Any Member object provided by name or SID string will be looked up
|
||||
/// to ensure that such an object exists. If an object is not found,
|
||||
/// an error message is displayed by PowerShell and null will be returned from this method
|
||||
/// </para>
|
||||
/// <para>
|
||||
/// This method also handles the WhatIf scenario. If the Cmdlet's
|
||||
/// <b>ShouldProcess</b> method returns false on any Member object
|
||||
/// </para>
|
||||
/// </remarks>
|
||||
private LocalPrincipal MakePrincipal(string groupId, LocalPrincipal member)
|
||||
{
|
||||
LocalPrincipal principal = null;
|
||||
|
||||
// if the member has a SID, we can use it directly
|
||||
if (member.SID != null)
|
||||
{
|
||||
principal = member;
|
||||
}
|
||||
else // otherwise it must have been constructed by name
|
||||
{
|
||||
SecurityIdentifier sid = this.TrySid(member.Name);
|
||||
|
||||
if (sid != null)
|
||||
{
|
||||
member.SID = sid;
|
||||
principal = member;
|
||||
}
|
||||
else
|
||||
{
|
||||
try
|
||||
{
|
||||
principal = sam.LookupAccount(member.Name);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (CheckShouldProcess(principal, groupId))
|
||||
return principal;
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Determine if a principal should be processed.
|
||||
/// Just a wrapper around Cmdlet.ShouldProcess, with localized string
|
||||
/// formatting.
|
||||
/// </summary>
|
||||
/// <param name="principal">Name of the principal to be removed.</param>
|
||||
/// <param name="groupName">
|
||||
/// Name of the group from which the members will be removed.
|
||||
/// </param>
|
||||
/// <returns>
|
||||
/// True if the principal should be processed, false otherwise.
|
||||
/// </returns>
|
||||
private bool CheckShouldProcess(LocalPrincipal principal, string groupName)
|
||||
{
|
||||
if (principal == null)
|
||||
return false;
|
||||
|
||||
string msg = StringUtil.Format(Strings.ActionRemoveGroupMember, principal.ToString());
|
||||
|
||||
return ShouldProcess(groupName, msg);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Remove members from a group.
|
||||
/// </summary>
|
||||
/// <param name="group">
|
||||
/// A <see cref="LocalGroup"/> object representing the group from which
|
||||
/// the members will be removed.
|
||||
/// </param>
|
||||
private void ProcessGroup(LocalGroup group)
|
||||
{
|
||||
string groupId = group.Name ?? group.SID.ToString();
|
||||
foreach (var member in this.Member)
|
||||
{
|
||||
LocalPrincipal principal = MakePrincipal(groupId, member);
|
||||
if (null != principal)
|
||||
{
|
||||
var ex = sam.RemoveLocalGroupMember(group, principal);
|
||||
if (null != ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Remove members from a group specified by name.
|
||||
/// </summary>
|
||||
/// <param name="name">
|
||||
/// The name of the group from which the members will be removed.
|
||||
/// </param>
|
||||
private void ProcessName(string name)
|
||||
{
|
||||
ProcessGroup(sam.GetLocalGroup(name));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Remove members from a group specified by SID.
|
||||
/// </summary>
|
||||
/// <param name="groupSid">
|
||||
/// A <see cref="SecurityIdentifier"/> object identifying the group
|
||||
/// from which the members will be removed.
|
||||
/// </param>
|
||||
private void ProcessSid(SecurityIdentifier groupSid)
|
||||
{
|
||||
foreach (var member in this.Member)
|
||||
{
|
||||
LocalPrincipal principal = MakePrincipal(groupSid.ToString(), member);
|
||||
if (null != principal)
|
||||
{
|
||||
var ex = sam.RemoveLocalGroupMember(groupSid, principal);
|
||||
if (null != ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
#endregion Private Methods
|
||||
}//End Class
|
||||
|
||||
}//End namespace
|
||||
|
|
@ -0,0 +1,210 @@
|
|||
#region Using directives
|
||||
using System;
|
||||
using System.Management.Automation;
|
||||
|
||||
using System.Management.Automation.SecurityAccountsManager;
|
||||
using System.Management.Automation.SecurityAccountsManager.Extensions;
|
||||
|
||||
using Microsoft.PowerShell.LocalAccounts;
|
||||
using System.Diagnostics.CodeAnalysis;
|
||||
#endregion
|
||||
|
||||
|
||||
namespace Microsoft.PowerShell.Commands
|
||||
{
|
||||
/// <summary>
|
||||
/// The Remove-LocalUser cmdlet deletes a user account from the Windows Security
|
||||
/// Accounts manager.
|
||||
/// </summary>
|
||||
[Cmdlet(VerbsCommon.Remove, "LocalUser",
|
||||
SupportsShouldProcess = true,
|
||||
HelpUri = "http://go.microsoft.com/fwlink/?LinkId=717982")]
|
||||
[Alias("rlu")]
|
||||
public class RemoveLocalUserCommand : Cmdlet
|
||||
{
|
||||
#region Instance Data
|
||||
private Sam sam = null;
|
||||
#endregion Instance Data
|
||||
|
||||
#region Parameter Properties
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "InputObject".
|
||||
/// Specifies the of the local user accounts to remove in the local Security
|
||||
/// Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "InputObject")]
|
||||
[ValidateNotNullOrEmpty]
|
||||
[SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays")]
|
||||
public Microsoft.PowerShell.Commands.LocalUser[] InputObject
|
||||
{
|
||||
get { return this.inputobject;}
|
||||
set { this.inputobject = value; }
|
||||
}
|
||||
private Microsoft.PowerShell.Commands.LocalUser[] inputobject;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Name".
|
||||
/// Specifies the user accounts to be deleted from the local Security Accounts
|
||||
/// Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "Default")]
|
||||
[ValidateNotNullOrEmpty]
|
||||
[SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays")]
|
||||
public string[] Name
|
||||
{
|
||||
get { return this.name; }
|
||||
set { this.name = value; }
|
||||
}
|
||||
private string[] name;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "SID".
|
||||
/// Specifies the local user accounts to remove by
|
||||
/// System.Security.Principal.SecurityIdentifier.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "SecurityIdentifier")]
|
||||
[ValidateNotNullOrEmpty]
|
||||
[SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays")]
|
||||
public System.Security.Principal.SecurityIdentifier[] SID
|
||||
{
|
||||
get { return this.sid; }
|
||||
set { this.sid = value; }
|
||||
}
|
||||
private System.Security.Principal.SecurityIdentifier[] sid;
|
||||
#endregion Parameter Properties
|
||||
|
||||
|
||||
|
||||
#region Cmdlet Overrides
|
||||
/// <summary>
|
||||
/// BeginProcessing method.
|
||||
/// </summary>
|
||||
protected override void BeginProcessing()
|
||||
{
|
||||
sam = new Sam();
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// ProcessRecord method.
|
||||
/// </summary>
|
||||
protected override void ProcessRecord()
|
||||
{
|
||||
try
|
||||
{
|
||||
ProcessUsers();
|
||||
ProcessNames();
|
||||
ProcessSids();
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// EndProcessing method.
|
||||
/// </summary>
|
||||
protected override void EndProcessing()
|
||||
{
|
||||
if (sam != null)
|
||||
{
|
||||
sam.Dispose();
|
||||
sam = null;
|
||||
}
|
||||
}
|
||||
#endregion Cmdlet Overrides
|
||||
|
||||
#region Private Methods
|
||||
/// <summary>
|
||||
/// Process users requested by -Name
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// All arguments to -Name will be treated as names,
|
||||
/// even if a name looks like a SID.
|
||||
/// </remarks>
|
||||
private void ProcessNames()
|
||||
{
|
||||
if (Name != null)
|
||||
{
|
||||
foreach (var name in Name)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (CheckShouldProcess(name))
|
||||
sam.RemoveLocalUser(sam.GetLocalUser(name));
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process users requested by -SID
|
||||
/// </summary>
|
||||
private void ProcessSids()
|
||||
{
|
||||
if (SID != null)
|
||||
{
|
||||
foreach (var sid in SID)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (CheckShouldProcess(sid.ToString()))
|
||||
sam.RemoveLocalUser(sid);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process users given through -InputObject
|
||||
/// </summary>
|
||||
private void ProcessUsers()
|
||||
{
|
||||
if (InputObject != null)
|
||||
{
|
||||
foreach (var user in InputObject)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (CheckShouldProcess(user.Name))
|
||||
sam.RemoveLocalUser(user);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private bool CheckShouldProcess(string target)
|
||||
{
|
||||
return ShouldProcess(target, Strings.ActionRemoveUser);
|
||||
}
|
||||
#endregion Private Methods
|
||||
}//End Class
|
||||
|
||||
}//End namespace
|
||||
|
|
@ -0,0 +1,226 @@
|
|||
#region Using directives
|
||||
using System;
|
||||
using System.Management.Automation;
|
||||
|
||||
using System.Management.Automation.SecurityAccountsManager;
|
||||
using System.Management.Automation.SecurityAccountsManager.Extensions;
|
||||
|
||||
using Microsoft.PowerShell.LocalAccounts;
|
||||
#endregion
|
||||
|
||||
|
||||
namespace Microsoft.PowerShell.Commands
|
||||
{
|
||||
/// <summary>
|
||||
/// The Rename-LocalGroup cmdlet renames a local security group in the Security
|
||||
/// Accounts Manager.
|
||||
/// </summary>
|
||||
[Cmdlet(VerbsCommon.Rename, "LocalGroup",
|
||||
SupportsShouldProcess = true,
|
||||
HelpUri = "http://go.microsoft.com/fwlink/?LinkId=717978")]
|
||||
[Alias("rnlg")]
|
||||
public class RenameLocalGroupCommand : Cmdlet
|
||||
{
|
||||
#region Instance Data
|
||||
private Sam sam = null;
|
||||
#endregion Instance Data
|
||||
|
||||
#region Parameter Properties
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "InputObject".
|
||||
/// Specifies the of the local group account to rename in the local Security
|
||||
/// Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "InputObject")]
|
||||
[ValidateNotNullOrEmpty]
|
||||
public Microsoft.PowerShell.Commands.LocalGroup InputObject
|
||||
{
|
||||
get { return this.inputobject;}
|
||||
set { this.inputobject = value; }
|
||||
}
|
||||
private Microsoft.PowerShell.Commands.LocalGroup inputobject;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Name".
|
||||
/// Specifies the local group to be renamed in the local Security Accounts
|
||||
/// Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "Default")]
|
||||
[ValidateNotNullOrEmpty]
|
||||
public string Name
|
||||
{
|
||||
get { return this.name;}
|
||||
set { this.name = value; }
|
||||
}
|
||||
private string name;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "NewName".
|
||||
/// Specifies the new name for the local security group in the Security Accounts
|
||||
/// Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 1)]
|
||||
[ValidateNotNullOrEmpty]
|
||||
public string NewName
|
||||
{
|
||||
get { return this.newname;}
|
||||
set { this.newname = value; }
|
||||
}
|
||||
private string newname;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "SID".
|
||||
/// Specifies a security group from the local Security Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "SecurityIdentifier")]
|
||||
[ValidateNotNullOrEmpty]
|
||||
public System.Security.Principal.SecurityIdentifier SID
|
||||
{
|
||||
get { return this.sid;}
|
||||
set { this.sid = value; }
|
||||
}
|
||||
private System.Security.Principal.SecurityIdentifier sid;
|
||||
#endregion Parameter Properties
|
||||
|
||||
|
||||
#region Cmdlet Overrides
|
||||
/// <summary>
|
||||
/// BeginProcessing method.
|
||||
/// </summary>
|
||||
protected override void BeginProcessing()
|
||||
{
|
||||
sam = new Sam();
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// ProcessRecord method.
|
||||
/// </summary>
|
||||
protected override void ProcessRecord()
|
||||
{
|
||||
try
|
||||
{
|
||||
ProcessGroup();
|
||||
ProcessName();
|
||||
ProcessSid();
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// EndProcessing method.
|
||||
/// </summary>
|
||||
protected override void EndProcessing()
|
||||
{
|
||||
if (sam != null)
|
||||
{
|
||||
sam.Dispose();
|
||||
sam = null;
|
||||
}
|
||||
}
|
||||
#endregion Cmdlet Overrides
|
||||
|
||||
#region Private Methods
|
||||
/// <summary>
|
||||
/// Process group requested by -Name
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// Arguments to -Name will be treated as names,
|
||||
/// even if a name looks like a SID.
|
||||
/// </remarks>
|
||||
private void ProcessName()
|
||||
{
|
||||
if (Name != null)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (CheckShouldProcess(Name, NewName))
|
||||
sam.RenameLocalGroup(sam.GetLocalGroup(Name), NewName);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process group requested by -SID
|
||||
/// </summary>
|
||||
private void ProcessSid()
|
||||
{
|
||||
if (SID != null)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (CheckShouldProcess(SID.ToString(), NewName))
|
||||
sam.RenameLocalGroup(SID, NewName);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process group given through -InputObject
|
||||
/// </summary>
|
||||
private void ProcessGroup()
|
||||
{
|
||||
if (InputObject != null)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (CheckShouldProcess(InputObject.Name, NewName))
|
||||
sam.RenameLocalGroup(InputObject, NewName);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Determine if a group should be processed.
|
||||
/// Just a wrapper around Cmdlet.ShouldProcess, with localized string
|
||||
/// formatting.
|
||||
/// </summary>
|
||||
/// <param name="groupName">
|
||||
/// Name of the group to rename.
|
||||
/// </param>
|
||||
/// <param name="newName">
|
||||
/// New name for the group.
|
||||
/// </param>
|
||||
/// <returns>
|
||||
/// True if the group should be processed, false otherwise.
|
||||
/// </returns>
|
||||
private bool CheckShouldProcess(string groupName, string newName)
|
||||
{
|
||||
string msg = StringUtil.Format(Strings.ActionRenameGroup, newName);
|
||||
|
||||
return ShouldProcess(groupName, msg);
|
||||
}
|
||||
#endregion Private Methods
|
||||
}//End Class
|
||||
|
||||
}//End namespace
|
||||
|
|
@ -0,0 +1,227 @@
|
|||
#region Using directives
|
||||
using System;
|
||||
using System.Management.Automation;
|
||||
|
||||
using System.Management.Automation.SecurityAccountsManager;
|
||||
using System.Management.Automation.SecurityAccountsManager.Extensions;
|
||||
|
||||
using Microsoft.PowerShell.LocalAccounts;
|
||||
#endregion
|
||||
|
||||
|
||||
namespace Microsoft.PowerShell.Commands
|
||||
{
|
||||
/// <summary>
|
||||
/// The Rename-LocalUser cmdlet renames a local user account in the Security
|
||||
/// Accounts Manager.
|
||||
/// </summary>
|
||||
[Cmdlet(VerbsCommon.Rename, "LocalUser",
|
||||
SupportsShouldProcess = true,
|
||||
HelpUri = "http://go.microsoft.com/fwlink/?LinkID=717983")]
|
||||
[Alias("rnlu")]
|
||||
public class RenameLocalUserCommand : Cmdlet
|
||||
{
|
||||
#region Instance Data
|
||||
private Sam sam = null;
|
||||
#endregion Instance Data
|
||||
|
||||
#region Parameter Properties
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "InputObject".
|
||||
/// Specifies the of the local user account to rename in the local Security
|
||||
/// Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "InputObject")]
|
||||
[ValidateNotNull]
|
||||
public Microsoft.PowerShell.Commands.LocalUser InputObject
|
||||
{
|
||||
get { return this.inputobject;}
|
||||
set { this.inputobject = value; }
|
||||
}
|
||||
private Microsoft.PowerShell.Commands.LocalUser inputobject;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Name".
|
||||
/// Specifies the local user account to be renamed in the local Security
|
||||
/// Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "Default")]
|
||||
[ValidateNotNullOrEmpty]
|
||||
public string Name
|
||||
{
|
||||
get { return this.name;}
|
||||
set { this.name = value; }
|
||||
}
|
||||
private string name;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "NewName".
|
||||
/// Specifies the new name for the local user account in the Security Accounts
|
||||
/// Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 1)]
|
||||
[ValidateNotNullOrEmpty]
|
||||
public string NewName
|
||||
{
|
||||
get { return this.newname;}
|
||||
set { this.newname = value; }
|
||||
}
|
||||
private string newname;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "SID".
|
||||
/// Specifies the local user to rename.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "SecurityIdentifier")]
|
||||
[ValidateNotNull]
|
||||
public System.Security.Principal.SecurityIdentifier SID
|
||||
{
|
||||
get { return this.sid;}
|
||||
set { this.sid = value; }
|
||||
}
|
||||
private System.Security.Principal.SecurityIdentifier sid;
|
||||
#endregion Parameter Properties
|
||||
|
||||
|
||||
|
||||
#region Cmdlet Overrides
|
||||
/// <summary>
|
||||
/// BeginProcessing method.
|
||||
/// </summary>
|
||||
protected override void BeginProcessing()
|
||||
{
|
||||
sam = new Sam();
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// ProcessRecord method.
|
||||
/// </summary>
|
||||
protected override void ProcessRecord()
|
||||
{
|
||||
try
|
||||
{
|
||||
ProcessUser();
|
||||
ProcessName();
|
||||
ProcessSid();
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// EndProcessing method.
|
||||
/// </summary>
|
||||
protected override void EndProcessing()
|
||||
{
|
||||
if (sam != null)
|
||||
{
|
||||
sam.Dispose();
|
||||
sam = null;
|
||||
}
|
||||
}
|
||||
#endregion Cmdlet Overrides
|
||||
|
||||
#region Private Methods
|
||||
/// <summary>
|
||||
/// Process user requested by -Name
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// Arguments to -Name will be treated as names,
|
||||
/// even if a name looks like a SID.
|
||||
/// </remarks>
|
||||
private void ProcessName()
|
||||
{
|
||||
if (Name != null)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (CheckShouldProcess(Name, NewName))
|
||||
sam.RenameLocalUser(sam.GetLocalUser(Name), NewName);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process user requested by -SID
|
||||
/// </summary>
|
||||
private void ProcessSid()
|
||||
{
|
||||
if (SID != null)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (CheckShouldProcess(SID.ToString(), NewName))
|
||||
sam.RenameLocalUser(SID, NewName);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Process group given through -InputObject
|
||||
/// </summary>
|
||||
private void ProcessUser()
|
||||
{
|
||||
if (InputObject != null)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (CheckShouldProcess(InputObject.Name, NewName))
|
||||
sam.RenameLocalUser(InputObject, NewName);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Determine if a user should be processed.
|
||||
/// Just a wrapper around Cmdlet.ShouldProcess, with localized string
|
||||
/// formatting.
|
||||
/// </summary>
|
||||
/// <param name="userName">
|
||||
/// Name of the user to rename.
|
||||
/// </param>
|
||||
/// <param name="newName">
|
||||
/// New name for the user.
|
||||
/// </param>
|
||||
/// <returns>
|
||||
/// True if the user should be processed, false otherwise.
|
||||
/// </returns>
|
||||
private bool CheckShouldProcess(string userName, string newName)
|
||||
{
|
||||
string msg = StringUtil.Format(Strings.ActionRenameUser, newName);
|
||||
|
||||
return ShouldProcess(userName, msg);
|
||||
}
|
||||
#endregion Private Methods
|
||||
}//End Class
|
||||
|
||||
}//End namespace
|
||||
|
|
@ -0,0 +1,175 @@
|
|||
#region Using directives
|
||||
using System;
|
||||
using System.Management.Automation;
|
||||
|
||||
using System.Management.Automation.SecurityAccountsManager;
|
||||
using System.Management.Automation.SecurityAccountsManager.Extensions;
|
||||
|
||||
using Microsoft.PowerShell.LocalAccounts;
|
||||
#endregion
|
||||
|
||||
|
||||
namespace Microsoft.PowerShell.Commands
|
||||
{
|
||||
/// <summary>
|
||||
/// The Set-LocalGroup cmdlet modifies the properties of a local security group
|
||||
/// in the Windows Security Accounts Manager.
|
||||
/// </summary>
|
||||
[Cmdlet(VerbsCommon.Set, "LocalGroup",
|
||||
SupportsShouldProcess = true,
|
||||
HelpUri = "http://go.microsoft.com/fwlink/?LinkId=717979")]
|
||||
[Alias("slg")]
|
||||
public class SetLocalGroupCommand : Cmdlet
|
||||
{
|
||||
#region Instance Data
|
||||
private Sam sam = null;
|
||||
#endregion Instance Data
|
||||
|
||||
#region Parameter Properties
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Description".
|
||||
/// A descriptive comment (48 characters).
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true)]
|
||||
[ValidateNotNull]
|
||||
[ValidateLength(0, 48)]
|
||||
public string Description
|
||||
{
|
||||
get { return this.description;}
|
||||
set { this.description = value; }
|
||||
}
|
||||
private string description;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "InputObject".
|
||||
/// Specifies the local group account to modify in the local Security
|
||||
/// Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "InputObject")]
|
||||
[ValidateNotNull]
|
||||
public Microsoft.PowerShell.Commands.LocalGroup InputObject
|
||||
{
|
||||
get { return this.inputobject;}
|
||||
set { this.inputobject = value; }
|
||||
}
|
||||
private Microsoft.PowerShell.Commands.LocalGroup inputobject;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Name".
|
||||
/// Specifies the local group to be renamed in the local Security Accounts
|
||||
/// Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "Default")]
|
||||
[ValidateNotNull]
|
||||
public string Name
|
||||
{
|
||||
get { return this.name;}
|
||||
set { this.name = value; }
|
||||
}
|
||||
private string name;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "SID".
|
||||
/// Specifies a security group from the local Security Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "SecurityIdentifier")]
|
||||
[ValidateNotNull]
|
||||
public System.Security.Principal.SecurityIdentifier SID
|
||||
{
|
||||
get { return this.sid;}
|
||||
set { this.sid = value; }
|
||||
}
|
||||
private System.Security.Principal.SecurityIdentifier sid;
|
||||
#endregion Parameter Properties
|
||||
|
||||
|
||||
|
||||
#region Cmdlet Overrides
|
||||
/// <summary>
|
||||
/// BeginProcessing method.
|
||||
/// </summary>
|
||||
protected override void BeginProcessing()
|
||||
{
|
||||
sam = new Sam();
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// ProcessRecord method.
|
||||
/// </summary>
|
||||
protected override void ProcessRecord()
|
||||
{
|
||||
try
|
||||
{
|
||||
LocalGroup group = null;
|
||||
|
||||
if (InputObject != null)
|
||||
{
|
||||
if (CheckShouldProcess(InputObject.ToString()))
|
||||
group = InputObject;
|
||||
}
|
||||
else if (Name != null)
|
||||
{
|
||||
group = sam.GetLocalGroup(Name);
|
||||
|
||||
if (!CheckShouldProcess(Name))
|
||||
group = null;
|
||||
}
|
||||
else if (SID != null)
|
||||
{
|
||||
group = sam.GetLocalGroup(SID);
|
||||
|
||||
if (!CheckShouldProcess(SID.ToString()))
|
||||
group = null;
|
||||
}
|
||||
|
||||
if (group != null)
|
||||
{
|
||||
var delta = group.Clone();
|
||||
|
||||
delta.Description = Description;
|
||||
sam.UpdateLocalGroup(group, delta);
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// EndProcessing method.
|
||||
/// </summary>
|
||||
protected override void EndProcessing()
|
||||
{
|
||||
if (sam != null)
|
||||
{
|
||||
sam.Dispose();
|
||||
sam = null;
|
||||
}
|
||||
}
|
||||
#endregion Cmdlet Overrides
|
||||
|
||||
#region Private Methods
|
||||
private bool CheckShouldProcess(string target)
|
||||
{
|
||||
return ShouldProcess(target, Strings.ActionSetGroup);
|
||||
}
|
||||
#endregion Private Methods
|
||||
}//End Class
|
||||
|
||||
}//End namespace
|
||||
|
|
@ -0,0 +1,314 @@
|
|||
#region Using directives
|
||||
using System;
|
||||
using System.Management.Automation;
|
||||
|
||||
using System.Management.Automation.SecurityAccountsManager;
|
||||
using System.Management.Automation.SecurityAccountsManager.Extensions;
|
||||
|
||||
using Microsoft.PowerShell.LocalAccounts;
|
||||
#endregion
|
||||
|
||||
|
||||
namespace Microsoft.PowerShell.Commands
|
||||
{
|
||||
/// <summary>
|
||||
/// The Set-LocalUser cmdlet changes the properties of a user account in the
|
||||
/// local Windows Security Accounts Manager. It can also reset the password of a
|
||||
/// local user account.
|
||||
/// </summary>
|
||||
[Cmdlet(VerbsCommon.Set, "LocalUser",
|
||||
SupportsShouldProcess = true,
|
||||
DefaultParameterSetName = "Name",
|
||||
HelpUri = "http://go.microsoft.com/fwlink/?LinkId=717984")]
|
||||
[Alias("slu")]
|
||||
public class SetLocalUserCommand : PSCmdlet
|
||||
{
|
||||
#region Static Data
|
||||
// Names of object- and boolean-type parameters.
|
||||
// Switch parameters don't need to be included.
|
||||
private static string[] parameterNames = new string[]
|
||||
{
|
||||
"AccountExpires",
|
||||
"Description",
|
||||
"FullName",
|
||||
"Password",
|
||||
"UserMayChangePassword",
|
||||
"PasswordNeverExpires"
|
||||
};
|
||||
#endregion Static Data
|
||||
|
||||
#region Instance Data
|
||||
private Sam sam = null;
|
||||
#endregion Instance Data
|
||||
|
||||
#region Parameter Properties
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "AccountExpires".
|
||||
/// Specifies when the user account will expire. Set to null to indicate that
|
||||
/// the account will never expire. The default value is null (account never
|
||||
/// expires).
|
||||
/// </summary>
|
||||
[Parameter]
|
||||
public System.DateTime AccountExpires
|
||||
{
|
||||
get { return this.accountexpires;}
|
||||
set { this.accountexpires = value; }
|
||||
}
|
||||
private System.DateTime accountexpires;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "AccountNeverExpires".
|
||||
/// Specifies that the account will not expire.
|
||||
/// </summary>
|
||||
[Parameter]
|
||||
public System.Management.Automation.SwitchParameter AccountNeverExpires
|
||||
{
|
||||
get { return this.accountneverexpires;}
|
||||
set { this.accountneverexpires = value; }
|
||||
}
|
||||
private System.Management.Automation.SwitchParameter accountneverexpires;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Description".
|
||||
/// A descriptive comment for this user account (48 characters).
|
||||
/// </summary>
|
||||
[Parameter]
|
||||
[ValidateNotNull]
|
||||
[ValidateLength(0, 48)]
|
||||
public string Description
|
||||
{
|
||||
get { return this.description;}
|
||||
set { this.description = value; }
|
||||
}
|
||||
private string description;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "FullName".
|
||||
/// Specifies the full name of the user account. This is different from the
|
||||
/// username of the user account.
|
||||
/// </summary>
|
||||
[Parameter]
|
||||
[ValidateNotNull]
|
||||
public string FullName
|
||||
{
|
||||
get { return this.fullname;}
|
||||
set { this.fullname = value; }
|
||||
}
|
||||
private string fullname;
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "InputObject".
|
||||
/// Specifies the of the local user account to modify in the local Security
|
||||
/// Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "InputObject")]
|
||||
[ValidateNotNull]
|
||||
public Microsoft.PowerShell.Commands.LocalUser InputObject
|
||||
{
|
||||
get { return this.inputobject;}
|
||||
set { this.inputobject = value; }
|
||||
}
|
||||
private Microsoft.PowerShell.Commands.LocalUser inputobject;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Name".
|
||||
/// Specifies the local user account to change.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "Name")]
|
||||
[ValidateNotNullOrEmpty]
|
||||
public string Name
|
||||
{
|
||||
get { return this.name;}
|
||||
set { this.name = value; }
|
||||
}
|
||||
private string name;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "Password".
|
||||
/// Specifies the password for the local user account.
|
||||
/// </summary>
|
||||
[Parameter]
|
||||
[ValidateNotNull]
|
||||
public System.Security.SecureString Password
|
||||
{
|
||||
get { return this.password;}
|
||||
set { this.password = value; }
|
||||
}
|
||||
private System.Security.SecureString password;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "PasswordNeverExpires".
|
||||
/// Specifies that the password will not expire.
|
||||
/// </summary>
|
||||
[Parameter]
|
||||
public System.Boolean PasswordNeverExpires
|
||||
{
|
||||
get { return this.passwordneverexpires; }
|
||||
set { this.passwordneverexpires = value; }
|
||||
}
|
||||
private System.Boolean passwordneverexpires;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "SID".
|
||||
/// Specifies a user from the local Security Accounts Manager.
|
||||
/// </summary>
|
||||
[Parameter(Mandatory = true,
|
||||
Position = 0,
|
||||
ValueFromPipeline = true,
|
||||
ValueFromPipelineByPropertyName = true,
|
||||
ParameterSetName = "SecurityIdentifier")]
|
||||
[ValidateNotNull]
|
||||
public System.Security.Principal.SecurityIdentifier SID
|
||||
{
|
||||
get { return this.sid;}
|
||||
set { this.sid = value; }
|
||||
}
|
||||
private System.Security.Principal.SecurityIdentifier sid;
|
||||
|
||||
/// <summary>
|
||||
/// The following is the definition of the input parameter "UserMayChangePassword".
|
||||
/// Specifies whether the user is allowed to change the password on this
|
||||
/// account. The default value is True.
|
||||
/// </summary>
|
||||
[Parameter]
|
||||
public System.Boolean UserMayChangePassword
|
||||
{
|
||||
get { return this.usermaychangepassword;}
|
||||
set { this.usermaychangepassword = value; }
|
||||
}
|
||||
private System.Boolean usermaychangepassword;
|
||||
#endregion Parameter Properties
|
||||
|
||||
|
||||
|
||||
#region Cmdlet Overrides
|
||||
/// <summary>
|
||||
/// BeginProcessing method.
|
||||
/// </summary>
|
||||
protected override void BeginProcessing()
|
||||
{
|
||||
if (this.HasParameter("AccountExpires") && AccountNeverExpires.IsPresent)
|
||||
{
|
||||
InvalidParametersException ex = new InvalidParametersException("AccountExpires", "AccountNeverExpires");
|
||||
ThrowTerminatingError(ex.MakeErrorRecord());
|
||||
}
|
||||
sam = new Sam();
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// ProcessRecord method.
|
||||
/// </summary>
|
||||
protected override void ProcessRecord()
|
||||
{
|
||||
try
|
||||
{
|
||||
LocalUser user = null;
|
||||
|
||||
if (InputObject != null)
|
||||
{
|
||||
if (CheckShouldProcess(InputObject.ToString()))
|
||||
user = InputObject;
|
||||
}
|
||||
else if (Name != null)
|
||||
{
|
||||
user = sam.GetLocalUser(Name);
|
||||
|
||||
if (!CheckShouldProcess(Name))
|
||||
user = null;
|
||||
}
|
||||
else if (SID != null)
|
||||
{
|
||||
user = sam.GetLocalUser(SID);
|
||||
|
||||
if (!CheckShouldProcess(SID.ToString()))
|
||||
user = null;
|
||||
}
|
||||
|
||||
if (user == null)
|
||||
return;
|
||||
|
||||
// We start with what already exists
|
||||
var delta = user.Clone();
|
||||
bool? passwordNeverExpires = null;
|
||||
|
||||
foreach (var paramName in parameterNames)
|
||||
{
|
||||
if (this.HasParameter(paramName))
|
||||
{
|
||||
switch (paramName)
|
||||
{
|
||||
case "AccountExpires":
|
||||
delta.AccountExpires = this.AccountExpires;
|
||||
break;
|
||||
|
||||
case "Description":
|
||||
delta.Description = this.Description;
|
||||
break;
|
||||
|
||||
case "FullName":
|
||||
delta.FullName = this.FullName;
|
||||
break;
|
||||
|
||||
case "UserMayChangePassword":
|
||||
delta.UserMayChangePassword = this.UserMayChangePassword;
|
||||
break;
|
||||
|
||||
case "PasswordNeverExpires":
|
||||
passwordNeverExpires = this.PasswordNeverExpires;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (AccountNeverExpires.IsPresent)
|
||||
delta.AccountExpires = null;
|
||||
|
||||
sam.UpdateLocalUser(user, delta, Password, passwordNeverExpires);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
WriteError(ex.MakeErrorRecord());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// EndProcessing method.
|
||||
/// </summary>
|
||||
protected override void EndProcessing()
|
||||
{
|
||||
if (sam != null)
|
||||
{
|
||||
sam.Dispose();
|
||||
sam = null;
|
||||
}
|
||||
}
|
||||
#endregion Cmdlet Overrides
|
||||
|
||||
#region Private Methods
|
||||
private LocalUser GetUser()
|
||||
{
|
||||
if (InputObject != null)
|
||||
return InputObject;
|
||||
|
||||
return SID != null ? sam.GetLocalUser(SID)
|
||||
: sam.GetLocalUser(Name);
|
||||
}
|
||||
|
||||
private bool CheckShouldProcess(string target)
|
||||
{
|
||||
return ShouldProcess(target, Strings.ActionSetUser);
|
||||
}
|
||||
#endregion Private Methods
|
||||
}//End Class
|
||||
|
||||
}//End namespace
|
||||
|
|
@ -0,0 +1,695 @@
|
|||
using System;
|
||||
using System.Management.Automation;
|
||||
using System.Management.Automation.SecurityAccountsManager;
|
||||
using System.Runtime.Serialization;
|
||||
using Microsoft.PowerShell.LocalAccounts;
|
||||
|
||||
#if CORECLR
|
||||
using Microsoft.PowerShell.CoreClr.Stubs;
|
||||
#endif
|
||||
|
||||
namespace Microsoft.PowerShell.Commands
|
||||
{
|
||||
/// <summary>
|
||||
/// Base class for cmdlet-specific exceptions.
|
||||
/// </summary>
|
||||
public class LocalAccountsException : Exception
|
||||
{
|
||||
#region Public Properties
|
||||
/// <summary>
|
||||
/// Gets the <see cref="System.Management.Automation.ErrorCategory"/>
|
||||
/// value for this exception.
|
||||
/// </summary>
|
||||
public ErrorCategory ErrorCategory
|
||||
{
|
||||
get;
|
||||
private set;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the target object for this exception. This is used as
|
||||
/// the TargetObject member of a PowerShell
|
||||
/// <see cref="System.Management.Automation.ErrorRecord"/> object.
|
||||
/// </summary>
|
||||
public object Target
|
||||
{
|
||||
get;
|
||||
private set;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the error name. This is used as the ErrorId parameter when
|
||||
/// constructing a PowerShell <see cref="System.Management.Automation.ErrorRecord"/>
|
||||
/// oject.
|
||||
/// </summary>
|
||||
public string ErrorName
|
||||
{
|
||||
get
|
||||
{
|
||||
string exname = "Exception";
|
||||
var exlen = exname.Length;
|
||||
var name = this.GetType().Name;
|
||||
|
||||
if (name.EndsWith(exname, StringComparison.OrdinalIgnoreCase) && name.Length > exlen)
|
||||
name = name.Substring(0, name.Length - exlen);
|
||||
return name;
|
||||
}
|
||||
}
|
||||
#endregion Public Properties
|
||||
|
||||
internal LocalAccountsException(string message, object target, ErrorCategory errorCategory)
|
||||
: base(message)
|
||||
{
|
||||
ErrorCategory = errorCategory;
|
||||
Target = target;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
public LocalAccountsException() : base() { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
public LocalAccountsException(String message) : base(message) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
/// <param name="ex"></param>
|
||||
public LocalAccountsException(String message, Exception ex) : base(message, ex) { }
|
||||
|
||||
#if CORECLR
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="info"></param>
|
||||
/// <param name="ctx"></param>
|
||||
// This is not supported for CoreCLR
|
||||
protected LocalAccountsException(SerializationInfo info, StreamingContext ctx) : base() { }
|
||||
#else
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="info"></param>
|
||||
/// <param name="ctx"></param>
|
||||
protected LocalAccountsException(SerializationInfo info, StreamingContext ctx) : base(info, ctx) { }
|
||||
#endif
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Exception indicating an error occurred during one of the internal
|
||||
/// operations such as opening or closing a handle.
|
||||
/// </summary>
|
||||
public class InternalException : LocalAccountsException
|
||||
{
|
||||
#region Public Properties
|
||||
/// <summary>
|
||||
/// Gets the NTSTATUS code for this exception.
|
||||
/// </summary>
|
||||
public UInt32 StatusCode
|
||||
{
|
||||
get;
|
||||
private set;
|
||||
}
|
||||
#endregion Public Properties
|
||||
|
||||
internal InternalException(UInt32 ntStatus,
|
||||
string message,
|
||||
object target,
|
||||
ErrorCategory errorCategory = ErrorCategory.NotSpecified)
|
||||
: base(message, target, errorCategory)
|
||||
{
|
||||
StatusCode = ntStatus;
|
||||
}
|
||||
|
||||
internal InternalException(UInt32 ntStatus,
|
||||
object target,
|
||||
ErrorCategory errorCategory = ErrorCategory.NotSpecified)
|
||||
: this(ntStatus,
|
||||
StringUtil.Format(Strings.UnspecifiedErrorNtStatus, ntStatus),
|
||||
target,
|
||||
errorCategory)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
public InternalException() : base() { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
public InternalException(String message) : base(message) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
/// <param name="ex"></param>
|
||||
public InternalException(String message, Exception ex) : base(message, ex) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="info"></param>
|
||||
/// <param name="ctx"></param>
|
||||
protected InternalException(SerializationInfo info, StreamingContext ctx) : base(info, ctx) { }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Exception indicating an error occurred when a native function
|
||||
/// is called that returns a Win32 error code as opposed to an
|
||||
/// NT Status code.
|
||||
/// </summary>
|
||||
public class Win32InternalException : LocalAccountsException
|
||||
{
|
||||
#region Public Properties
|
||||
/// <summary>
|
||||
/// The Win32 error code for this exception.
|
||||
/// </summary>
|
||||
public int NativeErrorCode
|
||||
{
|
||||
get;
|
||||
private set;
|
||||
}
|
||||
#endregion Public Properties
|
||||
|
||||
internal Win32InternalException(int errorCode,
|
||||
string message,
|
||||
object target,
|
||||
ErrorCategory errorCategory = ErrorCategory.NotSpecified)
|
||||
: base(message, target, errorCategory)
|
||||
{
|
||||
NativeErrorCode = errorCode;
|
||||
}
|
||||
|
||||
internal Win32InternalException(int errorCode,
|
||||
object target,
|
||||
ErrorCategory errorCategory = ErrorCategory.NotSpecified)
|
||||
: this(errorCode,
|
||||
StringUtil.Format(Strings.UnspecifiedErrorWin32Error, errorCode),
|
||||
target,
|
||||
errorCategory)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
public Win32InternalException() : base() {}
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
public Win32InternalException(String message) : base(message) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
/// <param name="ex"></param>
|
||||
public Win32InternalException(String message, Exception ex) : base(message, ex) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="info"></param>
|
||||
/// <param name="ctx"></param>
|
||||
protected Win32InternalException(SerializationInfo info, StreamingContext ctx) : base(info, ctx) { }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Exception indicating an invalid password.
|
||||
/// </summary>
|
||||
public class InvalidPasswordException : LocalAccountsException
|
||||
{
|
||||
/// <summary>
|
||||
/// Generates with a default invalid password message.
|
||||
/// </summary>
|
||||
public InvalidPasswordException()
|
||||
: base(Strings.InvalidPassword, null, ErrorCategory.InvalidArgument)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Generates the exception with the specified message.
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
public InvalidPasswordException(string message)
|
||||
: base(message, null, ErrorCategory.InvalidArgument)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates a message from the specified error code.
|
||||
/// </summary>
|
||||
/// <param name="errorCode"></param>
|
||||
public InvalidPasswordException(uint errorCode)
|
||||
: base(StringUtil.GetSystemMessage(errorCode), null, ErrorCategory.InvalidArgument)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
/// <param name="ex"></param>
|
||||
public InvalidPasswordException(String message, Exception ex) : base(message, ex) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="info"></param>
|
||||
/// <param name="ctx"></param>
|
||||
protected InvalidPasswordException(SerializationInfo info, StreamingContext ctx) : base(info, ctx) { }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Exception thrown when invalid parameter pairing is detected.
|
||||
/// </summary>
|
||||
public class InvalidParametersException : LocalAccountsException
|
||||
{
|
||||
internal InvalidParametersException(string message)
|
||||
: base(message, null, ErrorCategory.InvalidArgument)
|
||||
{
|
||||
}
|
||||
|
||||
internal InvalidParametersException(string parameterA, string parameterB)
|
||||
: this(StringUtil.Format(Strings.InvalidParameterPair, parameterA, parameterB))
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
public InvalidParametersException() : base() { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
/// <param name="ex"></param>
|
||||
public InvalidParametersException(String message, Exception ex) : base(message, ex) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="info"></param>
|
||||
/// <param name="ctx"></param>
|
||||
protected InvalidParametersException(SerializationInfo info, StreamingContext ctx) : base(info, ctx) { }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Exception indicating permission denied.
|
||||
/// </summary>
|
||||
public class AccessDeniedException : LocalAccountsException
|
||||
{
|
||||
internal AccessDeniedException(object target)
|
||||
: base(Strings.AccessDenied, target, ErrorCategory.PermissionDenied)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
public AccessDeniedException() : base() { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
public AccessDeniedException(String message) : base(message) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
/// <param name="ex"></param>
|
||||
public AccessDeniedException(String message, Exception ex) : base(message, ex) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="info"></param>
|
||||
/// <param name="ctx"></param>
|
||||
protected AccessDeniedException(SerializationInfo info, StreamingContext ctx) : base(info, ctx) { }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Exception indicating that the name of a user or group is invalid.
|
||||
/// </summary>
|
||||
public class InvalidNameException : LocalAccountsException
|
||||
{
|
||||
internal InvalidNameException(string name, object target)
|
||||
: base(StringUtil.Format(Strings.InvalidName, name), target, ErrorCategory.InvalidArgument)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
public InvalidNameException() : base() { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
public InvalidNameException(String message) : base(message) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
/// <param name="ex"></param>
|
||||
public InvalidNameException(String message, Exception ex) : base(message, ex) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="info"></param>
|
||||
/// <param name="ctx"></param>
|
||||
protected InvalidNameException(SerializationInfo info, StreamingContext ctx) : base(info, ctx) { }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Exception indicating that the specified name is already in use.
|
||||
/// </summary>
|
||||
public class NameInUseException : LocalAccountsException
|
||||
{
|
||||
internal NameInUseException(string name, object target)
|
||||
: base(StringUtil.Format(Strings.NameInUse, name), target, ErrorCategory.InvalidArgument)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
public NameInUseException() : base() { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
public NameInUseException(String message) : base(message) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
/// <param name="ex"></param>
|
||||
public NameInUseException(String message, Exception ex) : base(message, ex) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="info"></param>
|
||||
/// <param name="ctx"></param>
|
||||
protected NameInUseException(SerializationInfo info, StreamingContext ctx) : base(info, ctx) { }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Exception indicating that an entity of some kind was not found.
|
||||
/// Also serves as a base class for more specific object-not-found errors.
|
||||
/// </summary>
|
||||
public class NotFoundException : LocalAccountsException
|
||||
{
|
||||
internal NotFoundException(string message, object target)
|
||||
: base(message, target, ErrorCategory.ObjectNotFound)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
public NotFoundException() : base() { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
public NotFoundException(String message) : base(message) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
/// <param name="ex"></param>
|
||||
public NotFoundException(String message, Exception ex) : base(message, ex) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="info"></param>
|
||||
/// <param name="ctx"></param>
|
||||
protected NotFoundException(SerializationInfo info, StreamingContext ctx) : base(info, ctx) { }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Exception indicating that a principal was not Found
|
||||
/// </summary>
|
||||
public class PrincipalNotFoundException : NotFoundException
|
||||
{
|
||||
internal PrincipalNotFoundException(string principal, object target)
|
||||
: base(StringUtil.Format(Strings.PrincipalNotFound, principal), target)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
public PrincipalNotFoundException() : base() { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
public PrincipalNotFoundException(String message) : base(message) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
/// <param name="ex"></param>
|
||||
public PrincipalNotFoundException(String message, Exception ex) : base(message, ex) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="info"></param>
|
||||
/// <param name="ctx"></param>
|
||||
protected PrincipalNotFoundException(SerializationInfo info, StreamingContext ctx) : base(info, ctx) { }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Exception indicating that a group was not found.
|
||||
/// </summary>
|
||||
public class GroupNotFoundException : NotFoundException
|
||||
{
|
||||
internal GroupNotFoundException(string group, object target)
|
||||
: base(StringUtil.Format(Strings.GroupNotFound, group), target)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
public GroupNotFoundException() : base() { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
public GroupNotFoundException(String message) : base(message) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
/// <param name="ex"></param>
|
||||
public GroupNotFoundException(String message, Exception ex) : base(message, ex) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="info"></param>
|
||||
/// <param name="ctx"></param>
|
||||
protected GroupNotFoundException(SerializationInfo info, StreamingContext ctx) : base(info, ctx) { }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Exception indicating that a user was not found.
|
||||
/// </summary>
|
||||
public class UserNotFoundException : NotFoundException
|
||||
{
|
||||
internal UserNotFoundException(string user, object target)
|
||||
: base(StringUtil.Format(Strings.UserNotFound, user), target)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
public UserNotFoundException() : base() { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
public UserNotFoundException(String message) : base(message) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
/// <param name="ex"></param>
|
||||
public UserNotFoundException(String message, Exception ex) : base(message, ex) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="info"></param>
|
||||
/// <param name="ctx"></param>
|
||||
protected UserNotFoundException(SerializationInfo info, StreamingContext ctx) : base(info, ctx) { }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Exception indicating that a group member was not found.
|
||||
/// </summary>
|
||||
public class MemberNotFoundException : NotFoundException
|
||||
{
|
||||
internal MemberNotFoundException(string member, string group)
|
||||
: base(StringUtil.Format(Strings.MemberNotFound, member, group), member)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
public MemberNotFoundException() : base() { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
public MemberNotFoundException(String message) : base(message) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
/// <param name="ex"></param>
|
||||
public MemberNotFoundException(String message, Exception ex) : base(message, ex) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="info"></param>
|
||||
/// <param name="ctx"></param>
|
||||
protected MemberNotFoundException(SerializationInfo info, StreamingContext ctx) : base(info, ctx) { }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Exception indicating that an entity of some kind already exists.
|
||||
/// Also serves as a base class for more specific object-exists errors.
|
||||
/// </summary>
|
||||
public class ObjectExistsException : LocalAccountsException
|
||||
{
|
||||
internal ObjectExistsException(string message, object target)
|
||||
: base(message, target, ErrorCategory.ResourceExists)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
public ObjectExistsException() : base() { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
public ObjectExistsException(String message) : base(message) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
/// <param name="ex"></param>
|
||||
public ObjectExistsException(String message, Exception ex) : base(message, ex) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="info"></param>
|
||||
/// <param name="ctx"></param>
|
||||
protected ObjectExistsException(SerializationInfo info, StreamingContext ctx) : base(info, ctx) { }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Exception indicating that a group already exists.
|
||||
/// </summary>
|
||||
public class GroupExistsException : ObjectExistsException
|
||||
{
|
||||
internal GroupExistsException(string group, object target)
|
||||
: base(StringUtil.Format(Strings.GroupExists, group), target)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
public GroupExistsException() : base() { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
public GroupExistsException(String message) : base(message) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
/// <param name="ex"></param>
|
||||
public GroupExistsException(String message, Exception ex) : base(message, ex) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="info"></param>
|
||||
/// <param name="ctx"></param>
|
||||
protected GroupExistsException(SerializationInfo info, StreamingContext ctx) : base(info, ctx) { }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Exception indicating that a group already exists.
|
||||
/// </summary>
|
||||
public class UserExistsException : ObjectExistsException
|
||||
{
|
||||
internal UserExistsException(string user, object target)
|
||||
: base(StringUtil.Format(Strings.UserExists, user), target)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
public UserExistsException() : base() { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
public UserExistsException(String message) : base(message) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
/// <param name="ex"></param>
|
||||
public UserExistsException(String message, Exception ex) : base(message, ex) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="info"></param>
|
||||
/// <param name="ctx"></param>
|
||||
protected UserExistsException(SerializationInfo info, StreamingContext ctx) : base(info, ctx) { }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Exception indicating that an object already exists as a group member.
|
||||
/// </summary>
|
||||
public class MemberExistsException : ObjectExistsException
|
||||
{
|
||||
internal MemberExistsException(string member, string group, object target)
|
||||
: base(StringUtil.Format(Strings.MemberExists, member, group), target)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
public MemberExistsException() : base() { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
public MemberExistsException(String message) : base(message) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
/// <param name="ex"></param>
|
||||
public MemberExistsException(String message, Exception ex) : base(message, ex) { }
|
||||
/// <summary>
|
||||
/// Compliance Constructor
|
||||
/// </summary>
|
||||
/// <param name="info"></param>
|
||||
/// <param name="ctx"></param>
|
||||
protected MemberExistsException(SerializationInfo info, StreamingContext ctx) : base(info, ctx) { }
|
||||
}
|
||||
}
|
|
@ -0,0 +1,217 @@
|
|||
using System.Runtime.InteropServices;
|
||||
using System.Security;
|
||||
using System.Security.Principal;
|
||||
using System.Text.RegularExpressions;
|
||||
|
||||
using Microsoft.PowerShell.Commands;
|
||||
using Microsoft.PowerShell.LocalAccounts;
|
||||
|
||||
namespace System.Management.Automation.SecurityAccountsManager.Extensions
|
||||
{
|
||||
/// <summary>
|
||||
/// Provides extension methods for the Cmdlet class
|
||||
/// </summary>
|
||||
internal static class CmdletExtensions
|
||||
{
|
||||
/// <summary>
|
||||
/// Attempt to create a SID from a string.
|
||||
/// </summary>
|
||||
/// <param name="cmdlet">The cmdlet being extended with this method.</param>
|
||||
/// <param name="s">The string to be converted to a SID.</param>
|
||||
/// <param name="allowSidConstants">
|
||||
/// A boolean indicating whether SID constants, such as "BA", are considered.
|
||||
/// </param>
|
||||
/// <returns>
|
||||
/// A <see cref="SecurityIdentifier"/> object if the conversion was successful,
|
||||
/// null otherwise.
|
||||
/// </returns>
|
||||
internal static SecurityIdentifier TrySid(this Cmdlet cmdlet,
|
||||
string s,
|
||||
bool allowSidConstants = false)
|
||||
{
|
||||
if (!allowSidConstants)
|
||||
if (!(s.Length > 2 && s.StartsWith("S-") && Char.IsDigit(s[2])))
|
||||
return null;
|
||||
|
||||
SecurityIdentifier sid = null;
|
||||
|
||||
try
|
||||
{
|
||||
sid = new SecurityIdentifier(s);
|
||||
}
|
||||
catch (ArgumentException)
|
||||
{
|
||||
// do nothing here, just fall through to the return
|
||||
}
|
||||
|
||||
return sid;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Provides extension methods for the PSCmdlet class
|
||||
/// </summary>
|
||||
internal static class PSExtensions
|
||||
{
|
||||
/// <summary>
|
||||
/// Determine if a given parameter was provided to the cmdlet
|
||||
/// </summary>
|
||||
/// <param name="cmdlet">
|
||||
/// The <see cref="PSCmdlet"/> object to check.
|
||||
/// </param>
|
||||
/// <param name="parameterName">
|
||||
/// A string containing the name of the parameter. This should be in the
|
||||
/// same letter-casing as the defined parameter.
|
||||
/// </param>
|
||||
/// <returns>
|
||||
/// True if the specified parameter was given on the cmdlet invocation,
|
||||
/// false otherwise.
|
||||
/// </returns>
|
||||
internal static bool HasParameter(this PSCmdlet cmdlet, string parameterName)
|
||||
{
|
||||
var invocation = cmdlet.MyInvocation;
|
||||
if (invocation != null)
|
||||
{
|
||||
var parameters = invocation.BoundParameters;
|
||||
|
||||
if (parameters != null)
|
||||
{
|
||||
// PowerShell sets the parameter names in the BoundParameters dictionary
|
||||
// to their "proper" casing, so we don't have to do a case-insensitive search.
|
||||
if (parameters.ContainsKey(parameterName))
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Provides extension methods for the SecurityIdentifier class.
|
||||
/// </summary>
|
||||
internal static class SidExtensions
|
||||
{
|
||||
/// <summary>
|
||||
/// Get the Relative ID (RID) from a <see cref="SecurityIdentifier"/> object.
|
||||
/// </summary>
|
||||
/// <param name="sid">The SecurityIdentifier containing the desired Relative ID.</param>
|
||||
/// <returns>
|
||||
/// A UInt32 value containing the Relative ID in the SecurityIdentifier.
|
||||
/// </returns>
|
||||
internal static UInt32 GetRid(this SecurityIdentifier sid)
|
||||
{
|
||||
byte[] sidBinary = new byte[sid.BinaryLength];
|
||||
sid.GetBinaryForm(sidBinary, 0);
|
||||
|
||||
return System.BitConverter.ToUInt32(sidBinary, sidBinary.Length-4);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the Identifier Authority portion of a <see cref="SecurityIdentifier"/>
|
||||
/// </summary>
|
||||
/// <param name="sid">The SecurityIdentifier containing the desired Authority.</param>
|
||||
/// <returns>
|
||||
/// A long integer value containing the SecurityIdentifier's Identifier Authority value.
|
||||
/// </returns>
|
||||
/// <remarks>
|
||||
/// This method is used primarily for determining the Source of a Principal.
|
||||
/// The Win32 API LsaLookupUserAccountType function does not (yet) properly
|
||||
/// identify MicrosoftAccount principals.
|
||||
/// </remarks>
|
||||
internal static long GetIdentifierAuthority(this SecurityIdentifier sid)
|
||||
{
|
||||
byte[] sidBinary = new byte[sid.BinaryLength];
|
||||
|
||||
sid.GetBinaryForm(sidBinary, 0);
|
||||
|
||||
// The Identifier Authority is six bytes wide,
|
||||
// in big-endian format, starting at the third byte
|
||||
long authority = (long) (((long)sidBinary[2]) << 40) +
|
||||
(((long)sidBinary[3]) << 32) +
|
||||
(((long)sidBinary[4]) << 24) +
|
||||
(((long)sidBinary[5]) << 16) +
|
||||
(((long)sidBinary[6]) << 8) +
|
||||
(((long)sidBinary[7]) );
|
||||
|
||||
return authority;
|
||||
}
|
||||
|
||||
internal static bool IsMsaAccount(this SecurityIdentifier sid)
|
||||
{
|
||||
return sid.GetIdentifierAuthority() == 11;
|
||||
}
|
||||
}
|
||||
|
||||
internal static class SecureStringExtensions
|
||||
{
|
||||
private static Regex pwRegex = new Regex(@"^[^\x00-\x1F""/\\\[\]:;\|=,+\*?<>@]{0,127}$",
|
||||
RegexOptions.Compiled | RegexOptions.CultureInvariant);
|
||||
|
||||
internal static bool IsValidPassword(this SecureString str)
|
||||
{
|
||||
return str.Length == 0 || pwRegex.IsMatch(str.AsString());
|
||||
}
|
||||
|
||||
internal static void ValidatePassword(this SecureString str)
|
||||
{
|
||||
if (!str.IsValidPassword())
|
||||
throw new InvalidPasswordException();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Extension method to extract clear text from a
|
||||
/// <see cref="System.Security.SecureString"/> object.
|
||||
/// </summary>
|
||||
/// <param name="str">
|
||||
/// This SecureString object, containing encrypted text.
|
||||
/// </param>
|
||||
/// <returns>
|
||||
/// A string containing the SecureString object's original text.
|
||||
/// </returns>
|
||||
internal static string AsString(this SecureString str)
|
||||
{
|
||||
#if CORECLR
|
||||
IntPtr buffer = SecureStringMarshal.SecureStringToCoTaskMemUnicode(str);
|
||||
string clear = Marshal.PtrToStringUni(buffer);
|
||||
SecureStringMarshal.ZeroFreeCoTaskMemUnicode(buffer);
|
||||
#else
|
||||
var bstr = Marshal.SecureStringToBSTR(str);
|
||||
string clear = Marshal.PtrToStringAuto(bstr);
|
||||
Marshal.ZeroFreeBSTR(bstr);
|
||||
#endif
|
||||
return clear;
|
||||
}
|
||||
}
|
||||
|
||||
internal static class ExceptionExtensions
|
||||
{
|
||||
internal static ErrorRecord MakeErrorRecord(this Exception ex,
|
||||
string errorId,
|
||||
ErrorCategory errorCategory,
|
||||
object target = null)
|
||||
{
|
||||
return new ErrorRecord(ex, errorId, errorCategory, target);
|
||||
}
|
||||
|
||||
internal static ErrorRecord MakeErrorRecord(this Exception ex, object target = null)
|
||||
{
|
||||
// This part is somewhat less than beautiful, but it prevents
|
||||
// having to have multiple exception handlers in every cmdlet command.
|
||||
var exTemp = ex as LocalAccountsException;
|
||||
|
||||
if (exTemp != null)
|
||||
return MakeErrorRecord(exTemp, target ?? exTemp.Target);
|
||||
|
||||
return new ErrorRecord(ex,
|
||||
Strings.UnspecifiedError,
|
||||
ErrorCategory.NotSpecified,
|
||||
target);
|
||||
}
|
||||
|
||||
internal static ErrorRecord MakeErrorRecord(this LocalAccountsException ex, object target = null)
|
||||
{
|
||||
return ex.MakeErrorRecord(ex.ErrorName, ex.ErrorCategory, target ?? ex.Target);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,79 @@
|
|||
using System;
|
||||
|
||||
using Microsoft.PowerShell.LocalAccounts;
|
||||
|
||||
namespace Microsoft.PowerShell.Commands
|
||||
{
|
||||
/// <summary>
|
||||
/// Describes a Local Group.
|
||||
/// Objects of this type are provided to and returned from group-related Cmdlets.
|
||||
/// </summary>
|
||||
public class LocalGroup : LocalPrincipal
|
||||
{
|
||||
#region Public Properties
|
||||
/// <summary>
|
||||
/// A short description of the Group.
|
||||
/// </summary>
|
||||
public String Description { get; set; }
|
||||
#endregion Public Properties
|
||||
|
||||
#region Construction
|
||||
/// <summary>
|
||||
/// Initializes a new LocalGroup object.
|
||||
/// </summary>
|
||||
public LocalGroup()
|
||||
{
|
||||
ObjectClass = Strings.ObjectClassGroup;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new LocalUser object with the specified name.
|
||||
/// </summary>
|
||||
/// <param name="name">Name of the new LocalGroup.</param>
|
||||
public LocalGroup(string name)
|
||||
: base(name)
|
||||
{
|
||||
ObjectClass = Strings.ObjectClassGroup;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Construct a new LocalGroup object that is a copy of another
|
||||
/// </summary>
|
||||
/// <param name="other"></param>
|
||||
private LocalGroup(LocalGroup other)
|
||||
: this(other.Name)
|
||||
{
|
||||
Description = other.Description;
|
||||
}
|
||||
#endregion Construction
|
||||
|
||||
|
||||
#region Public Methods
|
||||
/// <summary>
|
||||
/// Provides a string representation of the LocalGroup object.
|
||||
/// </summary>
|
||||
/// <returns>
|
||||
/// A string containing the Group Name.
|
||||
/// </returns>
|
||||
public override string ToString()
|
||||
{
|
||||
return Name ?? SID.ToString();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Create a copy of a LocalGroup object.
|
||||
/// </summary>
|
||||
/// <returns>
|
||||
/// A new LocalGroup object with the same property values as this one.
|
||||
/// </returns>
|
||||
public LocalGroup Clone()
|
||||
{
|
||||
if (null == this)
|
||||
{
|
||||
throw new NullReferenceException();
|
||||
}
|
||||
return new LocalGroup(this);
|
||||
}
|
||||
#endregion Public Methods
|
||||
}
|
||||
}
|
|
@ -0,0 +1,97 @@
|
|||
using System.Security.Principal;
|
||||
|
||||
namespace Microsoft.PowerShell.Commands
|
||||
{
|
||||
/// <summary>
|
||||
/// Defines the source of a Principal
|
||||
/// </summary>
|
||||
public enum PrincipalSource
|
||||
{
|
||||
/// <summary>
|
||||
/// The principal source is unknown or could not be determined
|
||||
/// </summary>
|
||||
Unknown = 0,
|
||||
|
||||
/// <summary>
|
||||
/// The principal is sourced from the local Windows Security Accounts Manager.
|
||||
/// </summary>
|
||||
Local,
|
||||
|
||||
/// <summary>
|
||||
/// The principal is sourced from an Active Directory domain.
|
||||
/// </summary>
|
||||
ActiveDirectory,
|
||||
|
||||
/// <summary>
|
||||
/// The principal is sourced from Azure Active Directory.
|
||||
/// </summary>
|
||||
AzureAD,
|
||||
|
||||
/// <summary>
|
||||
/// The principal is a Microsoft Account, such as
|
||||
/// <b>MicrosoftAccount\user@domain.com</b>
|
||||
/// </summary>
|
||||
MicrosoftAccount
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Represents a Principal. Serves as a base class for Users and Groups.
|
||||
/// </summary>
|
||||
public class LocalPrincipal
|
||||
{
|
||||
#region Public Properties
|
||||
/// <summary>
|
||||
/// The account name of the Principal.
|
||||
/// </summary>
|
||||
public string Name { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// The Security Identifier that uniquely identifies the Principal/
|
||||
/// </summary>
|
||||
public SecurityIdentifier SID { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Indicates the account store from which the principal is sourced.
|
||||
/// One of the PrincipalSource enumerations.
|
||||
/// </summary>
|
||||
public PrincipalSource? PrincipalSource { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// The object class that represents this principal.
|
||||
/// This can be User or Group.
|
||||
/// </summary>
|
||||
public string ObjectClass { get; set; }
|
||||
#endregion Public Properties
|
||||
|
||||
#region Construction
|
||||
/// <summary>
|
||||
/// Initializes a new LocalPrincipal object.
|
||||
/// </summary>
|
||||
public LocalPrincipal()
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new LocalPrincipal object with the specified name.
|
||||
/// </summary>
|
||||
/// <param name="name">Name of the new LocalPrincipal.</param>
|
||||
public LocalPrincipal(string name)
|
||||
{
|
||||
Name = name;
|
||||
}
|
||||
#endregion Construction
|
||||
|
||||
#region Public Methods
|
||||
/// <summary>
|
||||
/// Provides a string representation of the Principal.
|
||||
/// </summary>
|
||||
/// <returns>
|
||||
/// A string, in SDDL form, representing the Principal.
|
||||
/// </returns>
|
||||
public override string ToString()
|
||||
{
|
||||
return Name ?? SID.ToString();
|
||||
}
|
||||
#endregion Public Methods
|
||||
}
|
||||
}
|
|
@ -0,0 +1,145 @@
|
|||
using System;
|
||||
|
||||
using Microsoft.PowerShell.LocalAccounts;
|
||||
|
||||
namespace Microsoft.PowerShell.Commands
|
||||
{
|
||||
/// <summary>
|
||||
/// Describes a Local User.
|
||||
/// Objects of this type are provided to and returned from user-related Cmdlets.
|
||||
/// </summary>
|
||||
public class LocalUser : LocalPrincipal
|
||||
{
|
||||
#region Public Properties
|
||||
/// <summary>
|
||||
/// The date and time at which this user account expires.
|
||||
/// A value of null indicates that the account never expires.
|
||||
/// </summary>
|
||||
public DateTime? AccountExpires { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// A short description of the User.
|
||||
/// </summary>
|
||||
public string Description { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Indicates whether the user account is enabled (true) or disabled (false).
|
||||
/// </summary>
|
||||
public bool Enabled { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// The user's full name. Not the same as the User name.
|
||||
/// </summary>
|
||||
public string FullName { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// The date and time at which this user account password is allowed
|
||||
/// to be changed. The password cannot be changed before this time.
|
||||
/// A value of null indicates that the password can be changed anytime.
|
||||
/// </summary>
|
||||
public DateTime? PasswordChangeableDate { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// The date and time at which this user account password must be changed
|
||||
/// to a new password. A value of null indicates that the password will
|
||||
/// never expire.
|
||||
/// </summary>
|
||||
public DateTime? PasswordExpires { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Indicates whether the user is allowed to change the password (true)
|
||||
/// or not (false).
|
||||
/// </summary>
|
||||
public bool UserMayChangePassword { get; set; }
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Indicates whether the user must have a password (true) or not (false).
|
||||
/// </summary>
|
||||
public bool PasswordRequired { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// The date and time at which this user last changed the account password.
|
||||
/// </summary>
|
||||
public DateTime? PasswordLastSet { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// The date and time at which the user last logged on to the machine.
|
||||
/// </summary>
|
||||
public DateTime? LastLogon { get; set; }
|
||||
#endregion Public Properties
|
||||
|
||||
|
||||
#region Construction
|
||||
/// <summary>
|
||||
/// Initializes a new LocalUser object.
|
||||
/// </summary>
|
||||
public LocalUser()
|
||||
{
|
||||
ObjectClass = Strings.ObjectClassUser;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new LocalUser object with the specified name.
|
||||
/// </summary>
|
||||
/// <param name="name">Name of the new LocalUser.</param>
|
||||
public LocalUser(string name)
|
||||
: base(name)
|
||||
{
|
||||
ObjectClass = Strings.ObjectClassUser;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Construct a new LocalUser object that is a copy of another.
|
||||
/// </summary>
|
||||
/// <param name="other">The LocalUser object to copy.</param>
|
||||
private LocalUser(LocalUser other)
|
||||
: this(other.Name)
|
||||
{
|
||||
SID = other.SID;
|
||||
PrincipalSource = other.PrincipalSource;
|
||||
ObjectClass = other.ObjectClass;
|
||||
|
||||
AccountExpires = other.AccountExpires;
|
||||
Description = other.Description;
|
||||
Enabled = other.Enabled;
|
||||
FullName = other.FullName;
|
||||
PasswordChangeableDate = other.PasswordChangeableDate;
|
||||
PasswordExpires = other.PasswordExpires;
|
||||
UserMayChangePassword = other.UserMayChangePassword;
|
||||
|
||||
PasswordRequired = other.PasswordRequired;
|
||||
PasswordLastSet = other.PasswordLastSet;
|
||||
LastLogon = other.LastLogon;
|
||||
}
|
||||
#endregion Construction
|
||||
|
||||
#region Public Methods
|
||||
/// <summary>
|
||||
/// Provides a string representation of the LocalUser object.
|
||||
/// </summary>
|
||||
/// <returns>
|
||||
/// A string containing the User Name.
|
||||
/// </returns>
|
||||
public override string ToString()
|
||||
{
|
||||
return Name ?? SID.ToString();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Create a copy of a LocalUser object.
|
||||
/// </summary>
|
||||
/// <returns>
|
||||
/// A new LocalUser object with the same property values as this one.
|
||||
/// </returns>
|
||||
public LocalUser Clone()
|
||||
{
|
||||
if (null == this)
|
||||
{
|
||||
throw new NullReferenceException();
|
||||
}
|
||||
return new LocalUser(this);
|
||||
}
|
||||
#endregion Public Methods
|
||||
}
|
||||
}
|
523
src/Microsoft.PowerShell.LocalAccounts/LocalAccounts/Native.cs
Normal file
523
src/Microsoft.PowerShell.LocalAccounts/LocalAccounts/Native.cs
Normal file
|
@ -0,0 +1,523 @@
|
|||
using System;
|
||||
using System.Runtime.InteropServices;
|
||||
using System.Text;
|
||||
|
||||
namespace System.Management.Automation.SecurityAccountsManager.Native
|
||||
{
|
||||
#region Enums
|
||||
internal enum POLICY_INFORMATION_CLASS
|
||||
{
|
||||
PolicyAuditLogInformation = 1,
|
||||
PolicyAuditEventsInformation,
|
||||
PolicyPrimaryDomainInformation,
|
||||
PolicyPdAccountInformation,
|
||||
PolicyAccountDomainInformation,
|
||||
PolicyLsaServerRoleInformation,
|
||||
PolicyReplicaSourceInformation,
|
||||
PolicyDefaultQuotaInformation,
|
||||
PolicyModificationInformation,
|
||||
PolicyAuditFullSetInformation,
|
||||
PolicyAuditFullQueryInformation,
|
||||
PolicyDnsDomainInformation
|
||||
}
|
||||
|
||||
[Flags]
|
||||
internal enum LSA_AccessPolicy : long
|
||||
{
|
||||
POLICY_VIEW_LOCAL_INFORMATION = 0x00000001L,
|
||||
POLICY_VIEW_AUDIT_INFORMATION = 0x00000002L,
|
||||
POLICY_GET_PRIVATE_INFORMATION = 0x00000004L,
|
||||
POLICY_TRUST_ADMIN = 0x00000008L,
|
||||
POLICY_CREATE_ACCOUNT = 0x00000010L,
|
||||
POLICY_CREATE_SECRET = 0x00000020L,
|
||||
POLICY_CREATE_PRIVILEGE = 0x00000040L,
|
||||
POLICY_SET_DEFAULT_QUOTA_LIMITS = 0x00000080L,
|
||||
POLICY_SET_AUDIT_REQUIREMENTS = 0x00000100L,
|
||||
POLICY_AUDIT_LOG_ADMIN = 0x00000200L,
|
||||
POLICY_SERVER_ADMIN = 0x00000400L,
|
||||
POLICY_LOOKUP_NAMES = 0x00000800L,
|
||||
POLICY_NOTIFICATION = 0x00001000L
|
||||
}
|
||||
|
||||
internal enum SID_NAME_USE
|
||||
{
|
||||
SidTypeUser = 1,
|
||||
SidTypeGroup,
|
||||
SidTypeDomain,
|
||||
SidTypeAlias,
|
||||
SidTypeWellKnownGroup,
|
||||
SidTypeDeletedAccount,
|
||||
SidTypeInvalid,
|
||||
SidTypeUnknown,
|
||||
SidTypeComputer,
|
||||
SidTypeLabel
|
||||
}
|
||||
|
||||
internal enum LSA_USER_ACCOUNT_TYPE
|
||||
{
|
||||
UnknownUserAccountType = 0,
|
||||
LocalUserAccountType,
|
||||
PrimaryDomainUserAccountType,
|
||||
ExternalDomainUserAccountType,
|
||||
LocalConnectedUserAccountType, // Microsoft Account
|
||||
AADUserAccountType,
|
||||
InternetUserAccountType, // Generic internet User (eg. if the SID supplied is MSA's internet SID)
|
||||
MSAUserAccountType // !!! NOT YET IN THE ENUM SPECIFIED IN THE C API !!!
|
||||
|
||||
}
|
||||
#endregion Enums
|
||||
|
||||
#region Structures
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
internal struct SECURITY_DESCRIPTOR
|
||||
{
|
||||
public byte Revision;
|
||||
public byte Sbz1;
|
||||
public UInt16 Control; // SECURITY_DESCRIPTOR_CONTROL
|
||||
public IntPtr Owner;
|
||||
public IntPtr Group;
|
||||
public IntPtr Sacl;
|
||||
public IntPtr Dacl;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
internal struct ACL
|
||||
{
|
||||
public byte AclRevision;
|
||||
public byte Sbz1;
|
||||
public UInt16 AclSize;
|
||||
public UInt16 AceCount;
|
||||
public UInt16 Sbz2;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode)]
|
||||
internal struct USER_INFO_1
|
||||
{
|
||||
public string name;
|
||||
public string password;
|
||||
public int password_age;
|
||||
public int priv;
|
||||
public string home_dir;
|
||||
public string comment;
|
||||
public uint flags;
|
||||
public string script_path;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
internal struct USER_INFO_1008
|
||||
{
|
||||
public uint flags;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// The UNICODE_STRING structure is passed to a number of the SAM and LSA
|
||||
/// API functions. This adds cleanup and managed-string conversion behaviors.
|
||||
/// </summary>
|
||||
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode)]
|
||||
internal struct UNICODE_STRING
|
||||
{
|
||||
public UInt16 Length;
|
||||
public UInt16 MaximumLength;
|
||||
[MarshalAs(UnmanagedType.LPWStr)]
|
||||
private string buffer;
|
||||
|
||||
public UNICODE_STRING(string s)
|
||||
{
|
||||
buffer = String.IsNullOrEmpty(s) ? String.Empty : s;
|
||||
Length = (UInt16)(2 * buffer.Length);
|
||||
MaximumLength = Length;
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
// UNICODE_STRING structures that were populated by unmanaged code
|
||||
// often have buffers that point to junk if Length = 0, or that
|
||||
// point to non-null-terminated strings, resulting in marshaled
|
||||
// String objects that have more characters than they should.
|
||||
return Length == 0 ? String.Empty
|
||||
: buffer.Substring(0, Length / 2);
|
||||
}
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
internal struct OBJECT_ATTRIBUTES : IDisposable
|
||||
{
|
||||
public int Length;
|
||||
public IntPtr RootDirectory;
|
||||
public uint Attributes;
|
||||
public IntPtr SecurityDescriptor;
|
||||
public IntPtr SecurityQualityOfService;
|
||||
|
||||
private IntPtr objectName;
|
||||
|
||||
public OBJECT_ATTRIBUTES(string name, uint attrs)
|
||||
{
|
||||
Length = 0;
|
||||
RootDirectory = IntPtr.Zero;
|
||||
objectName = IntPtr.Zero;
|
||||
Attributes = attrs;
|
||||
SecurityDescriptor = IntPtr.Zero;
|
||||
SecurityQualityOfService = IntPtr.Zero;
|
||||
|
||||
Length = ClrFacade.SizeOf<OBJECT_ATTRIBUTES>();
|
||||
ObjectName = new UNICODE_STRING(name);
|
||||
}
|
||||
|
||||
public UNICODE_STRING ObjectName
|
||||
{
|
||||
get
|
||||
{
|
||||
return ClrFacade.PtrToStructure<UNICODE_STRING>(objectName);
|
||||
}
|
||||
|
||||
set
|
||||
{
|
||||
bool fDeleteOld = objectName != IntPtr.Zero;
|
||||
|
||||
if (!fDeleteOld)
|
||||
objectName = Marshal.AllocHGlobal(Marshal.SizeOf(value));
|
||||
|
||||
Marshal.StructureToPtr(value, objectName, fDeleteOld);
|
||||
}
|
||||
}
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
if (objectName != IntPtr.Zero)
|
||||
{
|
||||
ClrFacade.DestroyStructure<UNICODE_STRING>(objectName);
|
||||
Marshal.FreeHGlobal(objectName);
|
||||
objectName = IntPtr.Zero;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// These structures are filled in by Marshalling, so fields will be initialized
|
||||
// invisibly to the C# compiler, and some fields will not be used in C# code.
|
||||
#pragma warning disable 0649, 0169
|
||||
[StructLayout(LayoutKind.Explicit, Size = 8)]
|
||||
struct LARGE_INTEGER
|
||||
{
|
||||
[FieldOffset(0)]
|
||||
public Int64 QuadPart;
|
||||
[FieldOffset(0)]
|
||||
public UInt32 LowPart;
|
||||
[FieldOffset(4)]
|
||||
public Int32 HighPart;
|
||||
}
|
||||
#pragma warning restore 0649, 0169
|
||||
#endregion Structures
|
||||
|
||||
/// <summary>
|
||||
/// Wraps calls to Marshal functions that differ between .Net 4.5 and CoreCLR. .Net 4.5.1 types are not allowed for PowerShell.
|
||||
/// </summary>
|
||||
internal class ClrFacade
|
||||
{
|
||||
/// <summary>
|
||||
/// Private constructor to prevent auto-generation of a default constructor
|
||||
/// </summary>
|
||||
private ClrFacade()
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Facade for Marshal.SizeOf
|
||||
/// </summary>
|
||||
internal static int SizeOf<T>()
|
||||
{
|
||||
#if CORECLR
|
||||
// Marshal.SizeOf(Type) is obsolete in CoreCLR
|
||||
return Marshal.SizeOf<T>();
|
||||
#else
|
||||
return Marshal.SizeOf(typeof(T));
|
||||
#endif
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Facade for Marshal.DestroyStructure
|
||||
/// </summary>
|
||||
internal static void DestroyStructure<T>(IntPtr ptr)
|
||||
{
|
||||
#if CORECLR
|
||||
// Marshal.DestroyStructure(IntPtr, Type) is obsolete in CoreCLR
|
||||
Marshal.DestroyStructure<T>(ptr);
|
||||
#else
|
||||
Marshal.DestroyStructure(ptr, typeof(T));
|
||||
#endif
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Facade for Marshal.PtrToStructure
|
||||
/// </summary>
|
||||
internal static T PtrToStructure<T>(IntPtr ptr)
|
||||
{
|
||||
#if CORECLR
|
||||
// Marshal.PtrToStructure(IntPtr, Type) is obsolete in CoreCLR
|
||||
return Marshal.PtrToStructure<T>(ptr);
|
||||
#else
|
||||
return (T)Marshal.PtrToStructure(ptr, typeof(T));
|
||||
#endif
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Wraps Marshal.StructureToPtr to hide differences between the CLRs.
|
||||
/// </summary>
|
||||
internal static void StructureToPtr<T>(
|
||||
T structure,
|
||||
IntPtr ptr,
|
||||
bool deleteOld)
|
||||
{
|
||||
#if CORECLR
|
||||
Marshal.StructureToPtr<T>( structure, ptr, deleteOld );
|
||||
#else
|
||||
Marshal.StructureToPtr(structure, ptr, deleteOld);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
internal static class Win32
|
||||
{
|
||||
#region Constants
|
||||
// The following are masks for the predefined standard access types
|
||||
internal const UInt32 DELETE = 0x00010000;
|
||||
internal const UInt32 READ_CONTROL = 0x00020000;
|
||||
internal const UInt32 WRITE_DAC = 0x00040000;
|
||||
internal const UInt32 WRITE_OWNER = 0x00080000;
|
||||
internal const UInt32 SYNCHRONIZE = 0x00100000;
|
||||
|
||||
internal const UInt32 STANDARD_RIGHTS_REQUIRED = 0x000F0000;
|
||||
|
||||
internal const UInt32 STANDARD_RIGHTS_READ = READ_CONTROL;
|
||||
internal const UInt32 STANDARD_RIGHTS_WRITE = READ_CONTROL;
|
||||
internal const UInt32 STANDARD_RIGHTS_EXECUTE = READ_CONTROL;
|
||||
|
||||
|
||||
internal const UInt32 STANDARD_RIGHTS_ALL = 0x001F0000;
|
||||
|
||||
internal const UInt32 SPECIFIC_RIGHTS_ALL = 0x0000FFFF;
|
||||
|
||||
internal const UInt32 ACCESS_SYSTEM_SECURITY = 0x01000000;
|
||||
|
||||
internal const UInt32 MAXIMUM_ALLOWED = 0x02000000;
|
||||
|
||||
internal const UInt32 GENERIC_READ = 0x80000000;
|
||||
internal const UInt32 GENERIC_WRITE = 0x40000000;
|
||||
internal const UInt32 GENERIC_EXECUTE = 0x20000000;
|
||||
internal const UInt32 GENERIC_ALL = 0x10000000;
|
||||
|
||||
|
||||
// These constants control the behavior of the FormatMessage Windows API function
|
||||
internal const uint FORMAT_MESSAGE_ALLOCATE_BUFFER = 0x00000100;
|
||||
internal const uint FORMAT_MESSAGE_IGNORE_INSERTS = 0x00000200;
|
||||
internal const uint FORMAT_MESSAGE_FROM_SYSTEM = 0x00001000;
|
||||
internal const uint FORMAT_MESSAGE_ARGUMENT_ARRAY = 0x00002000;
|
||||
internal const uint FORMAT_MESSAGE_FROM_HMODULE = 0x00000800;
|
||||
internal const uint FORMAT_MESSAGE_FROM_STRING = 0x00000400;
|
||||
|
||||
#region Win32 Error Codes
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The operation completed successfully.
|
||||
//
|
||||
internal const Int32 ERROR_SUCCESS = 0;
|
||||
internal const Int32 NO_ERROR = ERROR_SUCCESS;
|
||||
|
||||
//
|
||||
// MessageId: ERROR_ACCESS_DENIED
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// Access is denied.
|
||||
//
|
||||
internal const int ERROR_ACCESS_DENIED = 5;
|
||||
|
||||
//
|
||||
// MessageId: ERROR_BAD_NETPATH
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The network path was not found.
|
||||
//
|
||||
internal const int ERROR_BAD_NETPATH = 53;
|
||||
|
||||
//
|
||||
// MessageId: ERROR_NETWORK_ACCESS_DENIED
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// Network access is denied.
|
||||
//
|
||||
internal const int ERROR_NETWORK_ACCESS_DENIED = 65;
|
||||
|
||||
//
|
||||
// MessageId: ERROR_INVALID_PARAMETER
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The parameter is incorrect.
|
||||
//
|
||||
internal const int ERROR_INVALID_PARAMETER = 87;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The file name is too long.
|
||||
//
|
||||
internal const Int32 ERROR_BUFFER_OVERFLOW = 111;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The data area passed to a system call is too small.
|
||||
//
|
||||
internal const Int32 ERROR_INSUFFICIENT_BUFFER = 122;
|
||||
|
||||
//
|
||||
// MessageId: ERROR_INVALID_LEVEL
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The system call level is not correct.
|
||||
//
|
||||
internal const int ERROR_INVALID_LEVEL = 124;
|
||||
|
||||
//
|
||||
// MessageId: ERROR_INVALID_FLAGS
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// Invalid flags.
|
||||
//
|
||||
internal const Int32 ERROR_INVALID_FLAGS = 1004;
|
||||
|
||||
//
|
||||
// MessageId: ERROR_ILL_FORMED_PASSWORD
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// Unable to update the password. The value provided for the new password contains values that are not allowed in passwords.
|
||||
//
|
||||
internal const UInt32 ERROR_ILL_FORMED_PASSWORD = 1324;
|
||||
|
||||
//
|
||||
// MessageId: ERROR_PASSWORD_RESTRICTION
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// Unable to update the password. The value provided for the new password does not meet the length, complexity, or history requirements of the domain.
|
||||
//
|
||||
internal const UInt32 ERROR_PASSWORD_RESTRICTION = 1325;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// No mapping between account names and security IDs was done.
|
||||
//
|
||||
internal const Int32 ERROR_NONE_MAPPED = 1332;
|
||||
|
||||
internal const int NERR_Success = 0;
|
||||
// NERR_BASE is the base of error codes from network utilities,
|
||||
// chosen to avoid conflict with system and redirector error codes.
|
||||
// 2100 is a value that has been assigned to us by system.
|
||||
internal const int NERR_BASE = 2100;
|
||||
|
||||
internal const int NERR_BadPassword = NERR_BASE + 103; // The password parameter is invalid.
|
||||
internal const int NERR_UserNotFound = NERR_BASE + 121; // The user name could not be found.
|
||||
internal const int NERR_NotPrimary = NERR_BASE + 126; // This operation is only allowed on the primary domain controller of the domain.
|
||||
internal const int NERR_SpeGroupOp = NERR_BASE + 134; // This operation is not allowed on this special group.
|
||||
internal const int NERR_PasswordTooShort = NERR_BASE + 145; // The password does not meet the password policy requirements. Check the minimum password length, password complexity and password history requirements.
|
||||
internal const int NERR_InvalidComputer = NERR_BASE + 251; // This computer name is invalid.
|
||||
internal const int NERR_LastAdmin = NERR_BASE + 352; // This operation is not allowed on the last administrative account.
|
||||
#endregion Win32 Error Codes
|
||||
|
||||
|
||||
#region SECURITY_DESCRIPTOR Control Flags
|
||||
internal const UInt16 SE_DACL_PRESENT = 0x0004;
|
||||
internal const UInt16 SE_SELF_RELATIVE = 0x8000;
|
||||
#endregion SECURITY_DESCRIPTOR Control Flags
|
||||
|
||||
#region SECURITY_INFORMATION Values
|
||||
internal const int DACL_SECURITY_INFORMATION = 0x00000004;
|
||||
#endregion SECURITY_INFORMATION Values
|
||||
#endregion Constants
|
||||
|
||||
#region Win32 Functions
|
||||
[DllImport(PInvokeDllNames.LookupAccountSidDllName, CharSet = CharSet.Unicode, SetLastError = true)]
|
||||
internal static extern bool LookupAccountSid(string systemName,
|
||||
byte[] accountSid,
|
||||
StringBuilder accountName,
|
||||
ref Int32 nameLength,
|
||||
StringBuilder domainName,
|
||||
ref Int32 domainNameLength,
|
||||
out SID_NAME_USE use);
|
||||
|
||||
[DllImport(PInvokeDllNames.LookupAccountNameDllName, CharSet = CharSet.Unicode, SetLastError = true)]
|
||||
internal static extern bool LookupAccountName(string systemName,
|
||||
string accountName,
|
||||
[MarshalAs(UnmanagedType.LPArray)]
|
||||
byte[] sid,
|
||||
ref uint sidLength,
|
||||
StringBuilder domainName,
|
||||
ref uint domainNameLength,
|
||||
out SID_NAME_USE peUse);
|
||||
|
||||
[DllImport(PInvokeDllNames.GetComputerNameDllName, CharSet=CharSet.Unicode, SetLastError=true)]
|
||||
internal static extern bool GetComputerName(StringBuilder name, ref uint size);
|
||||
|
||||
[DllImport(PInvokeDllNames.GetSecurityDescriptorDaclDllName, SetLastError = true)]
|
||||
[return: MarshalAs(UnmanagedType.Bool)]
|
||||
internal static extern bool GetSecurityDescriptorDacl(IntPtr pSecurityDescriptor,
|
||||
[MarshalAs(UnmanagedType.Bool)]
|
||||
out bool bDaclPresent,
|
||||
out IntPtr pDacl,
|
||||
[MarshalAs(UnmanagedType.Bool)]
|
||||
out bool bDaclDefaulted);
|
||||
|
||||
[DllImport(PInvokeDllNames.SetSecurityDescriptorDaclDllName, SetLastError = true)]
|
||||
[return: MarshalAs(UnmanagedType.Bool)]
|
||||
internal static extern bool SetSecurityDescriptorDacl(IntPtr pSecurityDescriptor,
|
||||
[MarshalAs(UnmanagedType.Bool)]
|
||||
bool bDaclPresent,
|
||||
IntPtr pDacl,
|
||||
[MarshalAs(UnmanagedType.Bool)]
|
||||
bool bDaclDefaulted);
|
||||
|
||||
[DllImport(PInvokeDllNames.FormatMessageDllName, SetLastError = true)]
|
||||
internal static extern uint FormatMessage(uint dwFlags,
|
||||
IntPtr lpSource,
|
||||
uint dwMessageId,
|
||||
uint dwLanguageId,
|
||||
[Out] StringBuilder lpBuffer,
|
||||
uint nSize,
|
||||
string[] Arguments);
|
||||
|
||||
[DllImport("ntdll.dll")]
|
||||
internal static extern uint RtlNtStatusToDosError(uint ntStatus);
|
||||
#endregion Win32 Functions
|
||||
|
||||
#region LSA Functions
|
||||
[DllImport(PInvokeDllNames.LsaOpenPolicyDllName, CharSet = CharSet.Unicode)]
|
||||
internal static extern UInt32 LsaOpenPolicy(ref UNICODE_STRING SystemName,
|
||||
ref OBJECT_ATTRIBUTES ObjectAttributes,
|
||||
uint DesiredAccess,
|
||||
out IntPtr PolicyHandle);
|
||||
|
||||
[DllImport(PInvokeDllNames.LsaQueryInformationPolicyDllName, CharSet = CharSet.Unicode)]
|
||||
internal static extern UInt32 LsaQueryInformationPolicy(IntPtr lsaHandle,
|
||||
POLICY_INFORMATION_CLASS infoClass,
|
||||
out IntPtr buffer);
|
||||
|
||||
[DllImport(PInvokeDllNames.LsaFreeMemoryDllName)]
|
||||
internal static extern UInt32 LsaFreeMemory(IntPtr buffer);
|
||||
|
||||
[DllImport(PInvokeDllNames.LsaCloseDllName)]
|
||||
internal static extern UInt32 LsaClose(IntPtr handle);
|
||||
|
||||
[DllImport("api-ms-win-security-lsalookup-l1-1-2.dll")]
|
||||
internal static extern UInt32 LsaLookupUserAccountType([MarshalAs(UnmanagedType.LPArray)] byte[] Sid,
|
||||
out LSA_USER_ACCOUNT_TYPE accountType);
|
||||
#endregion LSA Functions
|
||||
}
|
||||
}
|
516
src/Microsoft.PowerShell.LocalAccounts/LocalAccounts/NtStatus.cs
Normal file
516
src/Microsoft.PowerShell.LocalAccounts/LocalAccounts/NtStatus.cs
Normal file
|
@ -0,0 +1,516 @@
|
|||
|
||||
namespace System.Management.Automation.SecurityAccountsManager.Native
|
||||
{
|
||||
internal static class NtStatus
|
||||
{
|
||||
#region Constants
|
||||
//
|
||||
// These values are taken from ntstatus.h
|
||||
//
|
||||
|
||||
//
|
||||
// Severity codes
|
||||
//
|
||||
public const UInt32 STATUS_SEVERITY_WARNING = 0x2;
|
||||
public const UInt32 STATUS_SEVERITY_SUCCESS = 0x0;
|
||||
public const UInt32 STATUS_SEVERITY_INFORMATIONAL = 0x1;
|
||||
public const UInt32 STATUS_SEVERITY_ERROR = 0x3;
|
||||
|
||||
|
||||
public const UInt32 STATUS_SUCCESS = 0x00000000;
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// Returned by enumeration APIs to indicate more information is available to successive calls.
|
||||
//
|
||||
public const UInt32 STATUS_MORE_ENTRIES = 0x00000105;
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Standard Information values
|
||||
//
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// {Object Exists}
|
||||
// An attempt was made to create an object and the object name already existed.
|
||||
//
|
||||
public const UInt32 STATUS_OBJECT_NAME_EXISTS = 0x40000000;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// {Password Too Complex}
|
||||
// The Windows password is too complex to be converted to a LAN Manager password. The LAN Manager password returned is a NULL string.
|
||||
//
|
||||
public const UInt32 STATUS_NULL_LM_PASSWORD = 0x4000000D;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// {Access Denied}
|
||||
// A process has requested access to an object, but has not been granted those access rights.
|
||||
//
|
||||
public const UInt32 STATUS_ACCESS_DENIED = 0xC0000022;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The name provided is not a properly formed account name.
|
||||
//
|
||||
public const UInt32 STATUS_INVALID_ACCOUNT_NAME = 0xC0000062;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The specified account already exists.
|
||||
//
|
||||
public const UInt32 STATUS_USER_EXISTS = 0xC0000063;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The specified account does not exist.
|
||||
//
|
||||
public const UInt32 STATUS_NO_SUCH_USER = 0xC0000064; // ntsubauth
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The specified group already exists.
|
||||
//
|
||||
public const UInt32 STATUS_GROUP_EXISTS = 0xC0000065;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The specified group does not exist.
|
||||
//
|
||||
public const UInt32 STATUS_NO_SUCH_GROUP = 0xC0000066;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The specified user account is already in the specified group account. Also used to indicate a group cannot be deleted because it contains a member.
|
||||
//
|
||||
public const UInt32 STATUS_MEMBER_IN_GROUP = 0xC0000067;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The specified user account is not a member of the specified group account.
|
||||
//
|
||||
public const UInt32 STATUS_MEMBER_NOT_IN_GROUP = 0xC0000068;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// Indicates the requested operation would disable, delete or could prevent logon for an administration account.
|
||||
// This is not allowed to prevent creating a situation in which the system cannot be administrated.
|
||||
//
|
||||
public const UInt32 STATUS_LAST_ADMIN = 0xC0000069;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// When trying to update a password, this return status indicates that the value provided as the current password is not correct.
|
||||
//
|
||||
public const UInt32 STATUS_WRONG_PASSWORD = 0xC000006A; // ntsubauth
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// When trying to update a password, this return status indicates that the value provided for the new password contains values that are not allowed in passwords.
|
||||
//
|
||||
public const UInt32 STATUS_ILL_FORMED_PASSWORD = 0xC000006B;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// When trying to update a password, this status indicates that some password update rule has been violated. For example, the password may not meet length criteria.
|
||||
//
|
||||
public const UInt32 STATUS_PASSWORD_RESTRICTION = 0xC000006C; // ntsubauth
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The user account's password has expired.
|
||||
//
|
||||
public const UInt32 STATUS_PASSWORD_EXPIRED = 0xC0000071; // ntsubauth
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The referenced account is currently disabled and may not be logged on to.
|
||||
//
|
||||
public const UInt32 STATUS_ACCOUNT_DISABLED = 0xC0000072; // ntsubauth
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// None of the information to be translated has been translated.
|
||||
//
|
||||
public const UInt32 STATUS_NONE_MAPPED = 0xC0000073;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// Indicates the sub-authority value is invalid for the particular use.
|
||||
//
|
||||
public const UInt32 STATUS_INVALID_SUB_AUTHORITY = 0xC0000076;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// Indicates the ACL structure is not valid.
|
||||
//
|
||||
public const UInt32 STATUS_INVALID_ACL = 0xC0000077;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// Indicates the SID structure is not valid.
|
||||
//
|
||||
public const UInt32 STATUS_INVALID_SID = 0xC0000078;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// Indicates the SECURITY_DESCRIPTOR structure is not valid.
|
||||
//
|
||||
public const UInt32 STATUS_INVALID_SECURITY_DESCR = 0xC0000079;
|
||||
|
||||
//
|
||||
// Network specific errors.
|
||||
//
|
||||
//
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The request is not supported.
|
||||
//
|
||||
public const UInt32 STATUS_NOT_SUPPORTED = 0xC00000BB;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// This remote computer is not listening.
|
||||
//
|
||||
public const UInt32 STATUS_REMOTE_NOT_LISTENING = 0xC00000BC;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// Network access is denied.
|
||||
//
|
||||
public const UInt32 STATUS_NETWORK_ACCESS_DENIED = 0xC00000CA;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// Indicates an attempt was made to operate on the security of an object that does not have security associated with it.
|
||||
//
|
||||
public const UInt32 STATUS_NO_SECURITY_ON_OBJECT = 0xC00000D7;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// An internal error occurred.
|
||||
//
|
||||
public const UInt32 STATUS_INTERNAL_ERROR = 0xC00000E5;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// Indicates a security descriptor is not in the necessary format (absolute or self-relative).
|
||||
//
|
||||
public const UInt32 STATUS_BAD_DESCRIPTOR_FORMAT = 0xC00000E7;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// A specified name string is too long for its intended use.
|
||||
//
|
||||
public const UInt32 STATUS_NAME_TOO_LONG = 0xC0000106;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// Indicates a name specified as a remote computer name is syntactically invalid.
|
||||
//
|
||||
public const UInt32 STATUS_INVALID_COMPUTER_NAME = 0xC0000122;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// Indicates an operation has been attempted on a built-in (special) SAM account which is incompatible with built-in accounts. For example, built-in accounts cannot be deleted.
|
||||
//
|
||||
public const UInt32 STATUS_SPECIAL_ACCOUNT = 0xC0000124;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The operation requested may not be performed on the specified group because it is a built-in special group.
|
||||
//
|
||||
public const UInt32 STATUS_SPECIAL_GROUP = 0xC0000125;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The operation requested may not be performed on the specified user because it is a built-in special user.
|
||||
//
|
||||
public const UInt32 STATUS_SPECIAL_USER = 0xC0000126;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// Indicates a member cannot be removed from a group because the group is currently the member's primary group.
|
||||
//
|
||||
public const UInt32 STATUS_MEMBERS_PRIMARY_GROUP = 0xC0000127;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The specified local group does not exist.
|
||||
//
|
||||
public const UInt32 STATUS_NO_SUCH_ALIAS = 0xC0000151;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The specified account name is not a member of the group.
|
||||
//
|
||||
public const UInt32 STATUS_MEMBER_NOT_IN_ALIAS = 0xC0000152;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The specified account name is already a member of the group.
|
||||
//
|
||||
public const UInt32 STATUS_MEMBER_IN_ALIAS = 0xC0000153;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The specified local group already exists.
|
||||
//
|
||||
public const UInt32 STATUS_ALIAS_EXISTS = 0xC0000154;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// A member could not be added to or removed from the local group because the member does not exist.
|
||||
//
|
||||
public const UInt32 STATUS_NO_SUCH_MEMBER = 0xC000017A;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// A new member could not be added to a local group because the member has the wrong account type.
|
||||
//
|
||||
public const UInt32 STATUS_INVALID_MEMBER = 0xC000017B;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The user's account has expired.
|
||||
//
|
||||
public const UInt32 STATUS_ACCOUNT_EXPIRED = 0xC0000193; // ntsubauth
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// {Invalid ACE Condition}
|
||||
// The specified access control entry (ACE) contains an invalid condition.
|
||||
//
|
||||
public const UInt32 STATUS_INVALID_ACE_CONDITION = 0xC00001A2;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The user's password must be changed before signing in.
|
||||
//
|
||||
public const UInt32 STATUS_PASSWORD_MUST_CHANGE = 0xC0000224; // ntsubauth
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The object was not found.
|
||||
//
|
||||
public const UInt32 STATUS_NOT_FOUND = 0xC0000225;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// Could not find a domain controller for this domain.
|
||||
//
|
||||
public const UInt32 STATUS_DOMAIN_CONTROLLER_NOT_FOUND = 0xC0000233;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The user account has been automatically locked because too many invalid logon attempts or password change attempts have been requested.
|
||||
//
|
||||
public const UInt32 STATUS_ACCOUNT_LOCKED_OUT = 0xC0000234; // ntsubauth
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The password provided is too short to meet the policy of your user account. Please choose a longer password.
|
||||
//
|
||||
public const UInt32 STATUS_PWD_TOO_SHORT = 0xC000025A;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The policy of your user account does not allow you to change passwords too frequently. This is done to prevent users from changing back to a familiar, but potentially discovered, password. If you feel your password has been compromised then please contact your administrator immediately to have a new one assigned.
|
||||
//
|
||||
public const UInt32 STATUS_PWD_TOO_RECENT = 0xC000025B;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// You have attempted to change your password to one that you have used in the past. The policy of your user account does not allow this. Please select a password that you have not previously used.
|
||||
//
|
||||
public const UInt32 STATUS_PWD_HISTORY_CONFLICT = 0xC000025C;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The password provided is too long to meet the policy of your user account. Please choose a shorter password.
|
||||
//
|
||||
public const UInt32 STATUS_PWD_TOO_LONG = 0xC000027A;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// Only an administrator can modify the membership list of an administrative group.
|
||||
//
|
||||
public const UInt32 STATUS_DS_SENSITIVE_GROUP_VIOLATION = 0xC00002CD;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The specified group type is invalid.
|
||||
//
|
||||
public const UInt32 STATUS_DS_INVALID_GROUP_TYPE = 0xC00002D4;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// A local group cannot have another cross domain local group as a member.
|
||||
//
|
||||
public const UInt32 STATUS_DS_LOCAL_CANT_HAVE_CROSSDOMAIN_LOCAL_MEMBER = 0xC00002DB;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// Cannot change to security disabled group because of having primary members in this group.
|
||||
//
|
||||
public const UInt32 STATUS_DS_HAVE_PRIMARY_MEMBERS = 0xC00002DC;
|
||||
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// EAS policy requires that the user change their password before this operation can be performed.
|
||||
//
|
||||
public const UInt32 STATUS_PASSWORD_CHANGE_REQUIRED = 0xC000030C;
|
||||
|
||||
#endregion Constants
|
||||
|
||||
#region Public Methods
|
||||
/// <summary>
|
||||
/// Determine if an NTSTATUS value indicates Success
|
||||
/// </summary>
|
||||
/// <param name="ntstatus">The NTSTATUS value returned from native functions.</param>
|
||||
/// <returns>
|
||||
/// True if the NTSTATUS value indicates success, false otherwise.
|
||||
/// </returns>
|
||||
public static bool IsSuccess(UInt32 ntstatus)
|
||||
{
|
||||
return Severity(ntstatus) == STATUS_SEVERITY_SUCCESS;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Determine if an NTSTATUS value indicates an Error
|
||||
/// </summary>
|
||||
/// <param name="ntstatus">The NTSTATUS value returned from native functions.</param>
|
||||
/// <returns>
|
||||
/// True if the NTSTATUS value indicates an error, false otherwise.
|
||||
/// </returns>
|
||||
public static bool IsError(UInt32 ntstatus)
|
||||
{
|
||||
return Severity(ntstatus) == STATUS_SEVERITY_ERROR;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Determine if an NTSTATUS value indicates a Warning
|
||||
/// </summary>
|
||||
/// <param name="ntstatus">The NTSTATUS value returned from native functions.</param>
|
||||
/// <returns>
|
||||
/// True if the NTSTATUS value indicates a warning, false otherwise.
|
||||
/// </returns>
|
||||
public static bool IsWarning(UInt32 ntstatus)
|
||||
{
|
||||
return Severity(ntstatus) == STATUS_SEVERITY_WARNING;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Determine if an NTSTATUS value indicates that the value is Informational.
|
||||
/// </summary>
|
||||
/// <param name="ntstatus">The NTSTATUS value returned from native functions.</param>
|
||||
/// <returns>
|
||||
/// True if the NTSTATUS value indicates that it is informational, false otherwise.
|
||||
/// </returns>
|
||||
public static bool IsInformational(UInt32 ntstatus)
|
||||
{
|
||||
return Severity(ntstatus) == STATUS_SEVERITY_INFORMATIONAL;
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Return the Severity part of an NTSTATUS value
|
||||
/// </summary>
|
||||
/// <param name="ntstatus">The NTSTATUS value returned from native functions.</param>
|
||||
/// <returns>
|
||||
/// One of the STATUS_SEVERITY_* values
|
||||
/// </returns>
|
||||
public static uint Severity(UInt32 ntstatus)
|
||||
{
|
||||
return ntstatus >> 30;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Return the Facility part of an NSTATUS value
|
||||
/// </summary>
|
||||
/// <param name="ntstatus">The NTSTATUS value returned from native functions.</param>
|
||||
/// <returns>
|
||||
/// The value of the Facility portion of an NTSTATUS value.
|
||||
/// </returns>
|
||||
public static uint Facility(UInt32 ntstatus)
|
||||
{
|
||||
return (ntstatus >> 16) & 0x0FFF;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Return the Code part of an NTSTATUS value
|
||||
/// </summary>
|
||||
/// <param name="ntstatus">The NTSTATUS value returned from native functions.</param>
|
||||
/// <returns>
|
||||
/// The value of the Code portion of an NTSTATUS value.
|
||||
/// </returns>
|
||||
public static uint Code(UInt32 ntstatus)
|
||||
{
|
||||
return ntstatus & 0xFFFF;
|
||||
}
|
||||
#endregion Public Methods
|
||||
}
|
||||
}
|
|
@ -0,0 +1,48 @@
|
|||
//
|
||||
// Copyright (C) Microsoft. All rights reserved.
|
||||
//
|
||||
|
||||
namespace System.Management.Automation
|
||||
{
|
||||
/// <summary>
|
||||
/// PinvokeDllNames contains the DLL names to be use for PInvoke in FullCLR/CoreCLR powershell.
|
||||
///
|
||||
/// * When adding a new DLL name here, make sure that you add both the FullCLR and CoreCLR version
|
||||
/// of it. Add the comment '/*COUNT*/' with the new DLL name, and make sure the 'COUNT' is the
|
||||
/// same for both FullCLR and CoreCLR DLL names.
|
||||
/// </summary>
|
||||
internal static class PInvokeDllNames
|
||||
{
|
||||
#if CORECLR
|
||||
internal const string GetLastErrorDllName = "api-ms-win-core-errorhandling-l1-1-0.dll"; /* 1*/
|
||||
internal const string LookupAccountSidDllName = "api-ms-win-security-lsalookup-l2-1-1.dll"; /* 2*/
|
||||
internal const string IsValidSidDllName = "api-ms-win-security-base-l1-2-0.dll"; /* 3*/
|
||||
internal const string GetLengthSidDllName = "api-ms-win-security-base-l1-2-0.dll"; /* 4*/
|
||||
internal const string LsaFreeMemoryDllName = "api-ms-win-security-lsapolicy-l1-1-0.dll"; /* 5*/
|
||||
internal const string LsaOpenPolicyDllName = "api-ms-win-security-lsapolicy-l1-1-0.dll"; /* 6*/
|
||||
internal const string LsaQueryInformationPolicyDllName = "api-ms-win-security-lsapolicy-l1-1-0.dll"; /* 7*/
|
||||
internal const string LsaCloseDllName = "api-ms-win-security-lsapolicy-l1-1-0.dll"; /* 8*/
|
||||
internal const string LookupAccountNameDllName = "api-ms-win-security-lsalookup-l2-1-1.dll"; /* 9*/
|
||||
internal const string GetComputerNameDllName = "api-ms-win-downlevel-kernel32-l2-1-0.dll"; /*10*/
|
||||
internal const string GetSecurityDescriptorDaclDllName = "api-ms-win-security-base-l1-2-0"; /*11*/
|
||||
internal const string SetSecurityDescriptorDaclDllName = "api-ms-win-security-base-l1-2-0"; /*12*/
|
||||
internal const string FormatMessageDllName = "api-ms-win-core-localization-l1-2-1"; /*13*/
|
||||
internal const string GetVersionExDllName = "api-ms-win-core-sysinfo-l1-2-1.dll"; /*14*/
|
||||
#else
|
||||
internal const string GetLastErrorDllName = "kernel32.dll"; /* 1*/
|
||||
internal const string LookupAccountSidDllName = "advapi32.dll"; /* 2*/
|
||||
internal const string IsValidSidDllName = "advapi32.dll"; /* 3*/
|
||||
internal const string GetLengthSidDllName = "advapi32.dll"; /* 4*/
|
||||
internal const string LsaFreeMemoryDllName = "advapi32.dll"; /* 5*/
|
||||
internal const string LsaOpenPolicyDllName = "advapi32.dll"; /* 6*/
|
||||
internal const string LsaQueryInformationPolicyDllName = "advapi32.dll"; /* 7*/
|
||||
internal const string LsaCloseDllName = "advapi32.dll"; /* 8*/
|
||||
internal const string LookupAccountNameDllName = "advapi32.dll"; /* 9*/
|
||||
internal const string GetComputerNameDllName = "kernel32.dll"; /*10*/
|
||||
internal const string GetSecurityDescriptorDaclDllName = "advapi32.dll"; /*11*/
|
||||
internal const string SetSecurityDescriptorDaclDllName = "advapi32.dll"; /*12*/
|
||||
internal const string FormatMessageDllName = "kernel32.dll"; /*13*/
|
||||
internal const string GetVersionExDllName = "kernel32.dll"; /*14*/
|
||||
#endif
|
||||
}
|
||||
}
|
|
@ -0,0 +1,7 @@
|
|||
using System.Reflection;
|
||||
|
||||
// General Information about an assembly is controlled through the following
|
||||
// set of attributes. Change these attribute values to modify the information
|
||||
// associated with an assembly.
|
||||
[assembly: AssemblyTitle("LocalAccounts")]
|
||||
[assembly: AssemblyDescription("PowerShell cmdlet for local accounts.")]
|
3300
src/Microsoft.PowerShell.LocalAccounts/LocalAccounts/Sam.cs
Normal file
3300
src/Microsoft.PowerShell.LocalAccounts/LocalAccounts/Sam.cs
Normal file
File diff suppressed because it is too large
Load diff
530
src/Microsoft.PowerShell.LocalAccounts/LocalAccounts/SamApi.cs
Normal file
530
src/Microsoft.PowerShell.LocalAccounts/LocalAccounts/SamApi.cs
Normal file
|
@ -0,0 +1,530 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Runtime.InteropServices;
|
||||
|
||||
//using System.Management.Automation.SecurityAccountsManager.Native;
|
||||
|
||||
namespace System.Management.Automation.SecurityAccountsManager.Native.NtSam
|
||||
{
|
||||
#region Enums
|
||||
internal enum ALIAS_INFORMATION_CLASS
|
||||
{
|
||||
AliasGeneralInformation = 1,
|
||||
AliasNameInformation,
|
||||
AliasAdminCommentInformation,
|
||||
AliasReplicationInformation,
|
||||
AliasExtendedInformation,
|
||||
}
|
||||
|
||||
internal enum GROUP_INFORMATION_CLASS
|
||||
{
|
||||
GroupGeneralInformation = 1,
|
||||
GroupNameInformation,
|
||||
GroupAttributeInformation,
|
||||
GroupAdminCommentInformation,
|
||||
GroupReplicationInformation
|
||||
}
|
||||
|
||||
internal enum USER_INFORMATION_CLASS
|
||||
{
|
||||
UserGeneralInformation = 1,
|
||||
UserPreferencesInformation,
|
||||
UserLogonInformation,
|
||||
UserLogonHoursInformation,
|
||||
UserAccountInformation,
|
||||
UserNameInformation,
|
||||
UserAccountNameInformation,
|
||||
UserFullNameInformation,
|
||||
UserPrimaryGroupInformation,
|
||||
UserHomeInformation,
|
||||
UserScriptInformation,
|
||||
UserProfileInformation,
|
||||
UserAdminCommentInformation,
|
||||
UserWorkStationsInformation,
|
||||
UserSetPasswordInformation,
|
||||
UserControlInformation,
|
||||
UserExpiresInformation,
|
||||
UserInternal1Information,
|
||||
UserInternal2Information,
|
||||
UserParametersInformation,
|
||||
UserAllInformation,
|
||||
UserInternal3Information,
|
||||
UserInternal4Information,
|
||||
UserInternal5Information,
|
||||
UserInternal4InformationNew,
|
||||
UserInternal5InformationNew,
|
||||
UserInternal6Information,
|
||||
UserExtendedInformation,
|
||||
UserLogonUIInformation,
|
||||
}
|
||||
|
||||
#endregion Enums
|
||||
|
||||
#region Structures
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
internal struct SR_SECURITY_DESCRIPTOR
|
||||
{
|
||||
public UInt32 Length;
|
||||
public IntPtr SecurityDescriptor;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
internal struct LOGON_HOURS
|
||||
{
|
||||
public UInt16 UnitsPerWeek;
|
||||
|
||||
//
|
||||
// UnitsPerWeek is the number of equal length time units the week is
|
||||
// divided into. This value is used to compute the length of the bit
|
||||
// string in logon_hours. Must be less than or equal to
|
||||
// SAM_UNITS_PER_WEEK (10080) for this release.
|
||||
//
|
||||
// LogonHours is a bit map of valid logon times. Each bit represents
|
||||
// a unique division in a week. The largest bit map supported is 1260
|
||||
// bytes (10080 bits), which represents minutes per week. In this case
|
||||
// the first bit (bit 0, byte 0) is Sunday, 00:00:00 - 00-00:59; bit 1,
|
||||
// byte 0 is Sunday, 00:01:00 - 00:01:59, etc. A NULL pointer means
|
||||
// DONT_CHANGE for SamSetInformationUser() calls.
|
||||
//
|
||||
|
||||
public IntPtr LogonHours;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential, Pack=4)]
|
||||
internal struct USER_ALL_INFORMATION
|
||||
{
|
||||
public LARGE_INTEGER LastLogon;
|
||||
public LARGE_INTEGER LastLogoff;
|
||||
public LARGE_INTEGER PasswordLastSet;
|
||||
public LARGE_INTEGER AccountExpires;
|
||||
public LARGE_INTEGER PasswordCanChange;
|
||||
public LARGE_INTEGER PasswordMustChange;
|
||||
public UNICODE_STRING UserName;
|
||||
public UNICODE_STRING FullName;
|
||||
public UNICODE_STRING HomeDirectory;
|
||||
public UNICODE_STRING HomeDirectoryDrive;
|
||||
public UNICODE_STRING ScriptPath;
|
||||
public UNICODE_STRING ProfilePath;
|
||||
public UNICODE_STRING AdminComment;
|
||||
public UNICODE_STRING WorkStations;
|
||||
public UNICODE_STRING UserComment;
|
||||
public UNICODE_STRING Parameters;
|
||||
public UNICODE_STRING LmPassword;
|
||||
public UNICODE_STRING NtPassword;
|
||||
public UNICODE_STRING PrivateData;
|
||||
public SR_SECURITY_DESCRIPTOR SecurityDescriptor;
|
||||
public UInt32 UserId;
|
||||
public UInt32 PrimaryGroupId;
|
||||
public UInt32 UserAccountControl;
|
||||
public UInt32 WhichFields;
|
||||
public LOGON_HOURS LogonHours;
|
||||
public UInt16 BadPasswordCount;
|
||||
public UInt16 LogonCount;
|
||||
public UInt16 CountryCode;
|
||||
public UInt16 CodePage;
|
||||
[MarshalAs(UnmanagedType.I1)]
|
||||
public bool LmPasswordPresent;
|
||||
[MarshalAs(UnmanagedType.I1)]
|
||||
public bool NtPasswordPresent;
|
||||
[MarshalAs(UnmanagedType.I1)]
|
||||
public bool PasswordExpired;
|
||||
[MarshalAs(UnmanagedType.I1)]
|
||||
public bool PrivateDataSensitive;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential, Pack=4)]
|
||||
internal struct USER_GENERAL_INFORMATION
|
||||
{
|
||||
public UNICODE_STRING UserName;
|
||||
public UNICODE_STRING FullName;
|
||||
public UInt32 PrimaryGroupId;
|
||||
public UNICODE_STRING AdminComment;
|
||||
public UNICODE_STRING UserComment;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential, Pack=4)]
|
||||
internal struct USER_LOGON_INFORMATION
|
||||
{
|
||||
public UNICODE_STRING UserName;
|
||||
public UNICODE_STRING FullName;
|
||||
public UInt32 UserId;
|
||||
public UInt32 PrimaryGroupId;
|
||||
public UNICODE_STRING HomeDirectory;
|
||||
public UNICODE_STRING HomeDirectoryDrive;
|
||||
public UNICODE_STRING ScriptPath;
|
||||
public UNICODE_STRING ProfilePath;
|
||||
public UNICODE_STRING WorkStations;
|
||||
public LARGE_INTEGER LastLogon;
|
||||
public LARGE_INTEGER LastLogoff;
|
||||
public LARGE_INTEGER PasswordLastSet;
|
||||
public LARGE_INTEGER PasswordCanChange;
|
||||
public LARGE_INTEGER PasswordMustChange;
|
||||
public LOGON_HOURS LogonHours;
|
||||
public UInt16 BadPasswordCount;
|
||||
public UInt16 LogonCount;
|
||||
public UInt32 UserAccountControl;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
internal struct USER_ACCOUNT_NAME_INFORMATION
|
||||
{
|
||||
public UNICODE_STRING UserName;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
internal struct USER_FULL_NAME_INFORMATION
|
||||
{
|
||||
public UNICODE_STRING FullName;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
internal struct USER_NAME_INFORMATION
|
||||
{
|
||||
public UNICODE_STRING UserName;
|
||||
public UNICODE_STRING FullName;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
internal struct USER_ADMIN_COMMENT_INFORMATION
|
||||
{
|
||||
UNICODE_STRING AdminComment;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
internal struct USER_EXPIRES_INFORMATION
|
||||
{
|
||||
//LARGE_INTEGER AccountExpires;
|
||||
public Int64 AccountExpires;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
internal struct USER_SET_PASSWORD_INFORMATION
|
||||
{
|
||||
public UNICODE_STRING Password;
|
||||
public bool PasswordExpired;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
internal struct USER_LOGON_HOURS_INFORMATION
|
||||
{
|
||||
public LOGON_HOURS LogonHours;
|
||||
}
|
||||
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
internal struct POLICY_PRIMARY_DOMAIN_INFO
|
||||
{
|
||||
public UNICODE_STRING Name;
|
||||
public IntPtr Sid;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
internal struct ALIAS_GENERAL_INFORMATION
|
||||
{
|
||||
public UNICODE_STRING Name;
|
||||
public UInt32 MemberCount;
|
||||
public UNICODE_STRING AdminComment;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
internal struct ALIAS_NAME_INFORMATION
|
||||
{
|
||||
public UNICODE_STRING Name;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
internal struct ALIAS_ADM_COMMENT_INFORMATION
|
||||
{
|
||||
public UNICODE_STRING AdminComment;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
internal struct SAMPR_GROUP_GENERAL_INFORMATION
|
||||
{
|
||||
public UNICODE_STRING Name;
|
||||
public UInt32 Attributes;
|
||||
public UInt32 MemberCount;
|
||||
public UNICODE_STRING AdminComment;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
internal struct SAMPR_GROUP_NAME_INFORMATION
|
||||
{
|
||||
public UNICODE_STRING Name;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
internal struct SAM_RID_ENUMERATION
|
||||
{
|
||||
public UInt32 RelativeId;
|
||||
public UNICODE_STRING Name;
|
||||
}
|
||||
#endregion Structures
|
||||
|
||||
/// <summary>
|
||||
/// Provides methods for invoking functions in the Windows
|
||||
/// Security Accounts Manager (SAM) API.
|
||||
/// </summary>
|
||||
internal static class SamApi
|
||||
{
|
||||
#region Constants
|
||||
// Account enumeration filters, may be combined by bitwise OR
|
||||
internal const UInt32 SAM_USER_ENUMERATION_FILTER_LOCAL = 0x00000001;
|
||||
internal const UInt32 SAM_USER_ENUMERATION_FILTER_INTERNET = 0x00000002;
|
||||
internal const UInt32 SAM_SERVER_LOOKUP_DOMAIN = 0x0020;
|
||||
|
||||
|
||||
//
|
||||
// Bits to be used in UserAllInformation's WhichFields field (to indicate
|
||||
// which items were queried or set).
|
||||
//
|
||||
internal const UInt32 USER_ALL_USERNAME = 0x00000001;
|
||||
internal const UInt32 USER_ALL_FULLNAME = 0x00000002;
|
||||
internal const UInt32 USER_ALL_USERID = 0x00000004;
|
||||
internal const UInt32 USER_ALL_PRIMARYGROUPID = 0x00000008;
|
||||
internal const UInt32 USER_ALL_ADMINCOMMENT = 0x00000010;
|
||||
internal const UInt32 USER_ALL_USERCOMMENT = 0x00000020;
|
||||
internal const UInt32 USER_ALL_HOMEDIRECTORY = 0x00000040;
|
||||
internal const UInt32 USER_ALL_HOMEDIRECTORYDRIVE = 0x00000080;
|
||||
internal const UInt32 USER_ALL_SCRIPTPATH = 0x00000100;
|
||||
internal const UInt32 USER_ALL_PROFILEPATH = 0x00000200;
|
||||
internal const UInt32 USER_ALL_WORKSTATIONS = 0x00000400;
|
||||
internal const UInt32 USER_ALL_LASTLOGON = 0x00000800;
|
||||
internal const UInt32 USER_ALL_LASTLOGOFF = 0x00001000;
|
||||
internal const UInt32 USER_ALL_LOGONHOURS = 0x00002000;
|
||||
internal const UInt32 USER_ALL_BADPASSWORDCOUNT = 0x00004000;
|
||||
internal const UInt32 USER_ALL_LOGONCOUNT = 0x00008000;
|
||||
internal const UInt32 USER_ALL_PASSWORDCANCHANGE = 0x00010000;
|
||||
internal const UInt32 USER_ALL_PASSWORDMUSTCHANGE = 0x00020000;
|
||||
internal const UInt32 USER_ALL_PASSWORDLASTSET = 0x00040000;
|
||||
internal const UInt32 USER_ALL_ACCOUNTEXPIRES = 0x00080000;
|
||||
internal const UInt32 USER_ALL_USERACCOUNTCONTROL = 0x00100000;
|
||||
internal const UInt32 USER_ALL_PARAMETERS = 0x00200000; // ntsubauth
|
||||
internal const UInt32 USER_ALL_COUNTRYCODE = 0x00400000;
|
||||
internal const UInt32 USER_ALL_CODEPAGE = 0x00800000;
|
||||
internal const UInt32 USER_ALL_NTPASSWORDPRESENT = 0x01000000; // field AND boolean
|
||||
internal const UInt32 USER_ALL_LMPASSWORDPRESENT = 0x02000000; // field AND boolean
|
||||
internal const UInt32 USER_ALL_PRIVATEDATA = 0x04000000; // field AND boolean
|
||||
internal const UInt32 USER_ALL_PASSWORDEXPIRED = 0x08000000;
|
||||
internal const UInt32 USER_ALL_SECURITYDESCRIPTOR = 0x10000000;
|
||||
internal const UInt32 USER_ALL_OWFPASSWORD = 0x20000000; // boolean
|
||||
|
||||
internal const UInt32 USER_ALL_UNDEFINED_MASK = 0xC0000000;
|
||||
|
||||
|
||||
//
|
||||
// Bit masks for the UserAccountControl member of the USER_ALL_INFORMATION structure
|
||||
//
|
||||
internal const UInt32 USER_ACCOUNT_DISABLED = 0x00000001;
|
||||
internal const UInt32 USER_HOME_DIRECTORY_REQUIRED = 0x00000002;
|
||||
internal const UInt32 USER_PASSWORD_NOT_REQUIRED = 0x00000004;
|
||||
internal const UInt32 USER_TEMP_DUPLICATE_ACCOUNT = 0x00000008;
|
||||
internal const UInt32 USER_NORMAL_ACCOUNT = 0x00000010;
|
||||
internal const UInt32 USER_MNS_LOGON_ACCOUNT = 0x00000020;
|
||||
internal const UInt32 USER_INTERDOMAIN_TRUST_ACCOUNT = 0x00000040;
|
||||
internal const UInt32 USER_WORKSTATION_TRUST_ACCOUNT = 0x00000080;
|
||||
internal const UInt32 USER_SERVER_TRUST_ACCOUNT = 0x00000100;
|
||||
internal const UInt32 USER_DONT_EXPIRE_PASSWORD = 0x00000200;
|
||||
internal const UInt32 USER_ACCOUNT_AUTO_LOCKED = 0x00000400;
|
||||
internal const UInt32 USER_ENCRYPTED_TEXT_PASSWORD_ALLOWED = 0x00000800;
|
||||
internal const UInt32 USER_SMARTCARD_REQUIRED = 0x00001000;
|
||||
internal const UInt32 USER_TRUSTED_FOR_DELEGATION = 0x00002000;
|
||||
internal const UInt32 USER_NOT_DELEGATED = 0x00004000;
|
||||
internal const UInt32 USER_USE_DES_KEY_ONLY = 0x00008000;
|
||||
internal const UInt32 USER_DONT_REQUIRE_PREAUTH = 0x00010000;
|
||||
internal const UInt32 USER_PASSWORD_EXPIRED = 0x00020000;
|
||||
internal const UInt32 USER_TRUSTED_TO_AUTHENTICATE_FOR_DELEGATION = 0x00040000;
|
||||
internal const UInt32 USER_NO_AUTH_DATA_REQUIRED = 0x00080000;
|
||||
internal const UInt32 USER_PARTIAL_SECRETS_ACCOUNT = 0x00100000;
|
||||
internal const UInt32 USER_USE_AES_KEYS = 0x00200000;
|
||||
|
||||
//
|
||||
// Access rights for user object
|
||||
//
|
||||
internal const UInt16 USER_CHANGE_PASSWORD = 0x0040;
|
||||
#endregion Constants
|
||||
|
||||
#region Sam Functions
|
||||
[DllImport("samlib.dll")]
|
||||
public static extern UInt32 SamConnect(ref UNICODE_STRING serverName,
|
||||
out IntPtr serverHandle,
|
||||
UInt32 desiredAccess,
|
||||
ref OBJECT_ATTRIBUTES objectAttributes);
|
||||
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamRidToSid(IntPtr objectHandle, UInt32 rid, out IntPtr sid);
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamCloseHandle(IntPtr serverHandle);
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamFreeMemory(IntPtr buffer);
|
||||
|
||||
#region Domain Functions
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamOpenDomain(IntPtr serverHandle,
|
||||
UInt32 desiredAccess,
|
||||
IntPtr domainId,
|
||||
out IntPtr domainHandle);
|
||||
#endregion Domain Functions
|
||||
|
||||
#region Alias Functions
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamEnumerateAliasesInDomain(IntPtr domainHandle,
|
||||
ref UInt32 enumerationContext,
|
||||
out IntPtr buffer,
|
||||
UInt32 preferredMaximumLength,
|
||||
out UInt32 countReturned);
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamCreateAliasInDomain(IntPtr domainHandle,
|
||||
IntPtr accountName, // PUNICODE_STRING
|
||||
UInt32 desiredAccess,
|
||||
out IntPtr aliasHandle,
|
||||
out UInt32 relativeId); // PULONG
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamOpenAlias(IntPtr domainHandle,
|
||||
UInt32 desiredAccess,
|
||||
UInt32 aliasId,
|
||||
out IntPtr aliasHandle);
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamQueryInformationAlias(IntPtr aliasHandle,
|
||||
ALIAS_INFORMATION_CLASS aliasInformationClass,
|
||||
out IntPtr buffer);
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamSetInformationAlias(IntPtr aliasHandle,
|
||||
ALIAS_INFORMATION_CLASS aliasInformationClass,
|
||||
IntPtr buffer);
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamDeleteAlias(IntPtr aliasHandle);
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamAddMemberToAlias(IntPtr aliasHandle,
|
||||
byte[] memberId); // PSID
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamAddMultipleMembersToAlias(IntPtr aliasHandle,
|
||||
IntPtr memberIds, // PSID
|
||||
UInt32 memberCount);
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamRemoveMemberFromAlias(IntPtr aliasHandle,
|
||||
byte[] memberId); // PSID
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamRemoveMultipleMembersFromAlias(IntPtr aliasHandle,
|
||||
IntPtr memberIds, // PSID
|
||||
UInt32 memberCount);
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamGetMembersInAlias(IntPtr aliasHandle,
|
||||
out IntPtr memberIds, // PSID **
|
||||
out UInt32 memberCount);
|
||||
#endregion Alias Functions
|
||||
|
||||
#region Group Functions
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamEnumerateGroupsInDomain(IntPtr domainHandle,
|
||||
ref UInt32 enumerationContext,
|
||||
out IntPtr buffer,
|
||||
UInt32 preferredMaximumLength,
|
||||
out UInt32 countReturned);
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamCreateGroupInDomain(IntPtr domainHandle,
|
||||
ref UNICODE_STRING accountName,
|
||||
UInt32 desiredAccess,
|
||||
out IntPtr groupHandle,
|
||||
out UInt32 relativeId);
|
||||
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamOpenGroup(IntPtr domainHandle,
|
||||
UInt32 desiredAccess,
|
||||
UInt32 groupId,
|
||||
out IntPtr groupHandle);
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamQueryInformationGroup(IntPtr groupHandle,
|
||||
GROUP_INFORMATION_CLASS groupInformationClass,
|
||||
out IntPtr buffer);
|
||||
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamSetInformationGroup(IntPtr groupHandle,
|
||||
GROUP_INFORMATION_CLASS groupInformationClass,
|
||||
IntPtr buffer);
|
||||
#endregion Group Functions
|
||||
|
||||
#region User Functions
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamOpenUser(IntPtr domainHandle,
|
||||
UInt32 desiredAccess,
|
||||
UInt32 userID,
|
||||
out IntPtr userHandle);
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamDeleteUser(IntPtr aliasHandle);
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamEnumerateUsersInDomain(IntPtr domainHandle,
|
||||
ref UInt32 enumerationContext,
|
||||
UInt32 userAccountControl,
|
||||
out IntPtr buffer,
|
||||
UInt32 preferredMaximumLength,
|
||||
out UInt32 countReturned);
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamEnumerateUsersInDomain2(IntPtr domainHandle,
|
||||
ref UInt32 enumerationContext,
|
||||
UInt32 userAccountControl,
|
||||
UInt32 filter,
|
||||
out IntPtr buffer,
|
||||
UInt32 preferredMaximumLength,
|
||||
out UInt32 countReturned);
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamCreateUserInDomain(IntPtr domainHandle,
|
||||
ref UNICODE_STRING accountName,
|
||||
UInt32 desiredAccess,
|
||||
out IntPtr userHandle,
|
||||
out UInt32 relativeId);
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamCreateUser2InDomain(IntPtr domainHandle,
|
||||
ref UNICODE_STRING accountName,
|
||||
Int32 accountType,
|
||||
UInt32 desiredAccess,
|
||||
out IntPtr userHandle,
|
||||
out UInt32 grantedAccess,
|
||||
out UInt32 relativeId);
|
||||
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamQueryInformationUser(IntPtr userHandle,
|
||||
USER_INFORMATION_CLASS userInformationClass,
|
||||
out IntPtr buffer);
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamSetInformationUser(IntPtr userHandle,
|
||||
USER_INFORMATION_CLASS userInformationClass,
|
||||
IntPtr buffer);
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamQuerySecurityObject(IntPtr objectHandle,
|
||||
UInt32 securityInformation,
|
||||
out IntPtr securityDescriptor);
|
||||
|
||||
[DllImport("samlib.dll")]
|
||||
internal static extern UInt32 SamSetSecurityObject(IntPtr objectHandle,
|
||||
UInt32 SecurityInformation,
|
||||
IntPtr SecurityDescriptor);
|
||||
#endregion User Functions
|
||||
#endregion Sam Functions
|
||||
}
|
||||
}
|
|
@ -0,0 +1,58 @@
|
|||
using System.Globalization;
|
||||
using System.Management.Automation.SecurityAccountsManager.Native;
|
||||
|
||||
namespace System.Management.Automation.SecurityAccountsManager
|
||||
{
|
||||
/// <summary>
|
||||
/// Contains utility functions for formatting localizable strings
|
||||
/// </summary>
|
||||
internal class StringUtil
|
||||
{
|
||||
internal static string Format(string str)
|
||||
{
|
||||
return string.Format(CultureInfo.CurrentCulture, str);
|
||||
}
|
||||
|
||||
internal static string Format(string fmt, string p0)
|
||||
{
|
||||
return string.Format(CultureInfo.CurrentCulture, fmt, p0);
|
||||
}
|
||||
|
||||
internal static string Format(string fmt, string p0, string p1)
|
||||
{
|
||||
return string.Format(CultureInfo.CurrentCulture, fmt, p0, p1);
|
||||
}
|
||||
|
||||
internal static string Format(string fmt, uint p0)
|
||||
{
|
||||
return string.Format(CultureInfo.CurrentCulture, fmt, p0);
|
||||
}
|
||||
internal static string Format(string fmt, int p0)
|
||||
{
|
||||
return string.Format(CultureInfo.CurrentCulture, fmt, p0);
|
||||
}
|
||||
|
||||
internal static string FormatMessage(uint messageId, string[] args)
|
||||
{
|
||||
var message = new System.Text.StringBuilder(256);
|
||||
UInt32 flags = Win32.FORMAT_MESSAGE_FROM_SYSTEM;
|
||||
|
||||
if (args == null)
|
||||
flags |= Win32.FORMAT_MESSAGE_IGNORE_INSERTS;
|
||||
else
|
||||
flags |= Win32.FORMAT_MESSAGE_ARGUMENT_ARRAY;
|
||||
|
||||
var length = Win32.FormatMessage(flags, IntPtr.Zero, messageId, 0, message, 256, args);
|
||||
|
||||
if (length > 0)
|
||||
return message.ToString();
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
internal static string GetSystemMessage(uint messageId)
|
||||
{
|
||||
return FormatMessage(messageId, null);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,234 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<root>
|
||||
<!--
|
||||
Microsoft ResX Schema
|
||||
|
||||
Version 2.0
|
||||
|
||||
The primary goals of this format is to allow a simple XML format
|
||||
that is mostly human readable. The generation and parsing of the
|
||||
various data types are done through the TypeConverter classes
|
||||
associated with the data types.
|
||||
|
||||
Example:
|
||||
|
||||
... ado.net/XML headers & schema ...
|
||||
<resheader name="resmimetype">text/microsoft-resx</resheader>
|
||||
<resheader name="version">2.0</resheader>
|
||||
<resheader name="reader">System.Resources.ResXResourceReader, System.Windows.Forms, ...</resheader>
|
||||
<resheader name="writer">System.Resources.ResXResourceWriter, System.Windows.Forms, ...</resheader>
|
||||
<data name="Name1"><value>this is my long string</value><comment>this is a comment</comment></data>
|
||||
<data name="Color1" type="System.Drawing.Color, System.Drawing">Blue</data>
|
||||
<data name="Bitmap1" mimetype="application/x-microsoft.net.object.binary.base64">
|
||||
<value>[base64 mime encoded serialized .NET Framework object]</value>
|
||||
</data>
|
||||
<data name="Icon1" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
|
||||
<value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
|
||||
<comment>This is a comment</comment>
|
||||
</data>
|
||||
|
||||
There are any number of "resheader" rows that contain simple
|
||||
name/value pairs.
|
||||
|
||||
Each data row contains a name, and value. The row also contains a
|
||||
type or mimetype. Type corresponds to a .NET class that support
|
||||
text/value conversion through the TypeConverter architecture.
|
||||
Classes that don't support this are serialized and stored with the
|
||||
mimetype set.
|
||||
|
||||
The mimetype is used for serialized objects, and tells the
|
||||
ResXResourceReader how to depersist the object. This is currently not
|
||||
extensible. For a given mimetype the value must be set accordingly:
|
||||
|
||||
Note - application/x-microsoft.net.object.binary.base64 is the format
|
||||
that the ResXResourceWriter will generate, however the reader can
|
||||
read any of the formats listed below.
|
||||
|
||||
mimetype: application/x-microsoft.net.object.binary.base64
|
||||
value : The object must be serialized with
|
||||
: System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
|
||||
: and then encoded with base64 encoding.
|
||||
|
||||
mimetype: application/x-microsoft.net.object.soap.base64
|
||||
value : The object must be serialized with
|
||||
: System.Runtime.Serialization.Formatters.Soap.SoapFormatter
|
||||
: and then encoded with base64 encoding.
|
||||
|
||||
mimetype: application/x-microsoft.net.object.bytearray.base64
|
||||
value : The object must be serialized into a byte array
|
||||
: using a System.ComponentModel.TypeConverter
|
||||
: and then encoded with base64 encoding.
|
||||
-->
|
||||
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
|
||||
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
|
||||
<xsd:element name="root" msdata:IsDataSet="true">
|
||||
<xsd:complexType>
|
||||
<xsd:choice maxOccurs="unbounded">
|
||||
<xsd:element name="metadata">
|
||||
<xsd:complexType>
|
||||
<xsd:sequence>
|
||||
<xsd:element name="value" type="xsd:string" minOccurs="0" />
|
||||
</xsd:sequence>
|
||||
<xsd:attribute name="name" use="required" type="xsd:string" />
|
||||
<xsd:attribute name="type" type="xsd:string" />
|
||||
<xsd:attribute name="mimetype" type="xsd:string" />
|
||||
<xsd:attribute ref="xml:space" />
|
||||
</xsd:complexType>
|
||||
</xsd:element>
|
||||
<xsd:element name="assembly">
|
||||
<xsd:complexType>
|
||||
<xsd:attribute name="alias" type="xsd:string" />
|
||||
<xsd:attribute name="name" type="xsd:string" />
|
||||
</xsd:complexType>
|
||||
</xsd:element>
|
||||
<xsd:element name="data">
|
||||
<xsd:complexType>
|
||||
<xsd:sequence>
|
||||
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
|
||||
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
|
||||
</xsd:sequence>
|
||||
<xsd:attribute name="name" type="xsd:string" use="required" msdata:Ordinal="1" />
|
||||
<xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
|
||||
<xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
|
||||
<xsd:attribute ref="xml:space" />
|
||||
</xsd:complexType>
|
||||
</xsd:element>
|
||||
<xsd:element name="resheader">
|
||||
<xsd:complexType>
|
||||
<xsd:sequence>
|
||||
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
|
||||
</xsd:sequence>
|
||||
<xsd:attribute name="name" type="xsd:string" use="required" />
|
||||
</xsd:complexType>
|
||||
</xsd:element>
|
||||
</xsd:choice>
|
||||
</xsd:complexType>
|
||||
</xsd:element>
|
||||
</xsd:schema>
|
||||
<resheader name="resmimetype">
|
||||
<value>text/microsoft-resx</value>
|
||||
</resheader>
|
||||
<resheader name="version">
|
||||
<value>2.0</value>
|
||||
</resheader>
|
||||
<resheader name="reader">
|
||||
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
|
||||
</resheader>
|
||||
<resheader name="writer">
|
||||
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
|
||||
</resheader>
|
||||
<data name="AccessDenied" xml:space="preserve">
|
||||
<value>Access denied.</value>
|
||||
</data>
|
||||
<data name="AccountNotFound" xml:space="preserve">
|
||||
<value>Account {0} was not found.</value>
|
||||
</data>
|
||||
<data name="ActionAddGroupMember" xml:space="preserve">
|
||||
<value>Add member {0}</value>
|
||||
</data>
|
||||
<data name="ActionDisableUser" xml:space="preserve">
|
||||
<value>Disable local user</value>
|
||||
</data>
|
||||
<data name="ActionEnableUser" xml:space="preserve">
|
||||
<value>Enable local user</value>
|
||||
</data>
|
||||
<data name="ActionNewGroup" xml:space="preserve">
|
||||
<value>Create new local group</value>
|
||||
</data>
|
||||
<data name="ActionNewUser" xml:space="preserve">
|
||||
<value>Create new local user</value>
|
||||
</data>
|
||||
<data name="ActionRemoveGroup" xml:space="preserve">
|
||||
<value>Remove local group</value>
|
||||
</data>
|
||||
<data name="ActionRemoveGroupMember" xml:space="preserve">
|
||||
<value>Remove member {0}</value>
|
||||
</data>
|
||||
<data name="ActionRemoveUser" xml:space="preserve">
|
||||
<value>Remove local user</value>
|
||||
</data>
|
||||
<data name="ActionRenameGroup" xml:space="preserve">
|
||||
<value>Rename local group to {0}</value>
|
||||
</data>
|
||||
<data name="ActionRenameUser" xml:space="preserve">
|
||||
<value>Rename local user to {0}</value>
|
||||
</data>
|
||||
<data name="ActionSetGroup" xml:space="preserve">
|
||||
<value>Modify local group</value>
|
||||
</data>
|
||||
<data name="ActionSetUser" xml:space="preserve">
|
||||
<value>Modify local user</value>
|
||||
</data>
|
||||
<data name="GroupExists" xml:space="preserve">
|
||||
<value>Group {0} already exists.</value>
|
||||
</data>
|
||||
<data name="GroupHasMembers" xml:space="preserve">
|
||||
<value>The group {0} still has members.</value>
|
||||
</data>
|
||||
<data name="GroupNotFound" xml:space="preserve">
|
||||
<value>Group {0} was not found.</value>
|
||||
</data>
|
||||
<data name="InvalidForGroup" xml:space="preserve">
|
||||
<value>The operation is not allowed for group {0}.</value>
|
||||
</data>
|
||||
<data name="InvalidForUser" xml:space="preserve">
|
||||
<value>The operation is not allowed for user {0}.</value>
|
||||
</data>
|
||||
<data name="InvalidName" xml:space="preserve">
|
||||
<value>The name {0} is invalid.</value>
|
||||
</data>
|
||||
<data name="InvalidParameterPair" xml:space="preserve">
|
||||
<value>Parameter {0} and parameter {1} may not be used together.</value>
|
||||
</data>
|
||||
<data name="InvalidPassword" xml:space="preserve">
|
||||
<value>Invalid password.</value>
|
||||
</data>
|
||||
<data name="LastAdmin" xml:space="preserve">
|
||||
<value>Cannot remove the last Administrator</value>
|
||||
</data>
|
||||
<data name="MemberExists" xml:space="preserve">
|
||||
<value>{0} is already a member of group {1}.</value>
|
||||
</data>
|
||||
<data name="MemberNotFound" xml:space="preserve">
|
||||
<value>Member {0} was not found in group {1}.</value>
|
||||
</data>
|
||||
<data name="MembersPrimaryGroup" xml:space="preserve">
|
||||
<value>User {0} may not be removed from its primary group.</value>
|
||||
</data>
|
||||
<data name="NameInUse" xml:space="preserve">
|
||||
<value>The name {0} is already in use.</value>
|
||||
</data>
|
||||
<data name="ObjectClassGroup" xml:space="preserve">
|
||||
<value>Group</value>
|
||||
</data>
|
||||
<data name="ObjectClassOther" xml:space="preserve">
|
||||
<value>Other</value>
|
||||
</data>
|
||||
<data name="ObjectClassUser" xml:space="preserve">
|
||||
<value>User</value>
|
||||
</data>
|
||||
<data name="PasswordRestriction" xml:space="preserve">
|
||||
<value>The password cannot be set because a password restriction is in place.</value>
|
||||
</data>
|
||||
<data name="PrincipalNotFound" xml:space="preserve">
|
||||
<value>Principal {0} was not found.</value>
|
||||
</data>
|
||||
<data name="RidToSidFailed" xml:space="preserve">
|
||||
<value>RID {0} was not found.</value>
|
||||
</data>
|
||||
<data name="UnspecifiedError" xml:space="preserve">
|
||||
<value>An unspecified error occurred.</value>
|
||||
</data>
|
||||
<data name="UnspecifiedErrorNtStatus" xml:space="preserve">
|
||||
<value>An unspecified error occurred: status = {0}</value>
|
||||
</data>
|
||||
<data name="UnspecifiedErrorWin32Error" xml:space="preserve">
|
||||
<value>An unspecified error occurred: error code = {0}</value>
|
||||
</data>
|
||||
<data name="UserExists" xml:space="preserve">
|
||||
<value>User {0} already exists.</value>
|
||||
</data>
|
||||
<data name="UserNotFound" xml:space="preserve">
|
||||
<value>User {0} was not found.</value>
|
||||
</data>
|
||||
</root>
|
|
@ -0,0 +1,93 @@
|
|||
<?xml version="1.0" encoding="utf-8" ?>
|
||||
<Configuration>
|
||||
<ViewDefinitions>
|
||||
<View>
|
||||
<Name>Microsoft.PowerShell.Commands.LocalUser</Name>
|
||||
<ViewSelectedBy>
|
||||
<TypeName>Microsoft.PowerShell.Commands.LocalUser</TypeName>
|
||||
</ViewSelectedBy>
|
||||
<TableControl>
|
||||
<TableHeaders>
|
||||
<TableColumnHeader>
|
||||
</TableColumnHeader>
|
||||
<TableColumnHeader>
|
||||
</TableColumnHeader>
|
||||
<TableColumnHeader>
|
||||
</TableColumnHeader>
|
||||
</TableHeaders>
|
||||
<TableRowEntries>
|
||||
<TableRowEntry>
|
||||
<TableColumnItems>
|
||||
<TableColumnItem>
|
||||
<PropertyName>Name</PropertyName>
|
||||
</TableColumnItem>
|
||||
<TableColumnItem>
|
||||
<PropertyName>Enabled</PropertyName>
|
||||
</TableColumnItem>
|
||||
<TableColumnItem>
|
||||
<PropertyName>Description</PropertyName>
|
||||
</TableColumnItem>
|
||||
</TableColumnItems>
|
||||
</TableRowEntry>
|
||||
</TableRowEntries>
|
||||
</TableControl>
|
||||
</View>
|
||||
<View>
|
||||
<Name>Microsoft.PowerShell.Commands.LocalGroup</Name>
|
||||
<ViewSelectedBy>
|
||||
<TypeName>Microsoft.PowerShell.Commands.LocalGroup</TypeName>
|
||||
</ViewSelectedBy>
|
||||
<TableControl>
|
||||
<TableHeaders>
|
||||
<TableColumnHeader>
|
||||
</TableColumnHeader>
|
||||
<TableColumnHeader>
|
||||
</TableColumnHeader>
|
||||
</TableHeaders>
|
||||
<TableRowEntries>
|
||||
<TableRowEntry>
|
||||
<TableColumnItems>
|
||||
<TableColumnItem>
|
||||
<PropertyName>Name</PropertyName>
|
||||
</TableColumnItem>
|
||||
<TableColumnItem>
|
||||
<PropertyName>Description</PropertyName>
|
||||
</TableColumnItem>
|
||||
</TableColumnItems>
|
||||
</TableRowEntry>
|
||||
</TableRowEntries>
|
||||
</TableControl>
|
||||
</View>
|
||||
<View>
|
||||
<Name>Microsoft.PowerShell.Commands.LocalPrincipal</Name>
|
||||
<ViewSelectedBy>
|
||||
<TypeName>Microsoft.PowerShell.Commands.LocalPrincipal</TypeName>
|
||||
</ViewSelectedBy>
|
||||
<TableControl>
|
||||
<TableHeaders>
|
||||
<TableColumnHeader>
|
||||
</TableColumnHeader>
|
||||
<TableColumnHeader>
|
||||
</TableColumnHeader>
|
||||
<TableColumnHeader>
|
||||
</TableColumnHeader>
|
||||
</TableHeaders>
|
||||
<TableRowEntries>
|
||||
<TableRowEntry>
|
||||
<TableColumnItems>
|
||||
<TableColumnItem>
|
||||
<PropertyName>ObjectClass</PropertyName>
|
||||
</TableColumnItem>
|
||||
<TableColumnItem>
|
||||
<PropertyName>Name</PropertyName>
|
||||
</TableColumnItem>
|
||||
<TableColumnItem>
|
||||
<PropertyName>PrincipalSource</PropertyName>
|
||||
</TableColumnItem>
|
||||
</TableColumnItems>
|
||||
</TableRowEntry>
|
||||
</TableRowEntries>
|
||||
</TableControl>
|
||||
</View>
|
||||
</ViewDefinitions>
|
||||
</Configuration>
|
Binary file not shown.
Loading…
Reference in a new issue