Enable Trust for Kerberos Delegation in AD using PowerShell

PowerShell: Enable Trust for Kerberos Delegation in Active Directory:  To allow a user or computer account to impersonate another user, you must trust that account for delegation. This is necessary, for example, if a user hits a web site, and that web site must connect to another server, such as a SQL server or a file server, using the user's credentials.

Normally, access to the other server would be denied, because the authentication request is coming from a different account (the service account that is running the web service). The web service is actually forging the user's signature in a sense. The account doing the impersonation must be trusted to do so.

To manually trust an account for delegation, launch Active Directory Users and Computers. From the menu, select View - Advanced Features. Find the account, and click on the Delegation tab. Then select "Trust this account for Delegation" as shown in the figure. Note that the delegation tab will not show up for a user account, unless an SPN (service principal name) has been added to the account.

When you have a multi-tiered application, all of the computers and service accounts used for every tier except that back-end must be trusted for delegation. In other words, if you have a web server, an application server, and a database server, you must trust the web server, the web service account, the application server, and the application service account. If you have an application distributed across many servers, enabling them all can be a challenge. That's where this script comes in.

The script takes one argument: the name of a user or computer account.  It then searches for the account and gets the contents of the userAccountControl attribute.  The attribute contains a bitmask, where each bit has some meaning associated with various account settings.  The bit for delegation is 524228.  The script executes a binary OR with the current contents of the userAccountControl attribute, then saves the new value to the account.

$accountName=$args[0]
if($args.count -lt 1){
 "Usage: ./trustForDelegation.ps1 <accountname>"
}
$TRUSTED_FOR_DELEGATION = 524288;
$gc="GC://" + $([adsi] "LDAP://RootDSE").Get("RootDomainNamingContext")
$filter = "(cn=$accountName)"
$domain = New-Object System.DirectoryServices.DirectoryEntry($gc)
$searcher = New-Object System.DirectoryServices.DirectorySearcher
$searcher.SearchRoot = $domain
$searcher.Filter = $filter
$results = $searcher.FindAll()
if($results.count -eq 0){ "User Not Found"; }else{
 foreach ($result in $results){
  $dn=[string]$($result.properties["adspath"]).replace("GC://","LDAP://")
  $account=New-Object System.DirectoryServices.DirectoryEntry($dn)
  "Trusting $($account.cn) for Delegation..."
  $uac=$account.userAccountControl[0] -bor $TRUSTED_FOR_DELEGATION
  $account.userAccountControl[0]=$uac
  $result=$account.CommitChanges()
 }
}

1 comments:

David Gardiner said...

Brilliant! Just what I was looking for,

-david

Post a Comment

Related Posts Plugin for WordPress, Blogger...