First of all: This is not an in-depth Kerberos how-to, nor is this tutorial about the different aspects of web application testing. This tutorial is just to give support in testing Kerberos authenticated web applications. The goal is to hand over the right tools and steps to be able to perform the configuration and be able to test the application.
When to use it?
When there is a 401 server response with the header “WWW-Authenticate:
Negotiate”. This can either mean Kerberos or NTLM authentication is needed. It
is possible to distinguish them by looking at valid authenticated client
traffic. As a simple reminder: The NTLM Authorization header will always start
with the value “TlRM…”, the Kerberos Authorization header will always start with
“YII…”. For further information this
link is
recommend.
In this tutorial the term “Kerberos authentication” will be used. There are
other terms sometimes used like SPNEGO, SSO or integrated authentication.
What Software is needed?
First of all a Kerberos implementation that is
able to talk to the KDC (Key Distribution Center) is needed. The python based
proxy “proxpy” will be used as the outgoing
proxy. Furthermore, the python library
PyKerberos will be used.
Gather the information about the domain
To be able to write the Kerberos configuration, first of all, the information
needs to be extracted form a Microsoft Windows domain member. There are many
different ways to get this information; only one of the possibilities via the
command line is shown here.
First the domain name is necessary. This can be acquired by running
“systeminfo”.
C:\Users\username>systeminfo
[...]
Domain: example.com
[...]
Since the domain name is known, it is possible to use nltest to query the domain for further information.
C:\Users\username>nltest /dsgetdc:example.com
DC: \\kdc.example.com
Address: \\10.0.0.1
Dom Guid: 00000000-0000-0000-0000-000000000000
Dom Name: example.com
Forest Name: example.com
Dc Site Name: Default-First-Site-Name
Our Site Name: Default-First-Site-Name
Flags: PDC DS LDAP KDC TIMESERV WRITABLE DNS_DC DNS_DOMAIN DNS_FOREST CL
OSE_SITE FULL_SECRET WS
The command completed successfully
Kerberos configuration
After gathering the necessary information, it is now possible to write the
Kerberos configuration. A sample configuration could look like this:
>cat /etc/krb5.conf
[logging]
Default = FILE:/var/log/krb5.log
[libdefaults]
ticket_lifetime = 24h
clock-skew = 300
default_realm = EXAMPLE.COM
dns_lookup_realm = false
dns_lookup_kdc = false
forwardable = true
renew_lifetime = 7d
[realms]
EXAMPLE.COM = {
kdc = kdc.example.com:88
admin_server = ad.example.com:464
}
[domain_realm]
.example.com = EXAMPLE.COM
example.com = EXAMPLE.COM
For further information see the krb5 documentation
Kerberos commands
After writing the Kerberos configuration, it is necessary to test it. For this
purpose kinit is used. kinit is used to obtain and cache Kerberos
ticket-granting tickets. A valid set of domain credentials is needed to
authenticate against the KDC.
>kinit username@EXAMPLE.COM
Password:
To view the local ticket cache after successful authentication, klist is used.
>klist
Ticket cache: FILE:/tmp/krb5cc_1000
Default principal: username@EXAMPLE.COM
Valid starting Expires Service principal
12/06/2015 10:24:50 12/06/2015 20:24:50 krbtgt/EXAMPLE.COM@EXAMPLE.COM
renew until 12/13/2015 10:24:46
The output shows that there is currently one Kerberos ticket-granting ticket
(krbtgt).
To delete all tickets kdestory can be used without options.
>kdestroy
Using Firefox to test the current settings
At this point it is possible to use e.g. Mozilla Firefox to visit the Kerberos
authenticated web application. To configure Firefox it is necessary to go to
about:config and search for negotiate
network.negotiate-auth.delegation-uris set to .example.com
network.negotiate-auth.trusted-uris set to .example.com
After this configuration step, Firefox can authenticate against the web application.
Kerberos Proxy
For this step there should be a working Kerberos configuration and a valid TGT. Then from this point on, all that is needed is a proxy that adds a Kerberos ticket into the HTTP header on every authentication failure. The tool proxpy with an own Kerberos plugin will be used. The plugin code looks as follows and is pretty self-explanatory.
>cat plugins/kerberos.py
def proxy_mangle_request(req):
v = req.getHeader("Host")
if len(v) > 0 and "example.com" in v[0]:
import kerberos
__, krb_context = kerberos.authGSSClientInit("HTTP@www.example.com")
kerberos.authGSSClientStep(krb_context, "")
negotiate_details = kerberos.authGSSClientResponse(krb_context)
req.addHeader("Authorization", "Negotiate " + negotiate_details)
return req
To start the proxpy use a command line similar to this:
>python2.7 proxpy.py -a 127.0.0.1 -p 3128 -vvv -x plugins/kerberos.py
After using the web application (either with Firefox or with the proxy), the ticket cache looks as follows
>klist
Ticket cache: FILE:/tmp/krb5cc_1000
Default principal: username@EXAMPLE.COM
Valid starting Expires Service principal
12/06/2015 10:24:50 12/06/2015 20:24:50 krbtgt/EXAMPLE.COM@EXAMPLE.COM
renew until 12/13/2015 10:24:46
12/06/2015 10:51:15 12/06/2015 20:24:50 HTTP/www.example.com@EXAMPLE.COM
renew until 12/13/2015 10:24:46
Everything works as expected and the common tools can be used. proxpy just needs
to be setup as the last proxy to ensure every request gets authenticated.
Happy testing of Kerberos authenticated web applications.
Kind Regards,
Simon