关于计数器和此陈述的POWERSHELL信息

时间:2012-12-18 11:17:24

标签: windows powershell active-directory

我在网站上找到了此代码:More userAccountControl Flag Fun (Convert-ToUACFlag.ps1) - http://bsonposh.com/archives/288,用于活动目录中的用户。 而且我认为我理解了一点,所以我根据这篇文章创建了一个相反的功能,但它似乎作为一个计数器(管道) - > ? (如果) %不是(非常)清楚,它做什么(我不认为它是模数运算符,否则我误解了管道)

%=按模数运算符分配

echo( 1..($flags.length) | ? {$value -band [math]::Pow(2,$_)} |  %{ $flags[$_] });

这是原始函数,工作正常

function checkUserControl
{
    param
    ([int]$value)
    $flags = @("","ACCOUNTDISABLE","", "HOMEDIR_REQUIRED",
    "LOCKOUT", "PASSWD_NOTREQD","PASSWD_CANT_CHANGE", "ENCRYPTED_TEXT_PWD_ALLOWED",
    "TEMP_DUPLICATE_ACCOUNT", "NORMAL_ACCOUNT", "","INTERDOMAIN_TRUST_ACCOUNT", "WORKSTATION_TRUST_ACCOUNT",
    "SERVER_TRUST_ACCOUNT", "", "", "DONT_EXPIRE_PASSWORD", "MNS_LOGON_ACCOUNT", "SMARTCARD_REQUIRED",
    "TRUSTED_FOR_DELEGATION", "NOT_DELEGATED","USE_DES_KEY_ONLY", "DONT_REQ_PREAUTH",
    "PASSWORD_EXPIRED", "TRUSTED_TO_AUTH_FOR_DELEGATION")

    echo( 1..($flags.length) | ? {$value -band [math]::Pow(2,$_)} |  %{ $flags[$_] });
}

所以我自己尝试(几次尝试)

function checkUserControl2
    {
        param
        ([string]$value)
        $flags = @("","ACCOUNTDISABLE","", "HOMEDIR_REQUIRED",
        "LOCKOUT", "PASSWD_NOTREQD","PASSWD_CANT_CHANGE", "ENCRYPTED_TEXT_PWD_ALLOWED",
        "TEMP_DUPLICATE_ACCOUNT", "NORMAL_ACCOUNT", "","INTERDOMAIN_TRUST_ACCOUNT", "WORKSTATION_TRUST_ACCOUNT",
        "SERVER_TRUST_ACCOUNT", "", "", "DONT_EXPIRE_PASSWORD", "MNS_LOGON_ACCOUNT", "SMARTCARD_REQUIRED",
        "TRUSTED_FOR_DELEGATION", "NOT_DELEGATED","USE_DES_KEY_ONLY", "DONT_REQ_PREAUTH",
        "PASSWORD_EXPIRED", "TRUSTED_TO_AUTH_FOR_DELEGATION")

        #echo( 1..($flags.length) | ? {$value -eq $flags[$_] } )} |  %{$_});
        #echo( 1..($flags.length) | ? {$value -match $flags[$_] } )} |  %{$_});
        #echo( 1..($flags.length) | ? {$value -ieq $flags[$_] } )} |  %{$_});
        #echo( 1..($flags.length) | ? {$value -imatch $flags[$_] } )} |  %{ $_ });
        #echo( 1..($flags.length) | ? {$value -ieq $flags[$_] } )} |  {$_});
        echo( 1..($flags.length) | ? {$value -imatch $flags[$_] } )} |  { $_ });
    }

 echo "DONT_EXPIRE_PASSWORD";
 checkUserControl2("DONT_EXPIRE_PASSWORD");

我得到的错误an empty pipe is not allowed

2 个答案:

答案 0 :(得分:1)

这是执行用户帐户控制操作的另一种方法,我觉得这种操作最终比其他提议的方法更清晰,更通用。这是我在answeruserAccountControl in Active Directory中提供的相同方法的PowerShell版本。  (另见How to use the UserAccountControl flags to manipulate user account properties。)

Add-Type -TypeDefinition @"
/// <summary>
/// Flags that control the behavior of the user account.
/// </summary>
[System.Flags()]
public enum UserAccountControl : int
{
    /// <summary>
    /// The logon script is executed. This flag does not work for the ADSI LDAP provider on either read or write operations. For 
    /// the ADSI WinNT provider, this flag is read-only data, and it cannot be set for user objects.
    ///</summary>
    SCRIPT = 0x00000001,

    /// <summary>
    /// The user account is disabled. 
    ///</summary>
    ACCOUNTDISABLE = 0x00000002,

    /// <summary>
    /// The home directory is required. 
    ///</summary>
    HOMEDIR_REQUIRED = 0x00000008,

    /// <summary>
    /// The account is currently locked out. 
    ///</summary>
    LOCKOUT = 0x00000010,

    /// <summary>
    /// No password is required. 
    ///</summary>
    PASSWD_NOTREQD = 0x00000020,

    /// <summary>
    /// The user cannot change the password. 
    ///</summary>
    /// <remarks>
    /// Note:  You cannot assign the permission settings of PASSWD_CANT_CHANGE by directly modifying the UserAccountControl attribute. 
    /// For more information and a code example that shows how to prevent a user from changing the password, see User Cannot Change Password.
    // </remarks>
    PASSWD_CANT_CHANGE = 0x00000040,

    /// <summary>
    /// The user can send an encrypted password. 
    ///</summary>
    ENCRYPTED_TEXT_PASSWORD_ALLOWED = 0x00000080,

    /// <summary>
    /// This is an account for users whose primary account is in another domain. This account provides user access to this domain, but not 
    /// to any domain that trusts this domain. Also known as a local user account. 
    ///</summary>
    TEMP_DUPLICATE_ACCOUNT = 0x00000100,

    /// <summary>
    /// This is a default account type that represents a typical user. 
    ///</summary>
    NORMAL_ACCOUNT = 0x00000200,

    /// <summary>
    /// This is a permit to trust account for a system domain that trusts other domains. 
    ///</summary>
    INTERDOMAIN_TRUST_ACCOUNT = 0x00000800,

    /// <summary>
    /// This is a computer account for a computer that is a member of this domain. 
    ///</summary>
    WORKSTATION_TRUST_ACCOUNT = 0x00001000,

    /// <summary>
    /// This is a computer account for a system backup domain controller that is a member of this domain. 
    ///</summary>
    SERVER_TRUST_ACCOUNT = 0x00002000,

    /// <summary>
    /// Not used. 
    ///</summary>
    Unused1 = 0x00004000,

    /// <summary>
    /// Not used. 
    ///</summary>
    Unused2 = 0x00008000,

    /// <summary>
    /// The password for this account will never expire. 
    ///</summary>
    DONT_EXPIRE_PASSWD = 0x00010000,

    /// <summary>
    /// This is an Majority Node Set (MNS) logon account. With MNS, you can configure a multi-node Windows cluster without using a common shared disk. 
    ///</summary>
    MNS_LOGON_ACCOUNT = 0x00020000,

    /// <summary>
    /// The user must log on using a smart card. 
    ///</summary>
    SMARTCARD_REQUIRED = 0x00040000,

    /// <summary>
    /// The service account (user or computer account), under which a service runs, is trusted for Kerberos delegation. Any such service 
    /// can impersonate a client requesting the service. 
    ///</summary>
    TRUSTED_FOR_DELEGATION = 0x00080000,

    /// <summary>
    /// The security context of the user will not be delegated to a service even if the service account is set as trusted for Kerberos delegation. 
    ///</summary>
    NOT_DELEGATED = 0x00100000,

    /// <summary>
    /// Restrict this principal to use only Data Encryption Standard (DES) encryption types for keys. 
    ///</summary>
    USE_DES_KEY_ONLY = 0x00200000,

    /// <summary>
    /// This account does not require Kerberos pre-authentication for logon. 
    ///</summary>
    DONT_REQUIRE_PREAUTH = 0x00400000,

    /// <summary>
    /// The user password has expired. This flag is created by the system using data from the Pwd-Last-Set attribute and the domain policy. 
    ///</summary>
    PASSWORD_EXPIRED = 0x00800000,

    /// <summary>
    /// The account is enabled for delegation. This is a security-sensitive setting; accounts with this option enabled should be strictly 
    /// controlled. This setting enables a service running under the account to assume a client identity and authenticate as that user to 
    /// other remote servers on the network.
    ///</summary>
    TRUSTED_TO_AUTHENTICATE_FOR_DELEGATION = 0x01000000,

    /// <summary>
    /// (Windows Server 2008/Windows Server 2008 R2) The account is a read-only domain controller (RODC). This is a security-sensitive 
    /// setting. Removing this setting from an RODC compromises security on that server.
    /// </summary>
    PARTIAL_SECRETS_ACCOUNT = 0x04000000,

    /// <summary>
    /// 
    /// </summary>
    USE_AES_KEYS = 0x08000000
}
"@

下面的PowerShell代码演示了如何使用此类型。

# This is how you convert an integer to a UserAccountControl value
[int] $userAccountControlValue = 544
[UserAccountControl] $userAccountControl = [UserAccountControl] $userAccountControlValue

# This is how you can build an account value up from the flags
[UserAccountControl] $userAccountControl = [UserAccountControl]::NORMAL_ACCOUNT -bor [UserAccountControl]::PASSWD_NOTREQD

# Alternatively, PowerShell will allow you to cast a string containing valid flags separated by commas directly into UserAccountControl
[UserAccountControl] $userAccountControl = [UserAccountControl] "NORMAL_ACCOUNT, PASSWD_NOTREQD"

# This is how you would add a flag to an existing value
$userAccountControl = $userAccountControl -bor [UserAccountControl]::DONT_EXPIRE_PASSWD

# This gets a comma separated string of the flag names that apply.
[string] $userAccountControlFlagNames = $userAccountControl.ToString()

# This is how you test for an individual flag.
[bool] $isNormalAccount = ($userAccountControl -band [UserAccountControl]::NORMAL_ACCOUNT) -eq [UserAccountControl]::NORMAL_ACCOUNT
[bool] $isAccountDisabled = ($userAccountControl -band [UserAccountControl]::ACCOUNTDISABLE) -eq [UserAccountControl]::ACCOUNTDISABLE
[bool] $isAccountLockedOut = ($userAccountControl -band [UserAccountControl]::LOCKOUT) -eq [UserAccountControl]::LOCKOUT
[bool] $dontExpirePassword = ($userAccountControl -band [UserAccountControl]::DONT_EXPIRE_PASSWD) -eq [UserAccountControl]::DONT_EXPIRE_PASSWD

# The results are easily used to do things.
if ($isAccountDisabled -eq $true)
{
    # Do something about it.
}

# The results are also easy to output.
"The account flags are $userAccountControlFlagNames."

"Is this a normal account? $isNormalAccount"
"Is the account disabled? $isAccountDisabled"
"Is the account locked out? $isAccountLockedOut"
"Does the account password never expire? $dontExpirePassword"

此外,如果您使用Active Directory模块进行Windows PowerShell Get-ADUser命令行开关,则可以使用以下代码快速查看已解码的标志:

Get-ADUser username -Properties userAccountConrol | Select *, @{ name = 'userAccountControlFlags'; expression = { [UserAccountControl] $_.userAccountControl } }

您还可以使用它来执行搜索特定标志组合的操作:

[UserAccountControl] $desiredFlags = "NORMAL_ACCOUNT, ACCOUNTDISABLE"

# You can search for specific flags like this
$filter = "objectCategory -eq 'person' -and objectClass -eq 'user' -and (userAccountControl -band $([int] $desiredFlags))"
$users = Get-ADUser -Filter $filter -Property userAccountControl
$users | Select *, @{ name = 'userAccountControlFlags'; expression = { [UserAccountControl] $_.userAccountControl } }

# or you can search for the desired flags more efficiently using an LDAP filter.
$ldapFilter = "(&(objectCategory=person)(objectClass=user)(userAccountControl:1.2.840.113556.1.4.803:=$([int] $desiredFlags)))"
$users = Get-ADUser -LDAPFilter $ldapFilter -Property userAccountControl
$users | Select *, @{ name = 'userAccountControlFlags'; expression = { [UserAccountControl] $_.userAccountControl } }

答案 1 :(得分:0)

你的代码中似乎也有一些错误的parantheses错误。我会用:

function test {
param([string]$value)

$flags = @("","ACCOUNTDISABLE","", "HOMEDIR_REQUIRED",
        "LOCKOUT", "PASSWD_NOTREQD","PASSWD_CANT_CHANGE", "ENCRYPTED_TEXT_PWD_ALLOWED",
        "TEMP_DUPLICATE_ACCOUNT", "NORMAL_ACCOUNT", "","INTERDOMAIN_TRUST_ACCOUNT", "WORKSTATION_TRUST_ACCOUNT",
        "SERVER_TRUST_ACCOUNT", "", "", "DONT_EXPIRE_PASSWORD", "MNS_LOGON_ACCOUNT", "SMARTCARD_REQUIRED",
        "TRUSTED_FOR_DELEGATION", "NOT_DELEGATED","USE_DES_KEY_ONLY", "DONT_REQ_PREAUTH",
        "PASSWORD_EXPIRED", "TRUSTED_TO_AUTH_FOR_DELEGATION")

    ## output bit flag-number (disabled atm.)   
    #(1..$flags.length) | ? {$flags[$_] -match $value}

    ## value
    (1..$flags.length) | ? {$flags[$_] -match $value} | % {[Math]::Pow(2,$_)}
}

test "HOMEDIR_REQUIRED"

输出:

8