Thursday, October 11, 2012

DES encryption and 2008R2 (does it really work?)

For everyone that finds themselves with DES dependencies and are having issues with 2008R2 and the DES turned off by default settings that it has, I have found a few things you can use to help check your environment.  First off, if you have systems that are 2008R2 pre SP1, there is a hotfix that is needed.  Otherwise SP1 should fix it (though there may be some exceptions).  If you have this in place, you can edit group policy to allow all encryption types.  After that, if you see see any intermittent issues, you can check individual domain controllers for DES support with java.  Get a copy of a java JRE, and there are some built in utility classes that you can use for quick tests of kerberos.

Java.exe "-Djava.security.krb5.kdc=MyDomainController1" "-Djava.security.krb5.conf=c:\windows\krb5.ini" "-Djava.security.krb5.realm=CONTOSO.COM" "-Djava.security.krb5.internal.crypto=DesCbcCRCEType" "sun.security.krb5.internal.tools.Kinit"  someuseraccount@CONTOSO.COM UserPassword

If you look at the example above (the quotes are in there for use within powershell), the first -D option points to your KDC, which is the domain controller you want to test.  The second points to a krb5.ini file (might not be required, you can search around to find the format of that if needed).  The third option: Realm, is the dns name of your domain.  Our fourth option is the encryption type you want to test.  You can do DesCbcCRCEtype or DesCbcMd5Etype (among others), to test different types of DES encryption ticket requests.  The last part of the java class paths is the Kinit class utility, and the two arguments after that are the username and password.  These can be any account in the domain, and doesn't require the DES checkbox on the user account to be checked.  Run this command and check output.  If there are errors, it will give you further details.  If DES is not supported on a domain controller, you will get an error 14 talking about encryption type no supported.  Otherwise, you will get a kerberos ticket that will be stored in a file. 

If you want verbose debugging details for the whole connection, you can add these two options prior to the kinit:

-Dsun.security.krb5.debug=true
-Dsun.security.krb5.krb5debug=all

If you want to test a large number of domain controllers, you can wrap this into a powershell function similar to this:

function check-dessupport {
    param(
        [string]$server,
        [string]$realm,
        [string]$user,
        [string]$password
    )
    echo $server >>c:\temp\kerbout.txt
    $res = new-object PSObject
    add-member -inputobject $res NoteProperty Server $server
    Java.exe "-Djava.security.krb5.kdc=$($server)" "-Djava.security.krb5.conf=c:\windows\krb5.ini" "-Djava.security.krb5.realm=$($realm)" "-Djava.security.krb5.internal.crypto=DesCbcCRCEType" "sun.security.krb5.internal.tools.Kinit"  $user $password 2>>c:\temp\kerbout.txt
    add-member -inputobject $res NoteProperty DesCbcCrc $?
    Java.exe "-Djava.security.krb5.kdc=$($server)" "-Djava.security.krb5.conf=c:\windows\krb5.ini" "-Djava.security.krb5.realm=$($realm)" "-Djava.security.krb5.internal.crypto=DesCbcMd5EType" "sun.security.krb5.internal.tools.Kinit"  $user $password 2>>c:\temp\kerbout.txt
    add-member -inputobject $res NoteProperty DesCbcMd5 $?
    return $res
}

This will return the server name and true/false for each time.  Just note that the failure of a test can just be the server is not available or is slow to respond.  This example logs the full details into c:\temp\kerbout.txt

To check the allowed encryption types that are set by policy you can look at the registry key

function check-enctypeRegEntry {
    param(
        [string]$server
    )
    $key = "Software\Microsoft\Windows\CurrentVersion\Policies\System\kerberos\parameters"
    $type = [Microsoft.Win32.RegistryHive]::LocalMachine

    $regkey = [Microsoft.win32.registrykey]::OpenRemoteBaseKey($type,$server)
    $regkey = $regkey.opensubkey($key)
    $enctypes = $regkey.getvalue("supportedencryptiontypes")
    $ret = New-Object psobject
    Add-Member -InputObject $ret NoteProperty Server $server
    Add-Member -InputObject $ret NoteProperty EncType $enctypes
    return $ret
}

And you will need to decode the numeric value from there.  A decimal value of 31 is the value for all check boxes being checked except future encryption types.

For further details on dealing with DES, you can look at my previous article on the subject. If you do have everything enabled and you are at SP1 but still have DES issues, please comment on the post.