A while back I wrote a blog post regarding PAC (Privilege Attribute Certificate) validation in Microsoft Kerberos. We’ve had enough interest in this lately, particularly around the idea of disabling it, that it seemed like a good idea to post about this again and add some more detail.
The reason for the Shatneresque drama in the title is that there are times when you expect that the PAC validation disabling action should work to prevent PAC validation but it does not. If your environment is in a situation where disabling PAC validation is a priority then this can lead to some serious angst and maybe even some hair pulling if you see unexpected results.
As a recap, PAC validation takes place when an application which is trusted for delegation attempts to reuse a Kerberos ticket from an impersonated or delegated user which it has already locally cached. This action essentially initiated a quick check to make sure that the PAC-which contains the core information on who the user is and what privileges in the environment he or she has-hasn’t been tampered with.
The obvious reason someone would tamper with a PAC would be to alter it somehow and inject more privileges into it than the user really has. In this regard-though not entirely accurate-you can think of the PAC as simply the users token. So a quick check of the PAC to make sure it is unaltered is a good thing from a security perspective.
To take a step further back and put this into context more, picture a delegation scenario where a user on a workstation client connects to an application server and the connection to the applications server’s resources are authenticated using Kerberos. When this takes place the user sends a Kerberos ticket which commonly includes the PAC to the application server as it’s “pass” to the resources it needs. The server takes that ticket and caches it locally in a secure area unique for that user in a similar way to how tickets would be cached for that user if he or she had logged on locally to that server.
In a delegation scenario, the account which the application is running under (such as when it is configured in CompMgmt.msc for a service Logon) is trusted to impersonate this user. This means that the application can request Kerberos tickets for access to resources on other servers on that users behalf and then provide those resources back to the user.
Once these tickets have been cached they can be reused as needed until they expire. This means that if the application server later needs impersonate that user and access an additional resource on that same back end server there was already a ticket cached for then it could trigger a PAC validation.
In that prior blog post I discussed a circumstance when PAC validation will not occur as well as a registry key to add which would help turn it off. Why would you want to turn PAC validation off? Well, there are applications out there which do a high volume of authentication actions on behalf of the user they are impersonating. Since PAC validation is taken care of by the Netlogon service this can lead to performance bottlenecks in the Netlogon service of application server and domain controller. It can also lead to additional network traffic which could be a problem in a low bandwidth situation.
Now let’s get back to the main reason I’m posting about this today-disabling PAC validation. There are two things which can prevent PAC validation from occurring in situations where it otherwise would: the application has the SeTcbPrivilege (also known as “Act as part of the operating system”), or the application is a service and someone has intentionally added the registry setting and value to disable PAC validation.
So if the process for that application can “Act as part of the operating system” it will be trusted enough to not warrant PAC validation. This description (taken from this Technet article) tells why we implicitly trust applications with SeTcbPrivilege:
· Allows a process to assume the identity of any user and thus gain access to the resources that the user is authorized to access. Typically, only low-level authentication services require this privilege.
· Default setting: Not assigned.
· Note that potential access is not limited to what is associated with the user by default; the calling process might request that arbitrary additional privileges be added to the access token. The calling process might also build an access token that does not provide a primary identity for tracking events in the audit log.
· When a service requires this privilege, configure the service to log on using the Local System account, which has the privilege inherently. Do not create a separate account and assign the privilege to it.
After reading the details above you can see what a very elevated and trusted thing “Act as part of the operating system” is. So naturally some applications or products may intentionally disallow using this privilege in an effort to apply the principle of least privilege . This is a common recommendation to developers as they write their code as well.
So having SeTcbPrivilege will prevent PAC validation from ever occurring, and adding it for a process/application will stop it from occurring as well. But this is not a recommended solution to turn off the PAC validation by any means since it gives so much access to one process that it becomes a security concern.
Additionally, it looks like there are applications which have code in place to remove this privilege if it is present. We recently saw what looks like the Exchange System Attendant service, otherwise known as MAD.EXE, doing this behavior. With that privilege removed you could be in a situation where the PAC would need to be validated.
To keep the eye on the ball here, that is a good thing. PAC validation means a more secure environment.
The other prevention item was to intentionally disable PAC validation by adding the registry key below with a value of “0”. I mentioned this in the other blog post but I’m going over it again in light of an example which highlights the importance of taking into account how it works.
To do this, add the registry entry to the following registry subkey:
DWORD Value Name: ValidateKdcPacSignature
When the DWORD value of this entry is 0, Kerberos does not perform PAC validation on a process that runs as a service.
More specifically, the above value-when set to 0-tells the code to not do PAC validation if the application has what is known as the “service RID”. This is a relative identifier bit of data added to the token used by the application process which says that it is a service. Here’s a good little snippet from MSDN on that:
“SU” SDDL_SERVICE Service logon user. This is a group identifier added to the token of a process when it was logged as a service. The corresponding logon type is LOGON32_LOGON_SERVICE. The corresponding RID is SECURITY_SERVICE_RID.
What if your application does not or cannot have the service RID? In that case then the registry value above can’t be used to disable PAC validation. Does this ever happen? Yes it does. The IIS application pool starts with the “batch RID” -a less privileged context than the service RID. As a result it should be expected to see PAC validation always occur from application pool running code which uses Kerberos and reuses an impersonated users cached ticket. To be clear, PAC validation cannot be disabled for code running in the IIS application pool. As I said when referring to SeTcbPrivilege, this is a good thing.
So above we’ve gone over two situations where you may specifically see PAC validation occurring when you would otherwise expect it not to. But how can you determine more about how you application is running if the SeTcbPrivilege or service RID are something you need to rule in or out as a possibility?
Process Explorer is your tool for that. You can view your applications process properties there and simply click on the Security folder tab.
Here’s a sample which shows a process (in this case Lsass.exe) which has SeTcbPrivilege:
You can find whether an application is being seen as a service here as well (shown in a different process as a Deny as a result of the awesome security hardening which Windows Vista has under the hood. In a PAC-preventable example it would need to be present as an Allow):
What about mitigation if you are in a situation where you wisely choose not to disable PAC validation, or in a situation where it cannot be turned off at all? Well, I mentioned above that PAC validation goes “through” the Netlogon service. For performance bottlenecks where the application server or the domain controller which is authenticating it are struggling you can increase the MaxConcurrentApi setting which will devote additional threads on client and server (when set on each) to these sorts of operations. Once increased the remaining possible bottlenecks would be client and server resource bottlenecks such as memory, disk and the like, as well as network bandwidth concerns if this traffic must transit networks which are low on available bandwidth.
There are many unique situations in the world so if you find yourself exploring Kerberos PAC validation and need to know more about it this post hopefully fills that need for you.