Adventures with Kerberos, CVS, and GSS-APIby Jennifer Vesperman, author of Essential CVS
While I was writing Essential CVS, I needed to write a section about using CVS with Kerberos 5 and GSS-API. Unfortunately, I've never used Kerberos before, not even as a user or a system administrator.
I happened to be running the
sid release of Debian Linux.
I needed to practice using CVS with both Kerberos 5 and Kerberos 4, so I
chose the Heimdal
implementation of Kerberos 5 because it includes Kerberos 4 support. I
used CVS 1.11.2, which was the latest stable version. I was running the
client and the server on the same computer to make the task easier.
(Note: CVS 1.11.5 became the latest stable before I finished Essential CVS, and I updated it before it went into technical review. I strongly recommend that you use at least CVS 1.11.5 because of a security problem with earlier versions.)
The easiest way to install CVS on a Debian system is to use
apt, with the command
cvs. However, the binaries from the Debian package I used weren't
compiled to allow you to use GSS-API and Kerberos, and I needed to compile
from source. To install the CVS sources, I used
You can check whether your CVS installation is compiled to run GSS-API by trying to check out a project. Test both client and server. Example 1 shows what happens if it fails.
bash-2.05a$ cvs -d :gserver:cvs:/var/lib/cvs checkout wizzard cvs checkout: CVSROOT is set for a GSS-API access method but your cvs checkout: CVS executable doesn't support it. cvs [checkout aborted]: Bad CVSROOT: `:gserver:cvs:/var/lib/cvs'.
You can also install Heimdal with the command
heimdal. To compile CVS for GSS-API, you need to install the
Heimdal libraries as well, which you can do with
It didn't initially occur to me to install the Heimdal libraries, so my first attempt at compiling CVS with GSS-API failed.
CVS will automatically support its
access method if it finds GSS-API and Kerberos 5 libraries at compile
time. Installations from packages may or may not support
gserver, depending on the package maintainer's choices. My
installation of CVS didn't, so the first thing to do was to try to compile
I read the
INSTALL file (always read the
INSTALL file) and tried to run the
script with the option
--with-gssapi. CVS searched for the
GSS-API libraries, but the Debian package for Heimdal installed them in
/usr/include, and CVS did not find them there.
Example 2 is part of the
configure output when CVS
doesn't find GSS-API and Kerberos libraries. There was no error message,
so you need to check this output carefully. You can also find a
configure report in the file
configurefails to find GSS-API
default place for krb4 is /usr/kerberos checking for krb.h... checking for krb_get_err_text... no checking for GSS-API checking for GSS-API.h... no checking for GSS-API/GSS-API.h... no checking for krb5.h... no checking for GSS-API in /usr/kerberos checking for GSS-API.h... no checking for GSS-API/GSS-API.h... no checking for krb5.h... no checking for GSS-API in /usr/cygnus/kerbnet checking for GSS-API.h... no checking for GSS-API/GSS-API.h... no checking for krb5.h... no checking for GSS-API... no
As I discovered when I reread the
INSTALL file, and read
the source for the
configure script, the syntax for
--with-gssapi is actually
--with-gssapi[=directory]. The directory should contain the
header files, but need not contain them directly--if they are in
/usr/gssapi/lib, you can
/usr/gssapi as the argument.
I also found that my
INSTALL file listed
--enable-encryption instead of
INSTALL file in your source code to see which
configure script expects.
Then I had a couple of failed
configure runs which didn't
make sense until I reread the
INSTALL file, consulted a
friendly sysadmin guru, and realized I had forgotten to run
The final command I used for
configure --with-GSS-API=/usr/include --with-krb4=/usr/include
--enable-encryption. I used
--with-krb4 to compile CVS
for Kerberos 4, which isn't necessary if you're only compiling for
Kerberos 5. The relevant parts of successful
are shown in Example 3.
default place for krb4 is /usr/include checking for krb.h... yes checking for printf in -lkrb... yes checking for printf in -ldes... no checking for krb_get_err_text... yes checking for GSS-API... /usr/include checking for GSS-API.h... yes checking for GSS-API/GSS-API.h... no checking for GSS-API/GSS-API_generic.h... no checking for krb5.h... yes checking for GSS_C_NT_HOSTBASED_SERVICE... yes checking for library containing des_set_odd_parity... none required checking for library containing com_err... none required checking for library containing initialize_asn1_error_table_r... -lasn1 checking for library containing __dn_expand... none required checking for library containing roken_gethostbyaddr... -lroken checking for library containing valid_enctype... no checking for library containing compile... no checking for library containing krb5_free_context... -lkrb5 checking for library containing gss_import_name... -lGSS-API
So, in order to compile CVS with GSS-API and Kerberos 5 support:
make distcleanto remove any cached configuration information or other remnants of previous compilations.
configurewith the arguments you need. To configure CVS for GSS-API and Kerberos 5, use
--with-gssapi. To enable encryption, use
--enable-encrypt. You may need to read the
INSTALLfile; you may also need to state the library location explicitly.
make, switch to
root, then run
The next step was configuring
inetd to run the CVS server
automatically when someone tries to connect to it. If
isn't configured, an attempt to connect to CVS with the
gserver method will result in an error message as shown in
bash$ cvs -d :gserver:helit:/home/cvs checkout wizzard cvs [checkout aborted]: connect to helit(10.0.3.1):2401 failed: Connection refused
inetd went smoothly. The instructions for
inetd are in
info:cvs#Password_authentication_server or in chapter 6 of
Essential CVS. CVS uses
gserver GSSAPI/Kerberos 5 connections.
The version of CVS that I was using (version 1.11.2) has an bug in its GSS-API code--a bug which produces the message shown in example 5 when it attempts to connect to a GSS-API server. Later versions do not have this problem, and you should be using CVS 1.11.5 or later for security reasons anyway. This is a legitimate error message if the file that it is attempting to connect through is not a socket. The bug causes it to be reported in all cases.
cvs [import aborted]: gserver currently only enabled for socket connections
A temporary fix is to use a patch to modify the
auth_server() function in
client.c, and move the
buffer.h. This repair was created by Brandon Rhodes and is
described in the archives of the
info-cvs mailing list.
Once CVS was running
gserver successfully as both client
and server, I configured the Kerberos configuration file
/etc/krb5.conf. I used the Heimdal installation documentation
info heimdal to work out what to put into the config
file, and I attempted to set up the Kerberos principal
cvs/NOSUCH.COM@NOSUCH.COM.*. A misconfigured Kerberos file
produces the errors shown in examples 6 and 7.
bash$ cvs -d :gserver:helit:/home/cvs checkout wizzard cvs checkout: GSS-API authentication failed: Miscellaneous failure (see text) cvs [checkout aborted]: GSS-API authentication failed: No such entry in the database
2002-10-20T20:11:53 Server not found in database: cvs/10.0.3.1@NOSUCH.COM: No such entry in the database
After more reading, experimentation, and the occasional bout of
swearing, I used
kadmin -l to change the principal to
cvs/10.0.3.1@NOSUCH.COM, and made progress. I had a new
error. I needed to create the principal with a random key and export the
key so that CVS could use it. The new error is shown in example 8. Example
9 shows how I successfully added the CVS principal and eliminated the
Kerberos 5 still misconfigured cvs [checkout aborted]: error from server helit: cvs [pserver aborted]: could not acquire GSS-API server credentials
Correctly adding a cvs principal kadmin> add --random-key cvs/10.0.3.1 Max ticket life [1 day]: Max renewable life [1 week]: Principal expiration time [never]: Password expiration time [never]: Attributes : kadmin> ext cvs/10.0.3.1 bash$ ktutil list FILE:/etc/krb5.keytab: Vno Type Principal 1 des-cbc-crc cvs/10.0.3.1@NOSUCH.COM 1 des-cbc-md4 cvs/10.0.3.1@NOSUCH.COM 1 des-cbc-md5 cvs/10.0.3.1@NOSUCH.COM 1 des3-cbc-sha1 cvs/10.0.3.1@NOSUCH.COM
After all of this, I forgot to get a new ticket in the Kerberos
client. The error is shown in example 10. Once I used
as the client to get a ticket,
gserver mode worked for
cvs [checkout aborted]: error from server blackrock: cvs [pserver aborted]: could not verify credentials
All of this was to produce two sections of a single chapter of Essential CVS, and to be sure I was accurate. I have, however, added a new page to my article ideas book: Kerberos. We definitely need more articles about Kerberos.
man 5 cvs
info cvshas a good section on 'what CVS is' and 'what CVS is not'. It's also a useful expansion on the manual. The 'Repository' section discusses protocols.
Jennifer Vesperman is the author of Essential CVS. She writes for the O'Reilly Network, the Linux Documentation Project, and occasionally Linux.Com.
O'Reilly & Associates will soon release (June 2003) Essential CVS.
Beta Sample Chapter 2: CVS Quickstart Guide, is available free online.
You can also look at the Full Description of the book.
For more information, or to order the book, click here.
Return to the Linux DevCenter.
Copyright © 2009 O'Reilly Media, Inc.