diff options
Diffstat (limited to 'crypto/heimdal/lib/gssapi')
26 files changed, 1943 insertions, 496 deletions
diff --git a/crypto/heimdal/lib/gssapi/8003.c b/crypto/heimdal/lib/gssapi/8003.c index f37fe04..c0d8881 100644 --- a/crypto/heimdal/lib/gssapi/8003.c +++ b/crypto/heimdal/lib/gssapi/8003.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997 - 2000 Kungliga Tekniska Högskolan + * Copyright (c) 1997 - 2001 Kungliga Tekniska Högskolan * (Royal Institute of Technology, Stockholm, Sweden). * All rights reserved. * @@ -33,7 +33,7 @@ #include "gssapi_locl.h" -RCSID("$Id: 8003.c,v 1.6 2000/01/25 23:10:13 assar Exp $"); +RCSID("$Id: 8003.c,v 1.8 2001/01/29 02:08:58 assar Exp $"); static krb5_error_code encode_om_uint32(OM_uint32 n, u_char *p) @@ -59,30 +59,30 @@ hash_input_chan_bindings (const gss_channel_bindings_t b, u_char num[4]; MD5_CTX md5; - MD5Init(&md5); + MD5_Init(&md5); encode_om_uint32 (b->initiator_addrtype, num); - MD5Update (&md5, num, sizeof(num)); + MD5_Update (&md5, num, sizeof(num)); encode_om_uint32 (b->initiator_address.length, num); - MD5Update (&md5, num, sizeof(num)); + MD5_Update (&md5, num, sizeof(num)); if (b->initiator_address.length) - MD5Update (&md5, + MD5_Update (&md5, b->initiator_address.value, b->initiator_address.length); encode_om_uint32 (b->acceptor_addrtype, num); - MD5Update (&md5, num, sizeof(num)); + MD5_Update (&md5, num, sizeof(num)); encode_om_uint32 (b->acceptor_address.length, num); - MD5Update (&md5, num, sizeof(num)); + MD5_Update (&md5, num, sizeof(num)); if (b->acceptor_address.length) - MD5Update (&md5, + MD5_Update (&md5, b->acceptor_address.value, b->acceptor_address.length); encode_om_uint32 (b->application_data.length, num); - MD5Update (&md5, num, sizeof(num)); + MD5_Update (&md5, num, sizeof(num)); if (b->application_data.length) - MD5Update (&md5, + MD5_Update (&md5, b->application_data.value, b->application_data.length); - MD5Final (p, &md5); + MD5_Final (p, &md5); return 0; } @@ -90,12 +90,20 @@ krb5_error_code gssapi_krb5_create_8003_checksum ( const gss_channel_bindings_t input_chan_bindings, OM_uint32 flags, + krb5_data *fwd_data, Checksum *result) { u_char *p; + /* + * see rfc1964 (section 1.1.1 (Initial Token), and the checksum value + * field's format) + */ result->cksumtype = 0x8003; - result->checksum.length = 24; + if (fwd_data->length > 0 && (flags & GSS_C_DELEG_FLAG)) + result->checksum.length = 24 + 4 + fwd_data->length; + else + result->checksum.length = 24; result->checksum.data = malloc (result->checksum.length); if (result->checksum.data == NULL) return ENOMEM; @@ -111,8 +119,31 @@ gssapi_krb5_create_8003_checksum ( p += 16; encode_om_uint32 (flags, p); p += 4; + + if (fwd_data->length > 0 && (flags & GSS_C_DELEG_FLAG)) { +#if 0 + u_char *tmp; + + result->checksum.length = 28 + fwd_data->length; + tmp = realloc(result->checksum.data, result->checksum.length); + if (tmp == NULL) + return ENOMEM; + result->checksum.data = tmp; + + p = (u_char*)result->checksum.data + 24; +#endif + *p++ = (1 >> 0) & 0xFF; /* DlgOpt */ /* == 1 */ + *p++ = (1 >> 8) & 0xFF; /* DlgOpt */ /* == 0 */ + *p++ = (fwd_data->length >> 0) & 0xFF; /* Dlgth */ + *p++ = (fwd_data->length >> 8) & 0xFF; /* Dlgth */ + memcpy(p, (unsigned char *) fwd_data->data, fwd_data->length); + + p += fwd_data->length; + if (p - (u_char *)result->checksum.data != result->checksum.length) - abort (); + abort(); + } + return 0; } @@ -120,14 +151,16 @@ krb5_error_code gssapi_krb5_verify_8003_checksum( const gss_channel_bindings_t input_chan_bindings, Checksum *cksum, - OM_uint32 *flags) + OM_uint32 *flags, + krb5_data *fwd_data) { unsigned char hash[16]; unsigned char *p; OM_uint32 length; + int DlgOpt; /* XXX should handle checksums > 24 bytes */ - if(cksum->cksumtype != 0x8003 || cksum->checksum.length != 24) + if(cksum->cksumtype != 0x8003) return GSS_S_BAD_BINDINGS; p = cksum->checksum.data; @@ -147,6 +180,24 @@ gssapi_krb5_verify_8003_checksum( p += sizeof(hash); decode_om_uint32(p, flags); + + if (cksum->checksum.length > 24 && (*flags & GSS_C_DELEG_FLAG)) { + + p += 4; + + DlgOpt = (p[0] << 0) | (p[1] << 8 ); + if (DlgOpt != 1) + return GSS_S_BAD_BINDINGS; + + p += 2; + fwd_data->length = (p[0] << 0) | (p[1] << 8); + fwd_data->data = malloc(fwd_data->length); + if (fwd_data->data == NULL) + return ENOMEM; + + p += 2; + memcpy(fwd_data->data, p, fwd_data->length); + } return 0; } diff --git a/crypto/heimdal/lib/gssapi/ChangeLog b/crypto/heimdal/lib/gssapi/ChangeLog index ba765ba..e335d4db 100644 --- a/crypto/heimdal/lib/gssapi/ChangeLog +++ b/crypto/heimdal/lib/gssapi/ChangeLog @@ -1,3 +1,106 @@ +2001-01-30 Assar Westerlund <assar@sics.se> + + * Makefile.am (libgssapi_la_LDFLAGS): bump version to 3:0:2 + * acquire_cred.c, init_sec_context.c, release_cred.c: add support + for getting creds from a keytab, from fvdl@netbsd.org + + * copy_ccache.c: add gss_krb5_copy_ccache + +2001-01-27 Assar Westerlund <assar@sics.se> + + * get_mic.c: cast parameters to des function to non-const pointers + to handle the case where these functions actually take non-const + des_cblock * + +2001-01-09 Assar Westerlund <assar@sics.se> + + * accept_sec_context.c (gss_accept_sec_context): use krb5_rd_cred2 + instead of krb5_rd_cred + +2000-12-11 Assar Westerlund <assar@sics.se> + + * Makefile.am (libgssapi_la_LDFLAGS): bump to 2:3:1 + +2000-12-08 Assar Westerlund <assar@sics.se> + + * wrap.c (wrap_des3): use the checksum as ivec when encrypting the + sequence number + * unwrap.c (unwrap_des3): use the checksum as ivec when encrypting + the sequence number + * init_sec_context.c (init_auth): always zero fwd_data + +2000-12-06 Johan Danielsson <joda@pdc.kth.se> + + * accept_sec_context.c: de-pointerise auth_context parameter to + krb5_mk_rep + +2000-11-15 Assar Westerlund <assar@sics.se> + + * init_sec_context.c (init_auth): update to new + krb5_build_authenticator + +2000-09-19 Assar Westerlund <assar@sics.se> + + * Makefile.am (libgssapi_la_LDFLAGS): bump to 2:2:1 + +2000-08-27 Assar Westerlund <assar@sics.se> + + * init_sec_context.c: actually pay attention to `time_req' + * init_sec_context.c: re-organize. leak less memory. + * gssapi_locl.h (gssapi_krb5_encapsulate, gss_krb5_getsomekey): + update prototypes add assert.h + * gssapi.h (GSS_KRB5_CONF_C_QOP_DES, GSS_KRB5_CONF_C_QOP_DES3_KD): + add + * verify_mic.c: re-organize and add 3DES code + * wrap.c: re-organize and add 3DES code + * unwrap.c: re-organize and add 3DES code + * get_mic.c: re-organize and add 3DES code + * encapsulate.c (gssapi_krb5_encapsulate): do not free `in_data', + let the caller do that. fix the callers. + +2000-08-16 Assar Westerlund <assar@sics.se> + + * Makefile.am: bump version to 2:1:1 + +2000-07-29 Assar Westerlund <assar@sics.se> + + * decapsulate.c (gssapi_krb5_verify_header): sanity-check length + +2000-07-25 Johan Danielsson <joda@pdc.kth.se> + + * Makefile.am: bump version to 2:0:1 + +2000-07-22 Assar Westerlund <assar@sics.se> + + * gssapi.h: update OID for GSS_C_NT_HOSTBASED_SERVICE and other + details from rfc2744 + +2000-06-29 Assar Westerlund <assar@sics.se> + + * address_to_krb5addr.c (gss_address_to_krb5addr): actually use + `int' instead of `sa_family_t' for the address family. + +2000-06-21 Assar Westerlund <assar@sics.se> + + * add support for token delegation. From Daniel Kouril + <kouril@ics.muni.cz> and Miroslav Ruda <ruda@ics.muni.cz> + +2000-05-15 Assar Westerlund <assar@sics.se> + + * Makefile.am (libgssapi_la_LDFLAGS): set version to 1:1:1 + +2000-04-12 Assar Westerlund <assar@sics.se> + + * release_oid_set.c (gss_release_oid_set): clear set for + robustness. From GOMBAS Gabor <gombasg@inf.elte.hu> + * release_name.c (gss_release_name): reset input_name for + robustness. From GOMBAS Gabor <gombasg@inf.elte.hu> + * release_buffer.c (gss_release_buffer): set value to NULL to be + more robust. From GOMBAS Gabor <gombasg@inf.elte.hu> + * add_oid_set_member.c (gss_add_oid_set_member): actually check if + the oid is a member first. leave the oid_set unchanged if realloc + fails. + 2000-02-13 Assar Westerlund <assar@sics.se> * Makefile.am: set version to 1:0:1 diff --git a/crypto/heimdal/lib/gssapi/Makefile.am b/crypto/heimdal/lib/gssapi/Makefile.am index 07d4e65..a086e29 100644 --- a/crypto/heimdal/lib/gssapi/Makefile.am +++ b/crypto/heimdal/lib/gssapi/Makefile.am @@ -1,11 +1,11 @@ -# $Id: Makefile.am,v 1.21 2000/02/13 20:34:49 assar Exp $ +# $Id: Makefile.am,v 1.30 2001/01/30 01:51:53 assar Exp $ include $(top_srcdir)/Makefile.am.common -INCLUDES += -I$(srcdir)/../krb5 +INCLUDES += -I$(srcdir)/../krb5 $(INCLUDE_krb4) lib_LTLIBRARIES = libgssapi.la -libgssapi_la_LDFLAGS = -version-info 1:0:1 +libgssapi_la_LDFLAGS = -version-info 3:0:2 include_HEADERS = gssapi.h @@ -17,6 +17,7 @@ libgssapi_la_SOURCES = \ canonicalize_name.c \ compare_name.c \ context_time.c \ + copy_ccache.c \ create_emtpy_oid_set.c \ decapsulate.c \ delete_sec_context.c \ @@ -45,4 +46,5 @@ libgssapi_la_SOURCES = \ unwrap.c \ v1.c \ verify_mic.c \ - wrap.c + wrap.c \ + address_to_krb5addr.c diff --git a/crypto/heimdal/lib/gssapi/Makefile.in b/crypto/heimdal/lib/gssapi/Makefile.in index 31ea813..4173934 100644 --- a/crypto/heimdal/lib/gssapi/Makefile.in +++ b/crypto/heimdal/lib/gssapi/Makefile.in @@ -1,6 +1,6 @@ -# Makefile.in generated automatically by automake 1.4 from Makefile.am +# Makefile.in generated automatically by automake 1.4a from Makefile.am -# Copyright (C) 1994, 1995-8, 1999 Free Software Foundation, Inc. +# Copyright (C) 1994, 1995-9, 2000 Free Software Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. @@ -10,15 +10,6 @@ # even the implied warranty of MERCHANTABILITY or FITNESS FOR A # PARTICULAR PURPOSE. -# $Id: Makefile.am,v 1.21 2000/02/13 20:34:49 assar Exp $ - - -# $Id: Makefile.am.common,v 1.3 1999/04/01 14:58:43 joda Exp $ - - -# $Id: Makefile.am.common,v 1.13 1999/11/01 03:19:58 assar Exp $ - - SHELL = @SHELL@ srcdir = @srcdir@ @@ -40,8 +31,6 @@ mandir = @mandir@ includedir = @includedir@ oldincludedir = /usr/include -DESTDIR = - pkgdatadir = $(datadir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ @@ -54,9 +43,10 @@ AUTOMAKE = @AUTOMAKE@ AUTOHEADER = @AUTOHEADER@ INSTALL = @INSTALL@ -INSTALL_PROGRAM = @INSTALL_PROGRAM@ $(AM_INSTALL_PROGRAM_FLAGS) +INSTALL_PROGRAM = @INSTALL_PROGRAM@ INSTALL_DATA = @INSTALL_DATA@ INSTALL_SCRIPT = @INSTALL_SCRIPT@ +INSTALL_STRIP_FLAG = transform = @program_transform_name@ NORMAL_INSTALL = : @@ -65,26 +55,39 @@ POST_INSTALL = : NORMAL_UNINSTALL = : PRE_UNINSTALL = : POST_UNINSTALL = : + +@SET_MAKE@ host_alias = @host_alias@ host_triplet = @host@ -AFS_EXTRA_LD = @AFS_EXTRA_LD@ AIX_EXTRA_KAFS = @AIX_EXTRA_KAFS@ +AMDEP = @AMDEP@ +AMTAR = @AMTAR@ +AS = @AS@ AWK = @AWK@ CANONICAL_HOST = @CANONICAL_HOST@ CATMAN = @CATMAN@ CATMANEXT = @CATMANEXT@ CC = @CC@ +CPP = @CPP@ +CXX = @CXX@ +CXXCPP = @CXXCPP@ DBLIB = @DBLIB@ +DEPDIR = @DEPDIR@ +DIR_des = @DIR_des@ +DIR_roken = @DIR_roken@ +DLLTOOL = @DLLTOOL@ EXEEXT = @EXEEXT@ EXTRA_LIB45 = @EXTRA_LIB45@ GROFF = @GROFF@ +INCLUDES_roken = @INCLUDES_roken@ INCLUDE_ = @INCLUDE_@ -LD = @LD@ LEX = @LEX@ LIBOBJS = @LIBOBJS@ LIBTOOL = @LIBTOOL@ LIB_ = @LIB_@ LIB_AUTH_SUBDIRS = @LIB_AUTH_SUBDIRS@ +LIB_des = @LIB_des@ +LIB_des_appl = @LIB_des_appl@ LIB_kdb = @LIB_kdb@ LIB_otp = @LIB_otp@ LIB_roken = @LIB_roken@ @@ -92,31 +95,43 @@ LIB_security = @LIB_security@ LN_S = @LN_S@ LTLIBOBJS = @LTLIBOBJS@ MAKEINFO = @MAKEINFO@ -MAKE_X_PROGS_BIN_PROGS = @MAKE_X_PROGS_BIN_PROGS@ -MAKE_X_PROGS_BIN_SCRPTS = @MAKE_X_PROGS_BIN_SCRPTS@ -MAKE_X_PROGS_LIBEXEC_PROGS = @MAKE_X_PROGS_LIBEXEC_PROGS@ NEED_WRITEAUTH_FALSE = @NEED_WRITEAUTH_FALSE@ NEED_WRITEAUTH_TRUE = @NEED_WRITEAUTH_TRUE@ -NM = @NM@ NROFF = @NROFF@ +OBJDUMP = @OBJDUMP@ OBJEXT = @OBJEXT@ PACKAGE = @PACKAGE@ RANLIB = @RANLIB@ +STRIP = @STRIP@ VERSION = @VERSION@ VOID_RETSIGTYPE = @VOID_RETSIGTYPE@ WFLAGS = @WFLAGS@ WFLAGS_NOIMPLICITINT = @WFLAGS_NOIMPLICITINT@ WFLAGS_NOUNUSED = @WFLAGS_NOUNUSED@ YACC = @YACC@ +dpagaix_CFLAGS = @dpagaix_CFLAGS@ +dpagaix_LDADD = @dpagaix_LDADD@ +install_sh = @install_sh@ + +# $Id: Makefile.am,v 1.30 2001/01/30 01:51:53 assar Exp $ + + +# $Id: Makefile.am.common,v 1.3 1999/04/01 14:58:43 joda Exp $ + + +# $Id: Makefile.am.common,v 1.23 2000/12/05 09:11:09 joda Exp $ + AUTOMAKE_OPTIONS = foreign no-dependencies SUFFIXES = .et .h .1 .3 .5 .8 .cat1 .cat3 .cat5 .cat8 .x -INCLUDES = -I$(top_builddir)/include -I$(srcdir)/../krb5 +INCLUDES = -I$(top_builddir)/include $(INCLUDES_roken) -I$(srcdir)/../krb5 $(INCLUDE_krb4) AM_CFLAGS = $(WFLAGS) +CP = cp + COMPILE_ET = $(top_builddir)/lib/com_err/compile_et buildinclude = $(top_builddir)/include @@ -136,6 +151,7 @@ LIB_getsockopt = @LIB_getsockopt@ LIB_logout = @LIB_logout@ LIB_logwtmp = @LIB_logwtmp@ LIB_odm_initialize = @LIB_odm_initialize@ +LIB_pidfile = @LIB_pidfile@ LIB_readline = @LIB_readline@ LIB_res_search = @LIB_res_search@ LIB_setpcred = @LIB_setpcred@ @@ -144,6 +160,8 @@ LIB_socket = @LIB_socket@ LIB_syslog = @LIB_syslog@ LIB_tgetent = @LIB_tgetent@ +LIBS = @LIBS@ + HESIODLIB = @HESIODLIB@ HESIODINCLUDE = @HESIODINCLUDE@ INCLUDE_hesiod = @INCLUDE_hesiod@ @@ -152,34 +170,69 @@ LIB_hesiod = @LIB_hesiod@ INCLUDE_krb4 = @INCLUDE_krb4@ LIB_krb4 = @LIB_krb4@ +INCLUDE_openldap = @INCLUDE_openldap@ +LIB_openldap = @LIB_openldap@ + INCLUDE_readline = @INCLUDE_readline@ LEXLIB = @LEXLIB@ -cat1dir = $(mandir)/cat1 -cat3dir = $(mandir)/cat3 -cat5dir = $(mandir)/cat5 -cat8dir = $(mandir)/cat8 - -MANRX = \(.*\)\.\([0-9]\) -CATSUFFIX = @CATSUFFIX@ - NROFF_MAN = groff -mandoc -Tascii -@KRB4_TRUE@LIB_kafs = $(top_builddir)/lib/kafs/libkafs.la $(AIX_EXTRA_KAFS) +@KRB4_TRUE@LIB_kafs = @KRB4_TRUE@$(top_builddir)/lib/kafs/libkafs.la $(AIX_EXTRA_KAFS) -@KRB5_TRUE@LIB_krb5 = $(top_builddir)/lib/krb5/libkrb5.la $(top_builddir)/lib/asn1/libasn1.la -@KRB5_TRUE@LIB_gssapi = $(top_builddir)/lib/gssapi/libgssapi.la +@KRB5_TRUE@LIB_krb5 = @KRB5_TRUE@$(top_builddir)/lib/krb5/libkrb5.la \ +@KRB5_TRUE@ $(top_builddir)/lib/asn1/libasn1.la +@KRB5_TRUE@LIB_gssapi = @KRB5_TRUE@$(top_builddir)/lib/gssapi/libgssapi.la CHECK_LOCAL = $(PROGRAMS) lib_LTLIBRARIES = libgssapi.la -libgssapi_la_LDFLAGS = -version-info 1:0:1 +libgssapi_la_LDFLAGS = -version-info 3:0:2 include_HEADERS = gssapi.h -libgssapi_la_SOURCES = 8003.c accept_sec_context.c acquire_cred.c add_oid_set_member.c canonicalize_name.c compare_name.c context_time.c create_emtpy_oid_set.c decapsulate.c delete_sec_context.c display_name.c display_status.c duplicate_name.c encapsulate.c export_sec_context.c export_name.c external.c get_mic.c gssapi.h gssapi_locl.h import_name.c import_sec_context.c indicate_mechs.c init.c init_sec_context.c inquire_context.c inquire_cred.c release_buffer.c release_cred.c release_name.c release_oid_set.c test_oid_set_member.c unwrap.c v1.c verify_mic.c wrap.c +libgssapi_la_SOURCES = \ + 8003.c \ + accept_sec_context.c \ + acquire_cred.c \ + add_oid_set_member.c \ + canonicalize_name.c \ + compare_name.c \ + context_time.c \ + copy_ccache.c \ + create_emtpy_oid_set.c \ + decapsulate.c \ + delete_sec_context.c \ + display_name.c \ + display_status.c \ + duplicate_name.c \ + encapsulate.c \ + export_sec_context.c \ + export_name.c \ + external.c \ + get_mic.c \ + gssapi.h \ + gssapi_locl.h \ + import_name.c \ + import_sec_context.c \ + indicate_mechs.c \ + init.c \ + init_sec_context.c \ + inquire_context.c \ + inquire_cred.c \ + release_buffer.c \ + release_cred.c \ + release_name.c \ + release_oid_set.c \ + test_oid_set_member.c \ + unwrap.c \ + v1.c \ + verify_mic.c \ + wrap.c \ + address_to_krb5addr.c +subdir = lib/gssapi mkinstalldirs = $(SHELL) $(top_srcdir)/mkinstalldirs CONFIG_HEADER = ../../include/config.h CONFIG_CLEAN_FILES = @@ -189,42 +242,43 @@ LTLIBRARIES = $(lib_LTLIBRARIES) DEFS = @DEFS@ -I. -I$(srcdir) -I../../include CPPFLAGS = @CPPFLAGS@ LDFLAGS = @LDFLAGS@ -LIBS = @LIBS@ X_CFLAGS = @X_CFLAGS@ X_LIBS = @X_LIBS@ X_EXTRA_LIBS = @X_EXTRA_LIBS@ X_PRE_LIBS = @X_PRE_LIBS@ libgssapi_la_LIBADD = -libgssapi_la_OBJECTS = 8003.lo accept_sec_context.lo acquire_cred.lo \ +am_libgssapi_la_OBJECTS = 8003.lo accept_sec_context.lo acquire_cred.lo \ add_oid_set_member.lo canonicalize_name.lo compare_name.lo \ -context_time.lo create_emtpy_oid_set.lo decapsulate.lo \ +context_time.lo copy_ccache.lo create_emtpy_oid_set.lo decapsulate.lo \ delete_sec_context.lo display_name.lo display_status.lo \ duplicate_name.lo encapsulate.lo export_sec_context.lo export_name.lo \ external.lo get_mic.lo import_name.lo import_sec_context.lo \ indicate_mechs.lo init.lo init_sec_context.lo inquire_context.lo \ inquire_cred.lo release_buffer.lo release_cred.lo release_name.lo \ release_oid_set.lo test_oid_set_member.lo unwrap.lo v1.lo verify_mic.lo \ -wrap.lo -CFLAGS = @CFLAGS@ +wrap.lo address_to_krb5addr.lo +libgssapi_la_OBJECTS = $(am_libgssapi_la_OBJECTS) COMPILE = $(CC) $(DEFS) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) LTCOMPILE = $(LIBTOOL) --mode=compile $(CC) $(DEFS) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) +CFLAGS = @CFLAGS@ CCLD = $(CC) -LINK = $(LIBTOOL) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) $(LDFLAGS) -o $@ +LINK = $(LIBTOOL) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) $(AM_LDFLAGS) $(LDFLAGS) -o $@ +DIST_SOURCES = $(libgssapi_la_SOURCES) HEADERS = $(include_HEADERS) -DIST_COMMON = ChangeLog Makefile.am Makefile.in +depcomp = +DIST_COMMON = $(include_HEADERS) ChangeLog Makefile.am Makefile.in -DISTFILES = $(DIST_COMMON) $(SOURCES) $(HEADERS) $(TEXINFOS) $(EXTRA_DIST) +DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) -TAR = tar GZIP_ENV = --best SOURCES = $(libgssapi_la_SOURCES) -OBJECTS = $(libgssapi_la_OBJECTS) +OBJECTS = $(am_libgssapi_la_OBJECTS) all: all-redirect .SUFFIXES: -.SUFFIXES: .1 .3 .5 .8 .S .c .cat1 .cat3 .cat5 .cat8 .et .h .lo .o .obj .s .x +.SUFFIXES: .1 .3 .5 .8 .c .cat1 .cat3 .cat5 .cat8 .et .h .lo .o .obj .x $(srcdir)/Makefile.in: Makefile.am $(top_srcdir)/configure.in $(ACLOCAL_M4) $(top_srcdir)/Makefile.am.common $(top_srcdir)/cf/Makefile.am.common cd $(top_srcdir) && $(AUTOMAKE) --foreign lib/gssapi/Makefile @@ -247,31 +301,18 @@ install-libLTLIBRARIES: $(lib_LTLIBRARIES) $(mkinstalldirs) $(DESTDIR)$(libdir) @list='$(lib_LTLIBRARIES)'; for p in $$list; do \ if test -f $$p; then \ - echo "$(LIBTOOL) --mode=install $(INSTALL) $$p $(DESTDIR)$(libdir)/$$p"; \ - $(LIBTOOL) --mode=install $(INSTALL) $$p $(DESTDIR)$(libdir)/$$p; \ + echo " $(LIBTOOL) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$p $(DESTDIR)$(libdir)/$$p"; \ + $(LIBTOOL) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$p $(DESTDIR)$(libdir)/$$p; \ else :; fi; \ done uninstall-libLTLIBRARIES: @$(NORMAL_UNINSTALL) - list='$(lib_LTLIBRARIES)'; for p in $$list; do \ + @list='$(lib_LTLIBRARIES)'; for p in $$list; do \ + echo " $(LIBTOOL) --mode=uninstall rm -f $(DESTDIR)$(libdir)/$$p"; \ $(LIBTOOL) --mode=uninstall rm -f $(DESTDIR)$(libdir)/$$p; \ done -.c.o: - $(COMPILE) -c $< - -# FIXME: We should only use cygpath when building on Windows, -# and only if it is available. -.c.obj: - $(COMPILE) -c `cygpath -w $<` - -.s.o: - $(COMPILE) -c $< - -.S.o: - $(COMPILE) -c $< - mostlyclean-compile: -rm -f *.o core *.core -rm -f *.$(OBJEXT) @@ -283,15 +324,6 @@ distclean-compile: maintainer-clean-compile: -.c.lo: - $(LIBTOOL) --mode=compile $(COMPILE) -c $< - -.s.lo: - $(LIBTOOL) --mode=compile $(COMPILE) -c $< - -.S.lo: - $(LIBTOOL) --mode=compile $(COMPILE) -c $< - mostlyclean-libtool: -rm -f *.lo @@ -304,41 +336,54 @@ maintainer-clean-libtool: libgssapi.la: $(libgssapi_la_OBJECTS) $(libgssapi_la_DEPENDENCIES) $(LINK) -rpath $(libdir) $(libgssapi_la_LDFLAGS) $(libgssapi_la_OBJECTS) $(libgssapi_la_LIBADD) $(LIBS) +.c.o: + $(COMPILE) -c $< +.c.obj: + $(COMPILE) -c `cygpath -w $<` +.c.lo: + $(LTCOMPILE) -c -o $@ $< install-includeHEADERS: $(include_HEADERS) @$(NORMAL_INSTALL) $(mkinstalldirs) $(DESTDIR)$(includedir) @list='$(include_HEADERS)'; for p in $$list; do \ if test -f "$$p"; then d= ; else d="$(srcdir)/"; fi; \ - echo " $(INSTALL_DATA) $$d$$p $(DESTDIR)$(includedir)/$$p"; \ - $(INSTALL_DATA) $$d$$p $(DESTDIR)$(includedir)/$$p; \ + f="`echo $$p | sed -e 's|^.*/||'`"; \ + echo " $(INSTALL_DATA) $$d$$p $(DESTDIR)$(includedir)/$$f"; \ + $(INSTALL_DATA) $$d$$p $(DESTDIR)$(includedir)/$$f; \ done uninstall-includeHEADERS: @$(NORMAL_UNINSTALL) - list='$(include_HEADERS)'; for p in $$list; do \ - rm -f $(DESTDIR)$(includedir)/$$p; \ + @list='$(include_HEADERS)'; for p in $$list; do \ + f="`echo $$p | sed -e 's|^.*/||'`"; \ + echo " rm -f $(DESTDIR)$(includedir)/$$f"; \ + rm -f $(DESTDIR)$(includedir)/$$f; \ done tags: TAGS -ID: $(HEADERS) $(SOURCES) $(LISP) - list='$(SOURCES) $(HEADERS)'; \ - unique=`for i in $$list; do echo $$i; done | \ - awk ' { files[$$0] = 1; } \ +ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) + list='$(SOURCES) $(HEADERS) $(TAGS_FILES)'; \ + unique=`for i in $$list; do \ + if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ + done | \ + $(AWK) ' { files[$$0] = 1; } \ END { for (i in files) print i; }'`; \ - here=`pwd` && cd $(srcdir) \ - && mkid -f$$here/ID $$unique $(LISP) + mkid -fID $$unique $(LISP) -TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) $(LISP) +TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \ + $(TAGS_FILES) $(LISP) tags=; \ here=`pwd`; \ - list='$(SOURCES) $(HEADERS)'; \ - unique=`for i in $$list; do echo $$i; done | \ - awk ' { files[$$0] = 1; } \ + list='$(SOURCES) $(HEADERS) $(TAGS_FILES)'; \ + unique=`for i in $$list; do \ + if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ + done | \ + $(AWK) ' { files[$$0] = 1; } \ END { for (i in files) print i; }'`; \ test -z "$(ETAGS_ARGS)$$unique$(LISP)$$tags" \ - || (cd $(srcdir) && etags $(ETAGS_ARGS) $$tags $$unique $(LISP) -o $$here/TAGS) + || etags $(ETAGS_ARGS) $$tags $$unique $(LISP) mostlyclean-tags: @@ -351,17 +396,16 @@ maintainer-clean-tags: distdir = $(top_builddir)/$(PACKAGE)-$(VERSION)/$(subdir) -subdir = lib/gssapi - distdir: $(DISTFILES) @for file in $(DISTFILES); do \ d=$(srcdir); \ if test -d $$d/$$file; then \ - cp -pr $$/$$file $(distdir)/$$file; \ + cp -pR $$d/$$file $(distdir) \ + || exit 1; \ else \ test -f $(distdir)/$$file \ - || ln $$d/$$file $(distdir)/$$file 2> /dev/null \ - || cp -p $$d/$$file $(distdir)/$$file || :; \ + || cp -p $$d/$$file $(distdir)/$$file \ + || exit 1; \ fi; \ done $(MAKE) $(AM_MAKEFLAGS) top_distdir="$(top_distdir)" distdir="$(distdir)" dist-hook @@ -390,7 +434,7 @@ uninstall: uninstall-am all-am: Makefile $(LTLIBRARIES) $(HEADERS) all-local all-redirect: all-am install-strip: - $(MAKE) $(AM_MAKEFLAGS) AM_INSTALL_PROGRAM_FLAGS=-s install + $(MAKE) $(AM_MAKEFLAGS) INSTALL_STRIP_FLAG=-s install installdirs: $(mkinstalldirs) $(DESTDIR)$(libdir) $(DESTDIR)$(includedir) @@ -404,6 +448,7 @@ distclean-generic: -rm -f config.cache config.log stamp-h stamp-h[0-9]* maintainer-clean-generic: + -rm -f Makefile.in mostlyclean-am: mostlyclean-libLTLIBRARIES mostlyclean-compile \ mostlyclean-libtool mostlyclean-tags \ mostlyclean-generic @@ -441,8 +486,8 @@ install-includeHEADERS tags mostlyclean-tags distclean-tags clean-tags \ maintainer-clean-tags distdir info-am info dvi-am dvi check-local check \ check-am installcheck-am installcheck install-exec-am install-exec \ install-data-local install-data-am install-data install-am install \ -uninstall-am uninstall all-local all-redirect all-am all installdirs \ -mostlyclean-generic distclean-generic clean-generic \ +uninstall-am uninstall all-local all-redirect all-am all install-strip \ +installdirs mostlyclean-generic distclean-generic clean-generic \ maintainer-clean-generic clean mostlyclean distclean maintainer-clean @@ -451,7 +496,10 @@ install-suid-programs: for file in $$foo; do \ x=$(DESTDIR)$(bindir)/$$file; \ if chown 0:0 $$x && chmod u+s $$x; then :; else \ - chmod 0 $$x; fi; done + echo "*"; \ + echo "* Failed to install $$x setuid root"; \ + echo "*"; \ + fi; done install-exec-hook: install-suid-programs @@ -463,8 +511,8 @@ install-build-headers:: $(include_HEADERS) $(build_HEADERZ) else file="$$f"; fi; \ if cmp -s $$file $(buildinclude)/$$f 2> /dev/null ; then \ : ; else \ - echo " cp $$file $(buildinclude)/$$f"; \ - cp $$file $(buildinclude)/$$f; \ + echo " $(CP) $$file $(buildinclude)/$$f"; \ + $(CP) $$file $(buildinclude)/$$f; \ fi ; \ done @@ -533,87 +581,8 @@ dist-cat8-mans: dist-hook: dist-cat1-mans dist-cat3-mans dist-cat5-mans dist-cat8-mans -install-cat1-mans: - @ext=1;\ - foo='$(man1_MANS)'; \ - bar='$(man_MANS)'; \ - for i in $$bar; do \ - case $$i in \ - *.1) foo="$$foo $$i";; \ - esac; done; \ - if test "$$foo"; then \ - $(mkinstalldirs) $(DESTDIR)$(cat1dir); \ - for x in $$foo; do \ - f=`echo $$x | sed 's/\.[^.]*$$/.cat1/'`; \ - if test -f "$(srcdir)/$$f"; then \ - b=`echo $$x | sed 's!$(MANRX)!\1!'`; \ - echo "$(INSTALL_DATA) $(srcdir)/$$f $(DESTDIR)$(cat1dir)/$$b.$(CATSUFFIX)";\ - $(INSTALL_DATA) $(srcdir)/$$g $(DESTDIR)$(cat1dir)/$$b.$(CATSUFFIX);\ - fi; \ - done ;\ - fi - -install-cat3-mans: - @ext=3;\ - foo='$(man3_MANS)'; \ - bar='$(man_MANS)'; \ - for i in $$bar; do \ - case $$i in \ - *.3) foo="$$foo $$i";; \ - esac; done; \ - if test "$$foo"; then \ - $(mkinstalldirs) $(DESTDIR)$(cat3dir); \ - for x in $$foo; do \ - f=`echo $$x | sed 's/\.[^.]*$$/.cat3/'`; \ - if test -f "$(srcdir)/$$f"; then \ - b=`echo $$x | sed 's!$(MANRX)!\1!'`; \ - echo "$(INSTALL_DATA) $(srcdir)/$$f $(DESTDIR)$(cat3dir)/$$b.$(CATSUFFIX)";\ - $(INSTALL_DATA) $(srcdir)/$$g $(DESTDIR)$(cat3dir)/$$b.$(CATSUFFIX);\ - fi; \ - done ;\ - fi - -install-cat5-mans: - @ext=5;\ - foo='$(man5_MANS)'; \ - bar='$(man_MANS)'; \ - for i in $$bar; do \ - case $$i in \ - *.5) foo="$$foo $$i";; \ - esac; done; \ - if test "$$foo"; then \ - $(mkinstalldirs) $(DESTDIR)$(cat5dir); \ - for x in $$foo; do \ - f=`echo $$x | sed 's/\.[^.]*$$/.cat5/'`; \ - if test -f "$(srcdir)/$$f"; then \ - b=`echo $$x | sed 's!$(MANRX)!\1!'`; \ - echo "$(INSTALL_DATA) $(srcdir)/$$f $(DESTDIR)$(cat5dir)/$$b.$(CATSUFFIX)";\ - $(INSTALL_DATA) $(srcdir)/$$g $(DESTDIR)$(cat5dir)/$$b.$(CATSUFFIX);\ - fi; \ - done ;\ - fi - -install-cat8-mans: - @ext=8;\ - foo='$(man8_MANS)'; \ - bar='$(man_MANS)'; \ - for i in $$bar; do \ - case $$i in \ - *.8) foo="$$foo $$i";; \ - esac; done; \ - if test "$$foo"; then \ - $(mkinstalldirs) $(DESTDIR)$(cat8dir); \ - for x in $$foo; do \ - f=`echo $$x | sed 's/\.[^.]*$$/.cat8/'`; \ - if test -f "$(srcdir)/$$f"; then \ - b=`echo $$x | sed 's!$(MANRX)!\1!'`; \ - echo "$(INSTALL_DATA) $(srcdir)/$$f $(DESTDIR)$(cat8dir)/$$b.$(CATSUFFIX)";\ - $(INSTALL_DATA) $(srcdir)/$$g $(DESTDIR)$(cat8dir)/$$b.$(CATSUFFIX);\ - fi; \ - done ;\ - fi - -install-cat-mans: install-cat1-mans install-cat3-mans install-cat5-mans install-cat8-mans +install-cat-mans: + $(SHELL) $(top_srcdir)/cf/install-catman.sh "$(INSTALL_DATA)" "$(mkinstalldirs)" "$(srcdir)" "$(DESTDIR)$(mandir)" '$(CATMANEXT)' $(man_MANS) $(man1_MANS) $(man3_MANS) $(man5_MANS) $(man8_MANS) install-data-local: install-cat-mans diff --git a/crypto/heimdal/lib/gssapi/accept_sec_context.c b/crypto/heimdal/lib/gssapi/accept_sec_context.c index 3f61ae1..a606c55 100644 --- a/crypto/heimdal/lib/gssapi/accept_sec_context.c +++ b/crypto/heimdal/lib/gssapi/accept_sec_context.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997 - 2000 Kungliga Tekniska Högskolan + * Copyright (c) 1997 - 2001 Kungliga Tekniska Högskolan * (Royal Institute of Technology, Stockholm, Sweden). * All rights reserved. * @@ -33,7 +33,7 @@ #include "gssapi_locl.h" -RCSID("$Id: accept_sec_context.c,v 1.17 2000/02/12 21:24:08 assar Exp $"); +RCSID("$Id: accept_sec_context.c,v 1.21 2001/01/09 18:47:11 assar Exp $"); static krb5_keytab gss_keytab; @@ -75,9 +75,11 @@ gss_accept_sec_context OM_uint32 flags; krb5_ticket *ticket = NULL; krb5_keytab keytab = NULL; + krb5_data fwd_data; gssapi_krb5_init (); + krb5_data_zero (&fwd_data); output_token->length = 0; output_token->value = NULL; @@ -103,6 +105,70 @@ gss_accept_sec_context goto failure; } + if (input_chan_bindings != GSS_C_NO_CHANNEL_BINDINGS + && input_chan_bindings->application_data.length == + 2 * sizeof((*context_handle)->auth_context->local_port) + ) { + + /* Port numbers are expected to be in application_data.value, + * initator's port first */ + + krb5_address initiator_addr, acceptor_addr; + + memset(&initiator_addr, 0, sizeof(initiator_addr)); + memset(&acceptor_addr, 0, sizeof(acceptor_addr)); + + (*context_handle)->auth_context->remote_port = + *(int16_t *) input_chan_bindings->application_data.value; + + (*context_handle)->auth_context->local_port = + *((int16_t *) input_chan_bindings->application_data.value + 1); + + + kret = gss_address_to_krb5addr(input_chan_bindings->acceptor_addrtype, + &input_chan_bindings->acceptor_address, + (*context_handle)->auth_context->local_port, + &acceptor_addr); + if (kret) { + *minor_status = kret; + ret = GSS_S_BAD_BINDINGS; + goto failure; + } + + kret = gss_address_to_krb5addr(input_chan_bindings->initiator_addrtype, + &input_chan_bindings->initiator_address, + (*context_handle)->auth_context->remote_port, + &initiator_addr); + if (kret) { + krb5_free_address (gssapi_krb5_context, &acceptor_addr); + *minor_status = kret; + ret = GSS_S_BAD_BINDINGS; + goto failure; + } + + kret = krb5_auth_con_setaddrs(gssapi_krb5_context, + (*context_handle)->auth_context, + &acceptor_addr, /* local address */ + &initiator_addr); /* remote address */ + + krb5_free_address (gssapi_krb5_context, &initiator_addr); + krb5_free_address (gssapi_krb5_context, &acceptor_addr); + +#if 0 + free(input_chan_bindings->application_data.value); + input_chan_bindings->application_data.value = NULL; + input_chan_bindings->application_data.length = 0; +#endif + + if (kret) { + *minor_status = kret; + ret = GSS_S_BAD_BINDINGS; + goto failure; + } + } + + + { int32_t tmp; @@ -183,7 +249,8 @@ gss_accept_sec_context kret = gssapi_krb5_verify_8003_checksum(input_chan_bindings, authenticator->cksum, - &flags); + &flags, + &fwd_data); krb5_free_authenticator(gssapi_krb5_context, &authenticator); if (kret) { ret = GSS_S_FAILURE; @@ -191,6 +258,49 @@ gss_accept_sec_context } } + if (fwd_data.length > 0 && (flags & GSS_C_DELEG_FLAG)) { + + krb5_ccache ccache; + + if (delegated_cred_handle == NULL || *delegated_cred_handle == NULL) + /* XXX Create a new delegated_cred_handle? */ + kret = krb5_cc_default (gssapi_krb5_context, &ccache); + + else { + if ((*delegated_cred_handle)->ccache == NULL) + kret = krb5_cc_gen_new (gssapi_krb5_context, + &krb5_mcc_ops, + &(*delegated_cred_handle)->ccache); + ccache = (*delegated_cred_handle)->ccache; + } + + if (kret) { + flags &= ~GSS_C_DELEG_FLAG; + goto end_fwd; + } + + kret = krb5_cc_initialize(gssapi_krb5_context, + ccache, + *src_name); + if (kret) { + flags &= ~GSS_C_DELEG_FLAG; + goto end_fwd; + } + + kret = krb5_rd_cred2(gssapi_krb5_context, + (*context_handle)->auth_context, + ccache, + &fwd_data); + if (kret) { + flags &= ~GSS_C_DELEG_FLAG; + goto end_fwd; + } + +end_fwd: + free(fwd_data.data); + } + + flags |= GSS_C_TRANS_FLAG; if (ret_flags) @@ -208,16 +318,16 @@ gss_accept_sec_context krb5_data outbuf; kret = krb5_mk_rep (gssapi_krb5_context, - &(*context_handle)->auth_context, + (*context_handle)->auth_context, &outbuf); if (kret) { - krb5_data_free (&outbuf); ret = GSS_S_FAILURE; goto failure; } ret = gssapi_krb5_encapsulate (&outbuf, output_token, "\x02\x00"); + krb5_data_free (&outbuf); if (ret) { kret = 0; goto failure; @@ -236,6 +346,8 @@ gss_accept_sec_context return GSS_S_COMPLETE; failure: + if (fwd_data.length > 0) + free(fwd_data.data); if (ticket != NULL) krb5_free_ticket (gssapi_krb5_context, ticket); krb5_auth_con_free (gssapi_krb5_context, diff --git a/crypto/heimdal/lib/gssapi/acquire_cred.c b/crypto/heimdal/lib/gssapi/acquire_cred.c index 821bbc3..341d06d 100644 --- a/crypto/heimdal/lib/gssapi/acquire_cred.c +++ b/crypto/heimdal/lib/gssapi/acquire_cred.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997 Kungliga Tekniska Högskolan + * Copyright (c) 1997 - 2001 Kungliga Tekniska Högskolan * (Royal Institute of Technology, Stockholm, Sweden). * All rights reserved. * @@ -33,7 +33,7 @@ #include "gssapi_locl.h" -RCSID("$Id: acquire_cred.c,v 1.3 1999/12/02 17:05:03 joda Exp $"); +RCSID("$Id: acquire_cred.c,v 1.4 2001/01/30 00:49:05 assar Exp $"); OM_uint32 gss_acquire_cred (OM_uint32 * minor_status, @@ -48,21 +48,67 @@ OM_uint32 gss_acquire_cred { gss_cred_id_t handle; OM_uint32 ret; + krb5_principal def_princ; + krb5_ccache ccache; + krb5_error_code pret = -1, kret = 0; + krb5_keytab kt; + krb5_creds cred; + krb5_get_init_creds_opt opt; handle = (gss_cred_id_t)malloc(sizeof(*handle)); if (handle == GSS_C_NO_CREDENTIAL) { return GSS_S_FAILURE; } + memset(handle, 0, sizeof (*handle)); ret = gss_duplicate_name(minor_status, desired_name, &handle->principal); if (ret) { return ret; } + if (krb5_cc_default(gssapi_krb5_context, &ccache) == 0 && + (pret = krb5_cc_get_principal(gssapi_krb5_context, ccache, + &def_princ)) == 0 && + krb5_principal_compare(gssapi_krb5_context, handle->principal, + def_princ) == TRUE) { + handle->ccache = ccache; + handle->keytab = NULL; + } else { + kret = krb5_kt_default(gssapi_krb5_context, &kt); + if (kret != 0) + goto out; + krb5_get_init_creds_opt_init(&opt); + memset(&cred, 0, sizeof(cred)); + kret = krb5_get_init_creds_keytab(gssapi_krb5_context, &cred, + handle->principal, kt, 0, NULL, &opt); + if (kret != 0) { + krb5_kt_close(gssapi_krb5_context, kt); + goto out; + } + kret = krb5_cc_gen_new(gssapi_krb5_context, &krb5_mcc_ops, &ccache); + if (kret != 0) { + krb5_kt_close(gssapi_krb5_context, kt); + goto out; + } + kret = krb5_cc_initialize(gssapi_krb5_context, ccache, cred.client); + if (kret != 0) { + krb5_kt_close(gssapi_krb5_context, kt); + krb5_cc_close(gssapi_krb5_context, ccache); + goto out; + } + kret = krb5_cc_store_cred(gssapi_krb5_context, ccache, &cred); + if (kret != 0) { + krb5_kt_close(gssapi_krb5_context, kt); + krb5_cc_close(gssapi_krb5_context, ccache); + goto out; + } + handle->ccache = ccache; + handle->keytab = kt; + } + + /* XXX */ handle->lifetime = time_req; - - handle->keytab = NULL; handle->usage = cred_usage; ret = gss_create_empty_oid_set(minor_status, &handle->mechanisms); @@ -83,5 +129,14 @@ OM_uint32 gss_acquire_cred *output_cred_handle = handle; +out: + if (pret == 0) + krb5_free_principal(gssapi_krb5_context, def_princ); + + if (kret != 0) { + *minor_status = kret; + return GSS_S_FAILURE; + } + return GSS_S_COMPLETE; } diff --git a/crypto/heimdal/lib/gssapi/add_oid_set_member.c b/crypto/heimdal/lib/gssapi/add_oid_set_member.c index 996c5cf..b8144ff 100644 --- a/crypto/heimdal/lib/gssapi/add_oid_set_member.c +++ b/crypto/heimdal/lib/gssapi/add_oid_set_member.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997 Kungliga Tekniska Högskolan + * Copyright (c) 1997 - 2000 Kungliga Tekniska Högskolan * (Royal Institute of Technology, Stockholm, Sweden). * All rights reserved. * @@ -33,7 +33,7 @@ #include "gssapi_locl.h" -RCSID("$Id: add_oid_set_member.c,v 1.3 1999/12/02 17:05:03 joda Exp $"); +RCSID("$Id: add_oid_set_member.c,v 1.6 2000/07/02 04:44:11 assar Exp $"); OM_uint32 gss_add_oid_set_member ( OM_uint32 * minor_status, @@ -41,13 +41,23 @@ OM_uint32 gss_add_oid_set_member ( gss_OID_set * oid_set ) { - size_t n = (*oid_set)->count; + gss_OID tmp; + size_t n; + OM_uint32 res; + int present; - (*oid_set)->elements = realloc ((*oid_set)->elements, - n * sizeof(gss_OID_desc)); - if ((*oid_set)->elements == NULL) { + res = gss_test_oid_set_member(minor_status, member_oid, *oid_set, &present); + if (res != GSS_S_COMPLETE) + return res; + + if (present) + return GSS_S_COMPLETE; + + n = (*oid_set)->count + 1; + tmp = realloc ((*oid_set)->elements, n * sizeof(gss_OID_desc)); + if (tmp == NULL) return GSS_S_FAILURE; - } + (*oid_set)->elements = tmp; (*oid_set)->count = n; (*oid_set)->elements[n-1] = *member_oid; return GSS_S_COMPLETE; diff --git a/crypto/heimdal/lib/gssapi/address_to_krb5addr.c b/crypto/heimdal/lib/gssapi/address_to_krb5addr.c new file mode 100644 index 0000000..1d8c1b6 --- /dev/null +++ b/crypto/heimdal/lib/gssapi/address_to_krb5addr.c @@ -0,0 +1,75 @@ +/* + * Copyright (c) 2000 Kungliga Tekniska Högskolan + * (Royal Institute of Technology, Stockholm, Sweden). + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * 3. Neither the name of the Institute nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include "gssapi_locl.h" + +#include <roken.h> + +krb5_error_code +gss_address_to_krb5addr(OM_uint32 gss_addr_type, + gss_buffer_desc *gss_addr, + int16_t port, + krb5_address *address) +{ + int addr_type; + struct sockaddr sa; + int sa_size = sizeof(sa); + krb5_error_code problem; + + if (gss_addr == NULL) + return GSS_S_FAILURE; + + switch (gss_addr_type) { +#ifdef HAVE_IPV6 + case GSS_C_AF_INET6: addr_type = AF_INET6; + break; +#endif /* HAVE_IPV6 */ + + case GSS_C_AF_INET: addr_type = AF_INET; + break; + default: + return GSS_S_FAILURE; + } + + problem = krb5_h_addr2sockaddr (addr_type, + gss_addr->value, + &sa, + &sa_size, + port); + if (problem) + return GSS_S_FAILURE; + + problem = krb5_sockaddr2address (&sa, address); + + return problem; +} diff --git a/crypto/heimdal/lib/gssapi/copy_ccache.c b/crypto/heimdal/lib/gssapi/copy_ccache.c new file mode 100644 index 0000000..f91acab --- /dev/null +++ b/crypto/heimdal/lib/gssapi/copy_ccache.c @@ -0,0 +1,56 @@ +/* + * Copyright (c) 2000 - 2001 Kungliga Tekniska Högskolan + * (Royal Institute of Technology, Stockholm, Sweden). + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * 3. Neither the name of the Institute nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include "gssapi_locl.h" + +RCSID("$Id: copy_ccache.c,v 1.1 2001/01/30 00:35:47 assar Exp $"); + +OM_uint32 +gss_krb5_copy_ccache(OM_uint32 *minor, + gss_cred_id_t cred, + krb5_ccache out) +{ + krb5_error_code kret; + + if (cred->ccache == NULL) { + *minor = EINVAL; + return GSS_S_FAILURE; + } + + kret = krb5_cc_copy_cache(gssapi_krb5_context, cred->ccache, out); + if (kret) { + *minor = kret; + return GSS_S_FAILURE; + } + return GSS_S_COMPLETE; +} diff --git a/crypto/heimdal/lib/gssapi/decapsulate.c b/crypto/heimdal/lib/gssapi/decapsulate.c index e3603c7..b0a0f1e 100644 --- a/crypto/heimdal/lib/gssapi/decapsulate.c +++ b/crypto/heimdal/lib/gssapi/decapsulate.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997 Kungliga Tekniska Högskolan + * Copyright (c) 1997 - 2000 Kungliga Tekniska Högskolan * (Royal Institute of Technology, Stockholm, Sweden). * All rights reserved. * @@ -33,7 +33,7 @@ #include "gssapi_locl.h" -RCSID("$Id: decapsulate.c,v 1.5 1999/12/02 17:05:03 joda Exp $"); +RCSID("$Id: decapsulate.c,v 1.6 2000/07/29 05:48:13 assar Exp $"); OM_uint32 gssapi_krb5_verify_header(u_char **str, @@ -44,18 +44,20 @@ gssapi_krb5_verify_header(u_char **str, int e; u_char *p = *str; + if (total_len < 1) + return GSS_S_DEFECTIVE_TOKEN; if (*p++ != 0x60) return GSS_S_DEFECTIVE_TOKEN; e = der_get_length (p, total_len - 1, &len, &len_len); if (e || 1 + len_len + len != total_len) - abort (); + return GSS_S_DEFECTIVE_TOKEN; p += len_len; if (*p++ != 0x06) return GSS_S_DEFECTIVE_TOKEN; e = der_get_length (p, total_len - 1 - len_len - 1, &mech_len, &foo); if (e) - abort (); + return GSS_S_DEFECTIVE_TOKEN; p += foo; if (mech_len != GSS_KRB5_MECHANISM->length) return GSS_S_BAD_MECH; diff --git a/crypto/heimdal/lib/gssapi/encapsulate.c b/crypto/heimdal/lib/gssapi/encapsulate.c index 1b8636bc..2732b23 100644 --- a/crypto/heimdal/lib/gssapi/encapsulate.c +++ b/crypto/heimdal/lib/gssapi/encapsulate.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997 Kungliga Tekniska Högskolan + * Copyright (c) 1997 - 2000 Kungliga Tekniska Högskolan * (Royal Institute of Technology, Stockholm, Sweden). * All rights reserved. * @@ -33,7 +33,7 @@ #include "gssapi_locl.h" -RCSID("$Id: encapsulate.c,v 1.4 1999/12/02 17:05:03 joda Exp $"); +RCSID("$Id: encapsulate.c,v 1.5 2000/08/27 02:46:23 assar Exp $"); void gssapi_krb5_encap_length (size_t data_len, @@ -78,7 +78,7 @@ gssapi_krb5_make_header (u_char *p, OM_uint32 gssapi_krb5_encapsulate( - krb5_data *in_data, + const krb5_data *in_data, gss_buffer_t output_token, u_char *type ) @@ -95,6 +95,5 @@ gssapi_krb5_encapsulate( p = gssapi_krb5_make_header (output_token->value, len, type); memcpy (p, in_data->data, in_data->length); - krb5_data_free (in_data); return GSS_S_COMPLETE; } diff --git a/crypto/heimdal/lib/gssapi/export_sec_context.c b/crypto/heimdal/lib/gssapi/export_sec_context.c index d982be7..7116f95 100644 --- a/crypto/heimdal/lib/gssapi/export_sec_context.c +++ b/crypto/heimdal/lib/gssapi/export_sec_context.c @@ -33,7 +33,7 @@ #include "gssapi_locl.h" -RCSID("$Id: export_sec_context.c,v 1.2 2000/02/12 21:25:24 assar Exp $"); +RCSID("$Id: export_sec_context.c,v 1.3 2000/07/08 11:42:22 assar Exp $"); OM_uint32 gss_export_sec_context ( @@ -44,8 +44,6 @@ gss_export_sec_context ( { krb5_storage *sp; krb5_auth_context ac; - unsigned char auth_buf[1024]; - size_t sz; int ret; krb5_data data; gss_buffer_desc buffer; @@ -97,16 +95,21 @@ gss_export_sec_context ( krb5_store_int32 (sp, ac->remote_seqnumber); #if 0 - ret = encode_Authenticator (auth_buf, sizeof(auth_buf), - ac->authenticator, &sz); - if (ret) { - krb5_storage_free (sp); - *minor_status = ret; - return GSS_S_FAILURE; + { + size_t sz; + unsigned char auth_buf[1024]; + + ret = encode_Authenticator (auth_buf, sizeof(auth_buf), + ac->authenticator, &sz); + if (ret) { + krb5_storage_free (sp); + *minor_status = ret; + return GSS_S_FAILURE; + } + data.data = auth_buf; + data.length = sz; + krb5_store_data (sp, data); } - data.data = auth_buf; - data.length = sz; - krb5_store_data (sp, data); #endif krb5_store_int32 (sp, ac->keytype); krb5_store_int32 (sp, ac->cksumtype); diff --git a/crypto/heimdal/lib/gssapi/external.c b/crypto/heimdal/lib/gssapi/external.c index 19e8306..dca35ea 100644 --- a/crypto/heimdal/lib/gssapi/external.c +++ b/crypto/heimdal/lib/gssapi/external.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997 Kungliga Tekniska Högskolan + * Copyright (c) 1997 - 2000 Kungliga Tekniska Högskolan * (Royal Institute of Technology, Stockholm, Sweden). * All rights reserved. * @@ -33,7 +33,7 @@ #include "gssapi_locl.h" -RCSID("$Id: external.c,v 1.4 1999/12/02 17:05:03 joda Exp $"); +RCSID("$Id: external.c,v 1.5 2000/07/22 03:45:28 assar Exp $"); /* * The implementation must reserve static storage for a @@ -94,15 +94,38 @@ gss_OID GSS_C_NT_STRING_UID_NAME = &gss_c_nt_string_uid_name_oid_desc; * gss_OID_desc object containing the value * {6, (void *)"\x2b\x06\x01\x05\x06\x02"}, * corresponding to an object-identifier value of - * {1(iso), 3(org), 6(dod), 1(internet), 5(security), - * 6(nametypes), 2(gss-host-based-services)}. The constant - * GSS_C_NT_HOSTBASED_SERVICE should be initialized to point - * to that gss_OID_desc. + * {iso(1) org(3) dod(6) internet(1) security(5) + * nametypes(6) gss-host-based-services(2)). The constant + * GSS_C_NT_HOSTBASED_SERVICE_X should be initialized to point + * to that gss_OID_desc. This is a deprecated OID value, and + * implementations wishing to support hostbased-service names + * should instead use the GSS_C_NT_HOSTBASED_SERVICE OID, + * defined below, to identify such names; + * GSS_C_NT_HOSTBASED_SERVICE_X should be accepted a synonym + * for GSS_C_NT_HOSTBASED_SERVICE when presented as an input + * parameter, but should not be emitted by GSS-API + * implementations */ -static gss_OID_desc gss_c_nt_hostbased_service_oid_desc = +static gss_OID_desc gss_c_nt_hostbased_service_x_oid_desc = {6, (void *)"\x2b\x06\x01\x05\x06\x02"}; +gss_OID GSS_C_NT_HOSTBASED_SERVICE_X = &gss_c_nt_hostbased_service_x_oid_desc; + +/* + * The implementation must reserve static storage for a + * gss_OID_desc object containing the value + * {10, (void *)"\x2a\x86\x48\x86\xf7\x12" + * "\x01\x02\x01\x04"}, corresponding to an + * object-identifier value of {iso(1) member-body(2) + * Unites States(840) mit(113554) infosys(1) gssapi(2) + * generic(1) service_name(4)}. The constant + * GSS_C_NT_HOSTBASED_SERVICE should be initialized + * to point to that gss_OID_desc. + */ +static gss_OID_desc gss_c_nt_hostbased_service_oid_desc = +{10, (void *)"\x2a\x86\x48\x86\xf7\x12" "\x01\x02\x01\x04"}; + gss_OID GSS_C_NT_HOSTBASED_SERVICE = &gss_c_nt_hostbased_service_oid_desc; /* diff --git a/crypto/heimdal/lib/gssapi/get_mic.c b/crypto/heimdal/lib/gssapi/get_mic.c index 8dd1b6f..a211004 100644 --- a/crypto/heimdal/lib/gssapi/get_mic.c +++ b/crypto/heimdal/lib/gssapi/get_mic.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997 - 2000 Kungliga Tekniska Högskolan + * Copyright (c) 1997 - 2001 Kungliga Tekniska Högskolan * (Royal Institute of Technology, Stockholm, Sweden). * All rights reserved. * @@ -33,21 +33,23 @@ #include "gssapi_locl.h" -RCSID("$Id: get_mic.c,v 1.11 2000/01/25 23:19:22 assar Exp $"); +RCSID("$Id: get_mic.c,v 1.15 2001/01/29 02:08:58 assar Exp $"); -OM_uint32 gss_get_mic +static OM_uint32 +mic_des (OM_uint32 * minor_status, const gss_ctx_id_t context_handle, gss_qop_t qop_req, const gss_buffer_t message_buffer, - gss_buffer_t message_token + gss_buffer_t message_token, + krb5_keyblock *key ) { u_char *p; MD5_CTX md5; u_char hash[16]; des_key_schedule schedule; - des_cblock key; + des_cblock deskey; des_cblock zero; int32_t seq_number; size_t len, total_len; @@ -56,42 +58,44 @@ OM_uint32 gss_get_mic message_token->length = total_len; message_token->value = malloc (total_len); - if (message_token->value == NULL) + if (message_token->value == NULL) { + *minor_status = ENOMEM; return GSS_S_FAILURE; + } p = gssapi_krb5_make_header(message_token->value, len, - "\x01\x01"); + "\x01\x01"); /* TOK_ID */ - memcpy (p, "\x00\x00", 2); + memcpy (p, "\x00\x00", 2); /* SGN_ALG = DES MAC MD5 */ p += 2; - memcpy (p, "\xff\xff\xff\xff", 4); + + memcpy (p, "\xff\xff\xff\xff", 4); /* Filler */ p += 4; - /* Fill in later */ + /* Fill in later (SND-SEQ) */ memset (p, 0, 16); p += 16; /* checksum */ - MD5Init (&md5); - MD5Update (&md5, p - 24, 8); - MD5Update (&md5, message_buffer->value, - message_buffer->length); - MD5Final (hash, &md5); + MD5_Init (&md5); + MD5_Update (&md5, p - 24, 8); + MD5_Update (&md5, message_buffer->value, message_buffer->length); + MD5_Final (hash, &md5); memset (&zero, 0, sizeof(zero)); - gss_krb5_getsomekey(context_handle, &key); - des_set_key (&key, schedule); - des_cbc_cksum ((const void *)hash, (void *)hash, sizeof(hash), + memcpy (&deskey, key->keyvalue.data, sizeof(deskey)); + des_set_key (&deskey, schedule); + des_cbc_cksum ((void *)hash, (void *)hash, sizeof(hash), schedule, &zero); - memcpy (p - 8, hash, 8); + memcpy (p - 8, hash, 8); /* SGN_CKSUM */ /* sequence number */ krb5_auth_getlocalseqnumber (gssapi_krb5_context, context_handle->auth_context, &seq_number); - p -= 16; + p -= 16; /* SND_SEQ */ p[0] = (seq_number >> 0) & 0xFF; p[1] = (seq_number >> 8) & 0xFF; p[2] = (seq_number >> 16) & 0xFF; @@ -100,16 +104,178 @@ OM_uint32 gss_get_mic (context_handle->more_flags & LOCAL) ? 0 : 0xFF, 4); - des_set_key (&key, schedule); - des_cbc_encrypt ((const void *)p, (void *)p, 8, + des_set_key (&deskey, schedule); + des_cbc_encrypt ((void *)p, (void *)p, 8, schedule, (des_cblock *)(p + 8), DES_ENCRYPT); krb5_auth_setlocalseqnumber (gssapi_krb5_context, context_handle->auth_context, ++seq_number); - memset (key, 0, sizeof(key)); + memset (deskey, 0, sizeof(deskey)); memset (schedule, 0, sizeof(schedule)); return GSS_S_COMPLETE; } + +static OM_uint32 +mic_des3 + (OM_uint32 * minor_status, + const gss_ctx_id_t context_handle, + gss_qop_t qop_req, + const gss_buffer_t message_buffer, + gss_buffer_t message_token, + krb5_keyblock *key + ) +{ + u_char *p; + Checksum cksum; + u_char seq[8]; + + int32_t seq_number; + size_t len, total_len; + + krb5_crypto crypto; + krb5_error_code kret; + krb5_data encdata; + char *tmp; + + gssapi_krb5_encap_length (36, &len, &total_len); + + message_token->length = total_len; + message_token->value = malloc (total_len); + if (message_token->value == NULL) { + *minor_status = ENOMEM; + return GSS_S_FAILURE; + } + + p = gssapi_krb5_make_header(message_token->value, + len, + "\x01\x01"); /* TOK-ID */ + + memcpy (p, "\x04\x00", 2); /* SGN_ALG = HMAC SHA1 DES3-KD */ + p += 2; + + memcpy (p, "\xff\xff\xff\xff", 4); /* filler */ + p += 4; + + /* this should be done in parts */ + + tmp = malloc (message_buffer->length + 8); + if (tmp == NULL) { + free (message_token->value); + *minor_status = ENOMEM; + return GSS_S_FAILURE; + } + memcpy (tmp, p - 8, 8); + memcpy (tmp + 8, message_buffer->value, message_buffer->length); + + kret = krb5_crypto_init(gssapi_krb5_context, key, 0, &crypto); + if (kret) { + free (message_token->value); + free (tmp); + *minor_status = kret; + return GSS_S_FAILURE; + } + + kret = krb5_create_checksum (gssapi_krb5_context, + crypto, + KRB5_KU_USAGE_SIGN, + tmp, + message_buffer->length + 8, + &cksum); + free (tmp); + krb5_crypto_destroy (gssapi_krb5_context, crypto); + if (kret) { + free (message_token->value); + *minor_status = kret; + return GSS_S_FAILURE; + } + + memcpy (p + 8, cksum.checksum.data, cksum.checksum.length); + + /* sequence number */ + krb5_auth_getlocalseqnumber (gssapi_krb5_context, + context_handle->auth_context, + &seq_number); + + seq[0] = (seq_number >> 0) & 0xFF; + seq[1] = (seq_number >> 8) & 0xFF; + seq[2] = (seq_number >> 16) & 0xFF; + seq[3] = (seq_number >> 24) & 0xFF; + memset (seq + 4, + (context_handle->more_flags & LOCAL) ? 0 : 0xFF, + 4); + + kret = krb5_crypto_init(gssapi_krb5_context, key, + ETYPE_DES3_CBC_NONE, &crypto); + if (kret) { + free (message_token->value); + *minor_status = kret; + return GSS_S_FAILURE; + } + + kret = krb5_encrypt (gssapi_krb5_context, + crypto, + KRB5_KU_USAGE_SEQ, + seq, 8, &encdata); + krb5_crypto_destroy (gssapi_krb5_context, crypto); + if (kret) { + free (message_token->value); + *minor_status = kret; + return GSS_S_FAILURE; + } + + assert (encdata.length == 8); + + memcpy (p, encdata.data, encdata.length); + krb5_data_free (&encdata); + + p += 8 + cksum.checksum.length; + + memcpy (p, message_buffer->value, message_buffer->length); + + krb5_auth_setlocalseqnumber (gssapi_krb5_context, + context_handle->auth_context, + ++seq_number); + + free_Checksum (&cksum); + return GSS_S_COMPLETE; +} + +OM_uint32 gss_get_mic + (OM_uint32 * minor_status, + const gss_ctx_id_t context_handle, + gss_qop_t qop_req, + const gss_buffer_t message_buffer, + gss_buffer_t message_token + ) +{ + krb5_keyblock *key; + OM_uint32 ret; + krb5_keytype keytype; + + ret = gss_krb5_getsomekey(context_handle, &key); + if (ret) { + *minor_status = ret; + return GSS_S_FAILURE; + } + krb5_enctype_to_keytype (gssapi_krb5_context, key->keytype, &keytype); + + switch (keytype) { + case KEYTYPE_DES : + ret = mic_des (minor_status, context_handle, qop_req, + message_buffer, message_token, key); + break; + case KEYTYPE_DES3 : + ret = mic_des3 (minor_status, context_handle, qop_req, + message_buffer, message_token, key); + break; + default : + *minor_status = KRB5_PROG_ETYPE_NOSUPP; + ret = GSS_S_FAILURE; + break; + } + krb5_free_keyblock (gssapi_krb5_context, key); + return ret; +} diff --git a/crypto/heimdal/lib/gssapi/gssapi.h b/crypto/heimdal/lib/gssapi/gssapi.h index 4c1b606..156a511 100644 --- a/crypto/heimdal/lib/gssapi/gssapi.h +++ b/crypto/heimdal/lib/gssapi/gssapi.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997, 1998, 1999 Kungliga Tekniska Högskolan + * Copyright (c) 1997 - 2001 Kungliga Tekniska Högskolan * (Royal Institute of Technology, Stockholm, Sweden). * All rights reserved. * @@ -31,7 +31,7 @@ * SUCH DAMAGE. */ -/* $Id: gssapi.h,v 1.14 1999/12/02 17:05:03 joda Exp $ */ +/* $Id: gssapi.h,v 1.20 2001/01/30 00:35:48 assar Exp $ */ #ifndef GSSAPI_H_ #define GSSAPI_H_ @@ -55,6 +55,8 @@ typedef u_int32_t OM_uint32; +typedef u_int32_t gss_uint32; + /* * This is to avoid having to include <krb5.h> */ @@ -89,6 +91,8 @@ typedef struct gss_OID_set_desc_struct { struct krb5_keytab_data; +struct krb5_ccache_data; + typedef int gss_cred_usage_t; typedef struct gss_cred_id_t_desc_struct { @@ -97,6 +101,7 @@ typedef struct gss_cred_id_t_desc_struct { OM_uint32 lifetime; gss_cred_usage_t usage; gss_OID_set mechanisms; + struct krb5_ccache_data *ccache; } gss_cred_id_t_desc; typedef gss_cred_id_t_desc *gss_cred_id_t; @@ -203,6 +208,9 @@ typedef OM_uint32 gss_qop_t; */ #define GSS_C_QOP_DEFAULT 0 +#define GSS_KRB5_CONF_C_QOP_DES 0x0100 +#define GSS_KRB5_CONF_C_QOP_DES3_KD 0x0200 + /* * Expiration time of 2^32-1 seconds means infinite lifetime for a * credential or security context @@ -253,10 +261,30 @@ extern gss_OID GSS_C_NT_STRING_UID_NAME; * gss_OID_desc object containing the value * {6, (void *)"\x2b\x06\x01\x05\x06\x02"}, * corresponding to an object-identifier value of - * {1(iso), 3(org), 6(dod), 1(internet), 5(security), - * 6(nametypes), 2(gss-host-based-services)}. The constant - * GSS_C_NT_HOSTBASED_SERVICE should be initialized to point - * to that gss_OID_desc. + * {iso(1) org(3) dod(6) internet(1) security(5) + * nametypes(6) gss-host-based-services(2)). The constant + * GSS_C_NT_HOSTBASED_SERVICE_X should be initialized to point + * to that gss_OID_desc. This is a deprecated OID value, and + * implementations wishing to support hostbased-service names + * should instead use the GSS_C_NT_HOSTBASED_SERVICE OID, + * defined below, to identify such names; + * GSS_C_NT_HOSTBASED_SERVICE_X should be accepted a synonym + * for GSS_C_NT_HOSTBASED_SERVICE when presented as an input + * parameter, but should not be emitted by GSS-API + * implementations + */ +extern gss_OID GSS_C_NT_HOSTBASED_SERVICE_X; + +/* + * The implementation must reserve static storage for a + * gss_OID_desc object containing the value + * {10, (void *)"\x2a\x86\x48\x86\xf7\x12" + * "\x01\x02\x01\x04"}, corresponding to an + * object-identifier value of {iso(1) member-body(2) + * Unites States(840) mit(113554) infosys(1) gssapi(2) + * generic(1) service_name(4)}. The constant + * GSS_C_NT_HOSTBASED_SERVICE should be initialized + * to point to that gss_OID_desc. */ extern gss_OID GSS_C_NT_HOSTBASED_SERVICE; @@ -295,6 +323,10 @@ extern gss_OID GSS_KRB5_NT_STRING_UID_NAME; extern gss_OID GSS_KRB5_MECHANISM; +/* for compatibility with MIT api */ + +#define gss_mech_krb5 GSS_KRB5_MECHANISM + /* Major status codes */ #define GSS_S_COMPLETE 0 @@ -739,4 +771,9 @@ OM_uint32 gss_unseal OM_uint32 gsskrb5_register_acceptor_identity (char *identity); +OM_uint32 gss_krb5_copy_ccache + (OM_uint32 *minor, + gss_cred_id_t cred, + struct krb5_ccache_data *out); + #endif /* GSSAPI_H_ */ diff --git a/crypto/heimdal/lib/gssapi/gssapi_locl.h b/crypto/heimdal/lib/gssapi/gssapi_locl.h index 53f9cdc..d8d0624 100644 --- a/crypto/heimdal/lib/gssapi/gssapi_locl.h +++ b/crypto/heimdal/lib/gssapi/gssapi_locl.h @@ -31,13 +31,14 @@ * SUCH DAMAGE. */ -/* $Id: gssapi_locl.h,v 1.12 2000/02/12 21:26:26 assar Exp $ */ +/* $Id: gssapi_locl.h,v 1.14 2000/08/27 04:19:00 assar Exp $ */ #ifndef GSSAPI_LOCL_H #define GSSAPI_LOCL_H #include <krb5_locl.h> #include <gssapi.h> +#include <assert.h> extern krb5_context gssapi_krb5_context; @@ -47,17 +48,19 @@ krb5_error_code gssapi_krb5_create_8003_checksum ( const gss_channel_bindings_t input_chan_bindings, OM_uint32 flags, + krb5_data *fwd_data, Checksum *result); krb5_error_code gssapi_krb5_verify_8003_checksum ( const gss_channel_bindings_t input_chan_bindings, Checksum *cksum, - OM_uint32 *flags); + OM_uint32 *flags, + krb5_data *fwd_data); OM_uint32 gssapi_krb5_encapsulate( - krb5_data *in_data, + const krb5_data *in_data, gss_buffer_t output_token, u_char *type); @@ -84,7 +87,13 @@ gssapi_krb5_verify_header(u_char **str, OM_uint32 gss_krb5_getsomekey(const gss_ctx_id_t context_handle, - des_cblock *key); + krb5_keyblock **key); + +krb5_error_code +gss_address_to_krb5addr(OM_uint32 gss_addr_type, + gss_buffer_desc *gss_addr, + int16_t port, + krb5_address *address); /* sec_context flags */ diff --git a/crypto/heimdal/lib/gssapi/import_sec_context.c b/crypto/heimdal/lib/gssapi/import_sec_context.c index 2667637..7d177a8 100644 --- a/crypto/heimdal/lib/gssapi/import_sec_context.c +++ b/crypto/heimdal/lib/gssapi/import_sec_context.c @@ -33,7 +33,7 @@ #include "gssapi_locl.h" -RCSID("$Id: import_sec_context.c,v 1.2 2000/02/12 21:26:00 assar Exp $"); +RCSID("$Id: import_sec_context.c,v 1.3 2000/07/08 11:56:03 assar Exp $"); OM_uint32 gss_import_sec_context ( @@ -51,7 +51,6 @@ gss_import_sec_context ( krb5_data data; gss_buffer_desc buffer; krb5_keyblock keyblock; - size_t sz; int32_t tmp; int32_t flags; @@ -121,21 +120,25 @@ gss_import_sec_context ( krb5_ret_int32 (sp, &ac->remote_seqnumber); #if 0 - krb5_ret_data (sp, &data); - ac->authenticator = malloc (sizeof (*ac->authenticator)); - if (ac->authenticator == NULL) { - *minor_status = ENOMEM; - ret = GSS_S_FAILURE; - goto failure; - } - - kret = decode_Authenticator (data.data, data.length, - ac->authenticator, &sz); - krb5_data_free (&data); - if (kret) { - *minor_status = kret; - ret = GSS_S_FAILURE; - goto failure; + { + size_t sz; + + krb5_ret_data (sp, &data); + ac->authenticator = malloc (sizeof (*ac->authenticator)); + if (ac->authenticator == NULL) { + *minor_status = ENOMEM; + ret = GSS_S_FAILURE; + goto failure; + } + + kret = decode_Authenticator (data.data, data.length, + ac->authenticator, &sz); + krb5_data_free (&data); + if (kret) { + *minor_status = kret; + ret = GSS_S_FAILURE; + goto failure; + } } #endif diff --git a/crypto/heimdal/lib/gssapi/init.c b/crypto/heimdal/lib/gssapi/init.c index 2c01490..6b19c46 100644 --- a/crypto/heimdal/lib/gssapi/init.c +++ b/crypto/heimdal/lib/gssapi/init.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997, 1999 Kungliga Tekniska Högskolan + * Copyright (c) 1997 - 2000 Kungliga Tekniska Högskolan * (Royal Institute of Technology, Stockholm, Sweden). * All rights reserved. * @@ -33,11 +33,15 @@ #include "gssapi_locl.h" -RCSID("$Id: init.c,v 1.4 1999/12/02 17:05:04 joda Exp $"); +RCSID("$Id: init.c,v 1.5 2000/12/31 07:58:37 assar Exp $"); void gssapi_krb5_init (void) { - if(gssapi_krb5_context == NULL) - krb5_init_context (&gssapi_krb5_context); + krb5_error_code ret; + + if(gssapi_krb5_context == NULL) { + ret = krb5_init_context (&gssapi_krb5_context); + /* and what do we do when that failed? */ + } } diff --git a/crypto/heimdal/lib/gssapi/init_sec_context.c b/crypto/heimdal/lib/gssapi/init_sec_context.c index 2f9bbc9..7b05d91 100644 --- a/crypto/heimdal/lib/gssapi/init_sec_context.c +++ b/crypto/heimdal/lib/gssapi/init_sec_context.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997, 1998, 1999 Kungliga Tekniska Högskolan + * Copyright (c) 1997 - 2001 Kungliga Tekniska Högskolan * (Royal Institute of Technology, Stockholm, Sweden). * All rights reserved. * @@ -33,24 +33,163 @@ #include "gssapi_locl.h" -RCSID("$Id: init_sec_context.c,v 1.18 1999/12/26 18:31:36 assar Exp $"); +RCSID("$Id: init_sec_context.c,v 1.25 2001/01/30 22:49:56 assar Exp $"); + +/* + * copy the addresses from `input_chan_bindings' (if any) to + * the auth context `ac' + */ + +static OM_uint32 +set_addresses (krb5_auth_context ac, + const gss_channel_bindings_t input_chan_bindings) +{ + /* Port numbers are expected to be in application_data.value, + * initator's port first */ + + krb5_address initiator_addr, acceptor_addr; + krb5_error_code kret; + + if (input_chan_bindings == GSS_C_NO_CHANNEL_BINDINGS + || input_chan_bindings->application_data.length != + 2 * sizeof(ac->local_port)) + return 0; + + memset(&initiator_addr, 0, sizeof(initiator_addr)); + memset(&acceptor_addr, 0, sizeof(acceptor_addr)); + + ac->local_port = + *(int16_t *) input_chan_bindings->application_data.value; + + ac->remote_port = + *((int16_t *) input_chan_bindings->application_data.value + 1); + + kret = gss_address_to_krb5addr(input_chan_bindings->acceptor_addrtype, + &input_chan_bindings->acceptor_address, + ac->remote_port, + &acceptor_addr); + if (kret) + return kret; + + kret = gss_address_to_krb5addr(input_chan_bindings->initiator_addrtype, + &input_chan_bindings->initiator_address, + ac->local_port, + &initiator_addr); + if (kret) { + krb5_free_address (gssapi_krb5_context, &acceptor_addr); + return kret; + } + + kret = krb5_auth_con_setaddrs(gssapi_krb5_context, + ac, + &initiator_addr, /* local address */ + &acceptor_addr); /* remote address */ + + krb5_free_address (gssapi_krb5_context, &initiator_addr); + krb5_free_address (gssapi_krb5_context, &acceptor_addr); + +#if 0 + free(input_chan_bindings->application_data.value); + input_chan_bindings->application_data.value = NULL; + input_chan_bindings->application_data.length = 0; +#endif + + return kret; +} + +/* + * handle delegated creds in init-sec-context + */ + +static void +do_delegation (krb5_auth_context ac, + krb5_ccache ccache, + krb5_creds *cred, + const gss_name_t target_name, + krb5_data *fwd_data, + int *flags) +{ + krb5_creds creds; + krb5_kdc_flags fwd_flags; + krb5_keyblock *subkey; + krb5_error_code kret; + + memset (&creds, 0, sizeof(creds)); + krb5_data_zero (fwd_data); + + kret = krb5_generate_subkey (gssapi_krb5_context, &cred->session, &subkey); + if (kret) + goto out; + + kret = krb5_auth_con_setlocalsubkey(gssapi_krb5_context, ac, subkey); + krb5_free_keyblock (gssapi_krb5_context, subkey); + if (kret) + goto out; + + kret = krb5_cc_get_principal(gssapi_krb5_context, ccache, &creds.client); + if (kret) + goto out; + + kret = krb5_build_principal(gssapi_krb5_context, + &creds.server, + strlen(creds.client->realm), + creds.client->realm, + KRB5_TGS_NAME, + creds.client->realm, + NULL); + if (kret) + goto out; + + creds.times.endtime = 0; + + fwd_flags.i = 0; + fwd_flags.b.forwarded = 1; + fwd_flags.b.forwardable = 1; + + if ( /*target_name->name.name_type != KRB5_NT_SRV_HST ||*/ + target_name->name.name_string.len < 2) + goto out; + + kret = krb5_get_forwarded_creds(gssapi_krb5_context, + ac, + ccache, + fwd_flags.i, + target_name->name.name_string.val[1], + &creds, + fwd_data); + + out: + if (kret) + *flags &= ~GSS_C_DELEG_FLAG; + else + *flags |= GSS_C_DELEG_FLAG; + + if (creds.client) + krb5_free_principal(gssapi_krb5_context, creds.client); + if (creds.server) + krb5_free_principal(gssapi_krb5_context, creds.server); +} + +/* + * first stage of init-sec-context + */ static OM_uint32 init_auth - (OM_uint32 * minor_status, - const gss_cred_id_t initiator_cred_handle, - gss_ctx_id_t * context_handle, - const gss_name_t target_name, - const gss_OID mech_type, - OM_uint32 req_flags, - OM_uint32 time_req, - const gss_channel_bindings_t input_chan_bindings, - const gss_buffer_t input_token, - gss_OID * actual_mech_type, - gss_buffer_t output_token, - OM_uint32 * ret_flags, - OM_uint32 * time_rec - ) +(OM_uint32 * minor_status, + const gss_cred_id_t initiator_cred_handle, + gss_ctx_id_t * context_handle, + const gss_name_t target_name, + const gss_OID mech_type, + OM_uint32 req_flags, + OM_uint32 time_req, + const gss_channel_bindings_t input_chan_bindings, + const gss_buffer_t input_token, + gss_OID * actual_mech_type, + gss_buffer_t output_token, + OM_uint32 * ret_flags, + OM_uint32 * time_rec + ) { OM_uint32 ret = GSS_S_FAILURE; krb5_error_code kret; @@ -63,12 +202,13 @@ init_auth krb5_data authenticator; Checksum cksum; krb5_enctype enctype; + krb5_data fwd_data; output_token->length = 0; output_token->value = NULL; - outbuf.length = 0; - outbuf.data = NULL; + krb5_data_zero(&outbuf); + krb5_data_zero(&fwd_data); *minor_status = 0; @@ -78,12 +218,12 @@ init_auth return GSS_S_FAILURE; } - (*context_handle)->auth_context = NULL; - (*context_handle)->source = NULL; - (*context_handle)->target = NULL; - (*context_handle)->flags = 0; - (*context_handle)->more_flags = 0; - (*context_handle)->ticket = NULL; + (*context_handle)->auth_context = NULL; + (*context_handle)->source = NULL; + (*context_handle)->target = NULL; + (*context_handle)->flags = 0; + (*context_handle)->more_flags = 0; + (*context_handle)->ticket = NULL; kret = krb5_auth_con_init (gssapi_krb5_context, &(*context_handle)->auth_context); @@ -93,6 +233,14 @@ init_auth goto failure; } + kret = set_addresses ((*context_handle)->auth_context, + input_chan_bindings); + if (kret) { + *minor_status = kret; + ret = GSS_S_BAD_BINDINGS; + goto failure; + } + { int32_t tmp; @@ -108,36 +256,15 @@ init_auth if (actual_mech_type) *actual_mech_type = GSS_KRB5_MECHANISM; - flags = 0; - ap_options = 0; - if (req_flags & GSS_C_DELEG_FLAG) - ; /* XXX */ - if (req_flags & GSS_C_MUTUAL_FLAG) { - flags |= GSS_C_MUTUAL_FLAG; - ap_options |= AP_OPTS_MUTUAL_REQUIRED; - } - if (req_flags & GSS_C_REPLAY_FLAG) - ; /* XXX */ - if (req_flags & GSS_C_SEQUENCE_FLAG) - ; /* XXX */ - if (req_flags & GSS_C_ANON_FLAG) - ; /* XXX */ - flags |= GSS_C_CONF_FLAG; - flags |= GSS_C_INTEG_FLAG; - flags |= GSS_C_SEQUENCE_FLAG; - flags |= GSS_C_TRANS_FLAG; - - if (ret_flags) - *ret_flags = flags; - (*context_handle)->flags = flags; - (*context_handle)->more_flags = LOCAL; - - kret = krb5_cc_default (gssapi_krb5_context, &ccache); - if (kret) { - *minor_status = kret; - ret = GSS_S_FAILURE; - goto failure; - } + if (initiator_cred_handle == GSS_C_NO_CREDENTIAL) { + kret = krb5_cc_default (gssapi_krb5_context, &ccache); + if (kret) { + *minor_status = kret; + ret = GSS_S_FAILURE; + goto failure; + } + } else + ccache = initiator_cred_handle->ccache; kret = krb5_cc_get_principal (gssapi_krb5_context, ccache, @@ -160,8 +287,14 @@ init_auth memset(&this_cred, 0, sizeof(this_cred)); this_cred.client = (*context_handle)->source; this_cred.server = (*context_handle)->target; - this_cred.times.endtime = 0; - this_cred.session.keytype = ETYPE_DES_CBC_CRC; + if (time_req) { + krb5_timestamp ts; + + krb5_timeofday (gssapi_krb5_context, &ts); + this_cred.times.endtime = ts + time_req; + } else + this_cred.times.endtime = 0; + this_cred.session.keytype = 0; kret = krb5_get_credentials (gssapi_krb5_context, KRB5_TC_MATCH_KEYTYPE, @@ -179,9 +312,38 @@ init_auth (*context_handle)->auth_context, &cred->session); + flags = 0; + ap_options = 0; + if (req_flags & GSS_C_DELEG_FLAG) + do_delegation ((*context_handle)->auth_context, + ccache, cred, target_name, &fwd_data, &flags); + + if (req_flags & GSS_C_MUTUAL_FLAG) { + flags |= GSS_C_MUTUAL_FLAG; + ap_options |= AP_OPTS_MUTUAL_REQUIRED; + } + + if (req_flags & GSS_C_REPLAY_FLAG) + ; /* XXX */ + if (req_flags & GSS_C_SEQUENCE_FLAG) + ; /* XXX */ + if (req_flags & GSS_C_ANON_FLAG) + ; /* XXX */ + flags |= GSS_C_CONF_FLAG; + flags |= GSS_C_INTEG_FLAG; + flags |= GSS_C_SEQUENCE_FLAG; + flags |= GSS_C_TRANS_FLAG; + + if (ret_flags) + *ret_flags = flags; + (*context_handle)->flags = flags; + (*context_handle)->more_flags = LOCAL; + kret = gssapi_krb5_create_8003_checksum (input_chan_bindings, flags, + &fwd_data, &cksum); + krb5_data_free (&fwd_data); if (kret) { *minor_status = kret; ret = GSS_S_FAILURE; @@ -202,15 +364,14 @@ init_auth } #endif - - kret = krb5_build_authenticator (gssapi_krb5_context, (*context_handle)->auth_context, enctype, cred, &cksum, &auth, - &authenticator); + &authenticator, + KRB5_KU_AP_REQ_AUTH); if (kret) { *minor_status = kret; @@ -231,14 +392,14 @@ init_auth goto failure; } - ret = gssapi_krb5_encapsulate (&outbuf, - output_token, - "\x01\x00"); + ret = gssapi_krb5_encapsulate (&outbuf, output_token, "\x01\x00"); if (ret) { *minor_status = kret; goto failure; } + krb5_data_free (&outbuf); + if (flags & GSS_C_MUTUAL_FLAG) { return GSS_S_CONTINUE_NEEDED; } else { @@ -246,7 +407,7 @@ init_auth return GSS_S_COMPLETE; } -failure: + failure: krb5_auth_con_free (gssapi_krb5_context, (*context_handle)->auth_context); if((*context_handle)->source) @@ -278,33 +439,31 @@ repl_mutual OM_uint32 * time_rec ) { - OM_uint32 ret; - krb5_error_code kret; - krb5_data indata; - krb5_ap_rep_enc_part *repl; - - ret = gssapi_krb5_decapsulate (input_token, - &indata, - "\x02\x00"); - if (ret) { + OM_uint32 ret; + krb5_error_code kret; + krb5_data indata; + krb5_ap_rep_enc_part *repl; + + ret = gssapi_krb5_decapsulate (input_token, &indata, "\x02\x00"); + if (ret) { /* XXX - Handle AP_ERROR */ - return GSS_S_FAILURE; - } + return GSS_S_FAILURE; + } - kret = krb5_rd_rep (gssapi_krb5_context, - (*context_handle)->auth_context, - &indata, - &repl); - if (kret) - return GSS_S_FAILURE; - krb5_free_ap_rep_enc_part (gssapi_krb5_context, - repl); + kret = krb5_rd_rep (gssapi_krb5_context, + (*context_handle)->auth_context, + &indata, + &repl); + if (kret) + return GSS_S_FAILURE; + krb5_free_ap_rep_enc_part (gssapi_krb5_context, + repl); - output_token->length = 0; + output_token->length = 0; - (*context_handle)->more_flags |= OPEN; + (*context_handle)->more_flags |= OPEN; - return GSS_S_COMPLETE; + return GSS_S_COMPLETE; } /* @@ -327,34 +486,34 @@ OM_uint32 gss_init_sec_context OM_uint32 * time_rec ) { - gssapi_krb5_init (); - - if (input_token == GSS_C_NO_BUFFER || input_token->length == 0) - return init_auth (minor_status, - initiator_cred_handle, - context_handle, - target_name, - mech_type, - req_flags, - time_req, - input_chan_bindings, - input_token, - actual_mech_type, - output_token, - ret_flags, - time_rec); - else - return repl_mutual(minor_status, - initiator_cred_handle, - context_handle, - target_name, - mech_type, - req_flags, - time_req, - input_chan_bindings, - input_token, - actual_mech_type, - output_token, - ret_flags, - time_rec); + gssapi_krb5_init (); + + if (input_token == GSS_C_NO_BUFFER || input_token->length == 0) + return init_auth (minor_status, + initiator_cred_handle, + context_handle, + target_name, + mech_type, + req_flags, + time_req, + input_chan_bindings, + input_token, + actual_mech_type, + output_token, + ret_flags, + time_rec); + else + return repl_mutual(minor_status, + initiator_cred_handle, + context_handle, + target_name, + mech_type, + req_flags, + time_req, + input_chan_bindings, + input_token, + actual_mech_type, + output_token, + ret_flags, + time_rec); } diff --git a/crypto/heimdal/lib/gssapi/release_buffer.c b/crypto/heimdal/lib/gssapi/release_buffer.c index 85f971f..f399a18 100644 --- a/crypto/heimdal/lib/gssapi/release_buffer.c +++ b/crypto/heimdal/lib/gssapi/release_buffer.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997 Kungliga Tekniska Högskolan + * Copyright (c) 1997 - 2000 Kungliga Tekniska Högskolan * (Royal Institute of Technology, Stockholm, Sweden). * All rights reserved. * @@ -33,7 +33,7 @@ #include "gssapi_locl.h" -RCSID("$Id: release_buffer.c,v 1.3 1999/12/02 17:05:04 joda Exp $"); +RCSID("$Id: release_buffer.c,v 1.4 2000/04/12 09:47:23 assar Exp $"); OM_uint32 gss_release_buffer (OM_uint32 * minor_status, @@ -41,6 +41,7 @@ OM_uint32 gss_release_buffer ) { free (buffer->value); + buffer->value = NULL; buffer->length = 0; return GSS_S_COMPLETE; } diff --git a/crypto/heimdal/lib/gssapi/release_cred.c b/crypto/heimdal/lib/gssapi/release_cred.c index 0ee876e..87ad512 100644 --- a/crypto/heimdal/lib/gssapi/release_cred.c +++ b/crypto/heimdal/lib/gssapi/release_cred.c @@ -33,7 +33,7 @@ #include "gssapi_locl.h" -RCSID("$Id: release_cred.c,v 1.4 1999/12/02 17:05:04 joda Exp $"); +RCSID("$Id: release_cred.c,v 1.5 2001/01/30 00:49:05 assar Exp $"); OM_uint32 gss_release_cred (OM_uint32 * minor_status, @@ -49,6 +49,8 @@ OM_uint32 gss_release_cred krb5_free_principal(gssapi_krb5_context, (*cred_handle)->principal); if ((*cred_handle)->keytab != NULL) krb5_kt_close(gssapi_krb5_context, (*cred_handle)->keytab); + if ((*cred_handle)->ccache != NULL) + krb5_cc_close(gssapi_krb5_context, (*cred_handle)->ccache); gss_release_oid_set(NULL, &(*cred_handle)->mechanisms); free(*cred_handle); *cred_handle = GSS_C_NO_CREDENTIAL; diff --git a/crypto/heimdal/lib/gssapi/release_name.c b/crypto/heimdal/lib/gssapi/release_name.c index 7c0fcd3..ce18a91 100644 --- a/crypto/heimdal/lib/gssapi/release_name.c +++ b/crypto/heimdal/lib/gssapi/release_name.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997 Kungliga Tekniska Högskolan + * Copyright (c) 1997 - 2000 Kungliga Tekniska Högskolan * (Royal Institute of Technology, Stockholm, Sweden). * All rights reserved. * @@ -33,7 +33,7 @@ #include "gssapi_locl.h" -RCSID("$Id: release_name.c,v 1.4 1999/12/02 17:05:04 joda Exp $"); +RCSID("$Id: release_name.c,v 1.5 2000/04/12 09:48:27 assar Exp $"); OM_uint32 gss_release_name (OM_uint32 * minor_status, @@ -43,5 +43,6 @@ OM_uint32 gss_release_name gssapi_krb5_init (); krb5_free_principal(gssapi_krb5_context, *input_name); + *input_name = GSS_C_NO_NAME; return GSS_S_COMPLETE; } diff --git a/crypto/heimdal/lib/gssapi/release_oid_set.c b/crypto/heimdal/lib/gssapi/release_oid_set.c index fe7171e..4225788 100644 --- a/crypto/heimdal/lib/gssapi/release_oid_set.c +++ b/crypto/heimdal/lib/gssapi/release_oid_set.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997 Kungliga Tekniska Högskolan + * Copyright (c) 1997 - 2000 Kungliga Tekniska Högskolan * (Royal Institute of Technology, Stockholm, Sweden). * All rights reserved. * @@ -33,7 +33,7 @@ #include "gssapi_locl.h" -RCSID("$Id: release_oid_set.c,v 1.3 1999/12/02 17:05:04 joda Exp $"); +RCSID("$Id: release_oid_set.c,v 1.4 2000/04/19 13:06:13 assar Exp $"); OM_uint32 gss_release_oid_set (OM_uint32 * minor_status, @@ -42,5 +42,6 @@ OM_uint32 gss_release_oid_set { free ((*set)->elements); free (*set); + *set = GSS_C_NO_OID_SET; return GSS_S_COMPLETE; } diff --git a/crypto/heimdal/lib/gssapi/unwrap.c b/crypto/heimdal/lib/gssapi/unwrap.c index 210bab1..588517e 100644 --- a/crypto/heimdal/lib/gssapi/unwrap.c +++ b/crypto/heimdal/lib/gssapi/unwrap.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997 - 2000 Kungliga Tekniska Högskolan + * Copyright (c) 1997 - 2001 Kungliga Tekniska Högskolan * (Royal Institute of Technology, Stockholm, Sweden). * All rights reserved. * @@ -33,11 +33,11 @@ #include "gssapi_locl.h" -RCSID("$Id: unwrap.c,v 1.11 2000/01/25 23:13:38 assar Exp $"); +RCSID("$Id: unwrap.c,v 1.15 2001/01/29 02:08:58 assar Exp $"); OM_uint32 gss_krb5_getsomekey(const gss_ctx_id_t context_handle, - des_cblock *key) + krb5_keyblock **key) { /* XXX this is ugly, and probably incorrect... */ krb5_keyblock *skey; @@ -54,18 +54,19 @@ gss_krb5_getsomekey(const gss_ctx_id_t context_handle, &skey); if(skey == NULL) return GSS_S_FAILURE; - memcpy(key, skey->keyvalue.data, sizeof(*key)); - krb5_free_keyblock(gssapi_krb5_context, skey); + *key = skey; return 0; } -OM_uint32 gss_unwrap +static OM_uint32 +unwrap_des (OM_uint32 * minor_status, const gss_ctx_id_t context_handle, const gss_buffer_t input_message_buffer, gss_buffer_t output_message_buffer, int * conf_state, - gss_qop_t * qop_state + gss_qop_t * qop_state, + krb5_keyblock *key ) { u_char *p, *pad; @@ -73,7 +74,7 @@ OM_uint32 gss_unwrap MD5_CTX md5; u_char hash[16], seq_data[8]; des_key_schedule schedule; - des_cblock key; + des_cblock deskey; des_cblock zero; int i; int32_t seq_number; @@ -109,19 +110,20 @@ OM_uint32 gss_unwrap if(cstate) { /* decrypt data */ - gss_krb5_getsomekey(context_handle, &key); - for (i = 0; i < sizeof(key); ++i) - key[i] ^= 0xf0; - des_set_key (&key, schedule); + memcpy (&deskey, key->keyvalue.data, sizeof(deskey)); + + for (i = 0; i < sizeof(deskey); ++i) + deskey[i] ^= 0xf0; + des_set_key (&deskey, schedule); memset (&zero, 0, sizeof(zero)); - des_cbc_encrypt ((const void *)p, + des_cbc_encrypt ((void *)p, (void *)p, input_message_buffer->length - len, schedule, &zero, DES_DECRYPT); - memset (key, 0, sizeof(key)); + memset (deskey, 0, sizeof(deskey)); memset (schedule, 0, sizeof(schedule)); } /* check pad */ @@ -134,15 +136,15 @@ OM_uint32 gss_unwrap if (i != 0) return GSS_S_BAD_MIC; - MD5Init (&md5); - MD5Update (&md5, p - 24, 8); - MD5Update (&md5, p, input_message_buffer->length - len); - MD5Final (hash, &md5); + MD5_Init (&md5); + MD5_Update (&md5, p - 24, 8); + MD5_Update (&md5, p, input_message_buffer->length - len); + MD5_Final (hash, &md5); memset (&zero, 0, sizeof(zero)); - gss_krb5_getsomekey(context_handle, &key); - des_set_key (&key, schedule); - des_cbc_cksum ((const void *)hash, (void *)hash, sizeof(hash), + memcpy (&deskey, key->keyvalue.data, sizeof(deskey)); + des_set_key (&deskey, schedule); + des_cbc_cksum ((void *)hash, (void *)hash, sizeof(hash), schedule, &zero); if (memcmp (p - 8, hash, 8) != 0) return GSS_S_BAD_MIC; @@ -161,11 +163,11 @@ OM_uint32 gss_unwrap 4); p -= 16; - des_set_key (&key, schedule); - des_cbc_encrypt ((const void *)p, (void *)p, 8, + des_set_key (&deskey, schedule); + des_cbc_encrypt ((void *)p, (void *)p, 8, schedule, (des_cblock *)hash, DES_DECRYPT); - memset (key, 0, sizeof(key)); + memset (deskey, 0, sizeof(deskey)); memset (schedule, 0, sizeof(schedule)); if (memcmp (p, seq_data, 8) != 0) { @@ -179,7 +181,7 @@ OM_uint32 gss_unwrap /* copy out data */ output_message_buffer->length = input_message_buffer->length - - len - 8 - padlength; + - len - padlength - 8; output_message_buffer->value = malloc(output_message_buffer->length); if(output_message_buffer->length != 0 && output_message_buffer->value == NULL) return GSS_S_FAILURE; @@ -188,3 +190,217 @@ OM_uint32 gss_unwrap output_message_buffer->length); return GSS_S_COMPLETE; } + +static OM_uint32 +unwrap_des3 + (OM_uint32 * minor_status, + const gss_ctx_id_t context_handle, + const gss_buffer_t input_message_buffer, + gss_buffer_t output_message_buffer, + int * conf_state, + gss_qop_t * qop_state, + krb5_keyblock *key + ) +{ + u_char *p, *pad; + size_t len; + u_char seq[8]; + krb5_data seq_data; + u_char cksum[20]; + int i; + int32_t seq_number; + size_t padlength; + OM_uint32 ret; + int cstate; + krb5_crypto crypto; + Checksum csum; + int cmp; + + p = input_message_buffer->value; + ret = gssapi_krb5_verify_header (&p, + input_message_buffer->length, + "\x02\x01"); + if (ret) + return ret; + + if (memcmp (p, "\x04\x00", 2) != 0) /* HMAC SHA1 DES3_KD */ + return GSS_S_BAD_SIG; + p += 2; + if (memcmp (p, "\x02\x00", 2) == 0) { + cstate = 1; + } else if (memcmp (p, "\xff\xff", 2) == 0) { + cstate = 0; + } else + return GSS_S_BAD_MIC; + p += 2; + if(conf_state != NULL) + *conf_state = cstate; + if (memcmp (p, "\xff\xff", 2) != 0) + return GSS_S_DEFECTIVE_TOKEN; + p += 2; + p += 28; + + len = p - (u_char *)input_message_buffer->value; + + if(cstate) { + /* decrypt data */ + krb5_data tmp; + + ret = krb5_crypto_init(gssapi_krb5_context, key, + ETYPE_DES3_CBC_NONE, &crypto); + if (ret) { + *minor_status = ret; + return GSS_S_FAILURE; + } + ret = krb5_decrypt(gssapi_krb5_context, crypto, KRB5_KU_USAGE_SEAL, + p, input_message_buffer->length - len, &tmp); + krb5_crypto_destroy(gssapi_krb5_context, crypto); + if (ret) { + *minor_status = ret; + return GSS_S_FAILURE; + } + assert (tmp.length == input_message_buffer->length - len); + + memcpy (p, tmp.data, tmp.length); + krb5_data_free(&tmp); + } + /* check pad */ + + pad = (u_char *)input_message_buffer->value + input_message_buffer->length - 1; + padlength = *pad; + + for (i = padlength; i > 0 && *pad == padlength; i--, pad--) + ; + if (i != 0) + return GSS_S_BAD_MIC; + + /* verify sequence number */ + + krb5_auth_getremoteseqnumber (gssapi_krb5_context, + context_handle->auth_context, + &seq_number); + seq[0] = (seq_number >> 0) & 0xFF; + seq[1] = (seq_number >> 8) & 0xFF; + seq[2] = (seq_number >> 16) & 0xFF; + seq[3] = (seq_number >> 24) & 0xFF; + memset (seq + 4, + (context_handle->more_flags & LOCAL) ? 0xFF : 0, + 4); + + p -= 28; + + ret = krb5_crypto_init(gssapi_krb5_context, key, + ETYPE_DES3_CBC_NONE_IVEC, &crypto); + if (ret) { + *minor_status = ret; + return GSS_S_FAILURE; + } + { + des_cblock ivec; + + memcpy(&ivec, p + 8, 8); + ret = krb5_decrypt_ivec (gssapi_krb5_context, + crypto, + KRB5_KU_USAGE_SEQ, + p, 8, &seq_data, + &ivec); + } + krb5_crypto_destroy (gssapi_krb5_context, crypto); + if (ret) { + *minor_status = ret; + return GSS_S_FAILURE; + } + if (seq_data.length != 8) { + krb5_data_free (&seq_data); + return GSS_S_BAD_MIC; + } + + cmp = memcmp (seq, seq_data.data, seq_data.length); + krb5_data_free (&seq_data); + if (cmp != 0) { + return GSS_S_BAD_MIC; + } + + krb5_auth_setremoteseqnumber (gssapi_krb5_context, + context_handle->auth_context, + ++seq_number); + + /* verify checksum */ + + memcpy (cksum, p + 8, 20); + + memcpy (p + 20, p - 8, 8); + + csum.cksumtype = CKSUMTYPE_HMAC_SHA1_DES3; + csum.checksum.length = 20; + csum.checksum.data = cksum; + + ret = krb5_crypto_init(gssapi_krb5_context, key, 0, &crypto); + if (ret) { + *minor_status = ret; + return GSS_S_FAILURE; + } + + ret = krb5_verify_checksum (gssapi_krb5_context, crypto, + KRB5_KU_USAGE_SIGN, + p + 20, + input_message_buffer->length - len + 8, + &csum); + krb5_crypto_destroy (gssapi_krb5_context, crypto); + if (ret) { + *minor_status = ret; + return GSS_S_FAILURE; + } + + /* copy out data */ + + output_message_buffer->length = input_message_buffer->length + - len - padlength - 8; + output_message_buffer->value = malloc(output_message_buffer->length); + if(output_message_buffer->length != 0 && output_message_buffer->value == NULL) + return GSS_S_FAILURE; + memcpy (output_message_buffer->value, + p + 36, + output_message_buffer->length); + return GSS_S_COMPLETE; +} + +OM_uint32 gss_unwrap + (OM_uint32 * minor_status, + const gss_ctx_id_t context_handle, + const gss_buffer_t input_message_buffer, + gss_buffer_t output_message_buffer, + int * conf_state, + gss_qop_t * qop_state + ) +{ + krb5_keyblock *key; + OM_uint32 ret; + krb5_keytype keytype; + + ret = gss_krb5_getsomekey(context_handle, &key); + if (ret) { + *minor_status = ret; + return GSS_S_FAILURE; + } + krb5_enctype_to_keytype (gssapi_krb5_context, key->keytype, &keytype); + + switch (keytype) { + case KEYTYPE_DES : + ret = unwrap_des (minor_status, context_handle, + input_message_buffer, output_message_buffer, + conf_state, qop_state, key); + break; + case KEYTYPE_DES3 : + ret = unwrap_des3 (minor_status, context_handle, + input_message_buffer, output_message_buffer, + conf_state, qop_state, key); + break; + default : + *minor_status = KRB5_PROG_ETYPE_NOSUPP; + ret = GSS_S_FAILURE; + break; + } + krb5_free_keyblock (gssapi_krb5_context, key); + return ret; +} diff --git a/crypto/heimdal/lib/gssapi/verify_mic.c b/crypto/heimdal/lib/gssapi/verify_mic.c index 1cc4c52..608de67 100644 --- a/crypto/heimdal/lib/gssapi/verify_mic.c +++ b/crypto/heimdal/lib/gssapi/verify_mic.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997 - 2000 Kungliga Tekniska Högskolan + * Copyright (c) 1997 - 2001 Kungliga Tekniska Högskolan * (Royal Institute of Technology, Stockholm, Sweden). * All rights reserved. * @@ -33,22 +33,24 @@ #include "gssapi_locl.h" -RCSID("$Id: verify_mic.c,v 1.9 2000/01/25 23:14:47 assar Exp $"); +RCSID("$Id: verify_mic.c,v 1.12 2001/01/29 02:08:59 assar Exp $"); -OM_uint32 gss_verify_mic +static OM_uint32 +verify_mic_des (OM_uint32 * minor_status, const gss_ctx_id_t context_handle, const gss_buffer_t message_buffer, const gss_buffer_t token_buffer, - gss_qop_t * qop_state + gss_qop_t * qop_state, + krb5_keyblock *key ) { u_char *p; MD5_CTX md5; u_char hash[16], seq_data[8]; des_key_schedule schedule; - des_cblock key; des_cblock zero; + des_cblock deskey; int32_t seq_number; OM_uint32 ret; @@ -68,25 +70,20 @@ OM_uint32 gss_verify_mic p += 16; /* verify checksum */ - MD5Init (&md5); - MD5Update (&md5, p - 24, 8); - MD5Update (&md5, message_buffer->value, + MD5_Init (&md5); + MD5_Update (&md5, p - 24, 8); + MD5_Update (&md5, message_buffer->value, message_buffer->length); - MD5Final (hash, &md5); + MD5_Final (hash, &md5); memset (&zero, 0, sizeof(zero)); -#if 0 - memcpy (&key, context_handle->auth_context->key.keyvalue.data, - sizeof(key)); -#endif - memcpy (&key, context_handle->auth_context->remote_subkey->keyvalue.data, - sizeof(key)); - - des_set_key (&key, schedule); - des_cbc_cksum ((const void *)hash, (void *)hash, sizeof(hash), + memcpy (&deskey, key->keyvalue.data, sizeof(deskey)); + + des_set_key (&deskey, schedule); + des_cbc_cksum ((void *)hash, (void *)hash, sizeof(hash), schedule, &zero); if (memcmp (p - 8, hash, 8) != 0) { - memset (key, 0, sizeof(key)); + memset (deskey, 0, sizeof(deskey)); memset (schedule, 0, sizeof(schedule)); return GSS_S_BAD_MIC; } @@ -105,11 +102,11 @@ OM_uint32 gss_verify_mic 4); p -= 16; - des_set_key (&key, schedule); - des_cbc_encrypt ((const void *)p, (void *)p, 8, + des_set_key (&deskey, schedule); + des_cbc_encrypt ((void *)p, (void *)p, 8, schedule, (des_cblock *)hash, DES_DECRYPT); - memset (key, 0, sizeof(key)); + memset (deskey, 0, sizeof(deskey)); memset (schedule, 0, sizeof(schedule)); if (memcmp (p, seq_data, 8) != 0) { @@ -122,3 +119,153 @@ OM_uint32 gss_verify_mic return GSS_S_COMPLETE; } + +static OM_uint32 +verify_mic_des3 + (OM_uint32 * minor_status, + const gss_ctx_id_t context_handle, + const gss_buffer_t message_buffer, + const gss_buffer_t token_buffer, + gss_qop_t * qop_state, + krb5_keyblock *key + ) +{ + u_char *p; + u_char seq[8]; + int32_t seq_number; + OM_uint32 ret; + krb5_crypto crypto; + krb5_data seq_data; + int cmp; + Checksum csum; + char *tmp; + + p = token_buffer->value; + ret = gssapi_krb5_verify_header (&p, + token_buffer->length, + "\x01\x01"); + if (ret) + return ret; + + if (memcmp(p, "\x04\x00", 2) != 0) /* SGN_ALG = HMAC SHA1 DES3-KD */ + return GSS_S_BAD_SIG; + p += 2; + if (memcmp (p, "\xff\xff\xff\xff", 4) != 0) + return GSS_S_BAD_MIC; + p += 4; + + ret = krb5_crypto_init(gssapi_krb5_context, key, + ETYPE_DES3_CBC_NONE, &crypto); + if (ret){ + *minor_status = ret; + return GSS_S_FAILURE; + } + + /* verify sequence number */ + + ret = krb5_decrypt (gssapi_krb5_context, + crypto, + KRB5_KU_USAGE_SEQ, + p, 8, &seq_data); + if (ret) { + krb5_crypto_destroy (gssapi_krb5_context, crypto); + *minor_status = ret; + return GSS_S_FAILURE; + } + + if (seq_data.length != 8) { + krb5_crypto_destroy (gssapi_krb5_context, crypto); + krb5_data_free (&seq_data); + return GSS_S_BAD_MIC; + } + + krb5_auth_getremoteseqnumber (gssapi_krb5_context, + context_handle->auth_context, + &seq_number); + seq[0] = (seq_number >> 0) & 0xFF; + seq[1] = (seq_number >> 8) & 0xFF; + seq[2] = (seq_number >> 16) & 0xFF; + seq[3] = (seq_number >> 24) & 0xFF; + memset (seq + 4, + (context_handle->more_flags & LOCAL) ? 0xFF : 0, + 4); + cmp = memcmp (seq, seq_data.data, seq_data.length); + krb5_data_free (&seq_data); + if (cmp != 0) { + krb5_crypto_destroy (gssapi_krb5_context, crypto); + return GSS_S_BAD_MIC; + } + + /* verify checksum */ + + tmp = malloc (message_buffer->length + 8); + if (tmp == NULL) { + krb5_crypto_destroy (gssapi_krb5_context, crypto); + *minor_status = ENOMEM; + return GSS_S_FAILURE; + } + + memcpy (tmp, p - 8, 8); + memcpy (tmp + 8, message_buffer->value, message_buffer->length); + + csum.cksumtype = CKSUMTYPE_HMAC_SHA1_DES3; + csum.checksum.length = 20; + csum.checksum.data = p + 8; + + ret = krb5_verify_checksum (gssapi_krb5_context, crypto, + KRB5_KU_USAGE_SIGN, + tmp, message_buffer->length + 8, + &csum); + free (tmp); + if (ret) { + krb5_crypto_destroy (gssapi_krb5_context, crypto); + *minor_status = ret; + return GSS_S_BAD_MIC; + } + + krb5_auth_setremoteseqnumber (gssapi_krb5_context, + context_handle->auth_context, + ++seq_number); + + krb5_crypto_destroy (gssapi_krb5_context, crypto); + return GSS_S_COMPLETE; +} + +OM_uint32 +gss_verify_mic + (OM_uint32 * minor_status, + const gss_ctx_id_t context_handle, + const gss_buffer_t message_buffer, + const gss_buffer_t token_buffer, + gss_qop_t * qop_state + ) +{ + krb5_keyblock *key; + OM_uint32 ret; + krb5_keytype keytype; + + ret = krb5_auth_con_getremotesubkey (gssapi_krb5_context, + context_handle->auth_context, + &key); + if (ret) { + *minor_status = ret; + return GSS_S_FAILURE; + } + krb5_enctype_to_keytype (gssapi_krb5_context, key->keytype, &keytype); + switch (keytype) { + case KEYTYPE_DES : + ret = verify_mic_des (minor_status, context_handle, + message_buffer, token_buffer, qop_state, key); + break; + case KEYTYPE_DES3 : + ret = verify_mic_des3 (minor_status, context_handle, + message_buffer, token_buffer, qop_state, key); + break; + default : + *minor_status = KRB5_PROG_ETYPE_NOSUPP; + ret = GSS_S_FAILURE; + break; + } + krb5_free_keyblock (gssapi_krb5_context, key); + return ret; +} diff --git a/crypto/heimdal/lib/gssapi/wrap.c b/crypto/heimdal/lib/gssapi/wrap.c index c71f2b1..1d9f51d 100644 --- a/crypto/heimdal/lib/gssapi/wrap.c +++ b/crypto/heimdal/lib/gssapi/wrap.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1997 - 2000 Kungliga Tekniska Högskolan + * Copyright (c) 1997 - 2001 Kungliga Tekniska Högskolan * (Royal Institute of Technology, Stockholm, Sweden). * All rights reserved. * @@ -33,9 +33,26 @@ #include "gssapi_locl.h" -RCSID("$Id: wrap.c,v 1.11 2000/01/25 23:15:44 assar Exp $"); +RCSID("$Id: wrap.c,v 1.15 2001/01/29 02:08:59 assar Exp $"); -OM_uint32 gss_wrap_size_limit ( +static OM_uint32 +sub_wrap_size ( + OM_uint32 req_output_size, + OM_uint32 * max_input_size, + int blocksize, + int extrasize + ) +{ + size_t len, total_len, padlength; + padlength = blocksize - (req_output_size % blocksize); + len = req_output_size + 8 + padlength + extrasize; + gssapi_krb5_encap_length(len, &len, &total_len); + *max_input_size = (OM_uint32)total_len; + return GSS_S_COMPLETE; +} + +OM_uint32 +gss_wrap_size_limit ( OM_uint32 * minor_status, const gss_ctx_id_t context_handle, int conf_req_flag, @@ -44,36 +61,58 @@ OM_uint32 gss_wrap_size_limit ( OM_uint32 * max_input_size ) { - size_t len, total_len, padlength; - padlength = 8 - (req_output_size % 8); - len = req_output_size + 8 + padlength + 22; - gssapi_krb5_encap_length(len, &len, &total_len); - *max_input_size = (OM_uint32)total_len; - return GSS_S_COMPLETE; + krb5_keyblock *key; + OM_uint32 ret; + krb5_keytype keytype; + + ret = gss_krb5_getsomekey(context_handle, &key); + if (ret) { + *minor_status = ret; + return GSS_S_FAILURE; + } + krb5_enctype_to_keytype (gssapi_krb5_context, key->keytype, &keytype); + + switch (keytype) { + case KEYTYPE_DES : + ret = sub_wrap_size(req_output_size, max_input_size, 8, 22); + break; + case KEYTYPE_DES3 : + ret = sub_wrap_size(req_output_size, max_input_size, 8, 34); + break; + default : + *minor_status = KRB5_PROG_ETYPE_NOSUPP; + ret = GSS_S_FAILURE; + break; + } + krb5_free_keyblock (gssapi_krb5_context, key); + return ret; } -OM_uint32 gss_wrap +static OM_uint32 +wrap_des (OM_uint32 * minor_status, const gss_ctx_id_t context_handle, int conf_req_flag, gss_qop_t qop_req, const gss_buffer_t input_message_buffer, int * conf_state, - gss_buffer_t output_message_buffer + gss_buffer_t output_message_buffer, + krb5_keyblock *key ) { u_char *p; MD5_CTX md5; u_char hash[16]; des_key_schedule schedule; - des_cblock key; + des_cblock deskey; des_cblock zero; int i; int32_t seq_number; - size_t len, total_len, padlength; + size_t len, total_len, padlength, datalen; padlength = 8 - (input_message_buffer->length % 8); - len = input_message_buffer->length + 8 + padlength + 22; + datalen = input_message_buffer->length + padlength + 8; + len = datalen + 22; gssapi_krb5_encap_length (len, &len, &total_len); output_message_buffer->length = total_len; @@ -83,8 +122,7 @@ OM_uint32 gss_wrap p = gssapi_krb5_make_header(output_message_buffer->value, len, - "\x02\x01"); - + "\x02\x01"); /* TOK_ID */ /* SGN_ALG */ memcpy (p, "\x00\x00", 2); @@ -110,15 +148,15 @@ OM_uint32 gss_wrap memset (p + 8 + input_message_buffer->length, padlength, padlength); /* checksum */ - MD5Init (&md5); - MD5Update (&md5, p - 24, 8); - MD5Update (&md5, p, input_message_buffer->length + padlength + 8); - MD5Final (hash, &md5); + MD5_Init (&md5); + MD5_Update (&md5, p - 24, 8); + MD5_Update (&md5, p, datalen); + MD5_Final (hash, &md5); memset (&zero, 0, sizeof(zero)); - gss_krb5_getsomekey(context_handle, &key); - des_set_key (&key, schedule); - des_cbc_cksum ((const void *)hash, (void *)hash, sizeof(hash), + memcpy (&deskey, key->keyvalue.data, sizeof(deskey)); + des_set_key (&deskey, schedule); + des_cbc_cksum ((void *)hash, (void *)hash, sizeof(hash), schedule, &zero); memcpy (p - 8, hash, 8); @@ -136,8 +174,8 @@ OM_uint32 gss_wrap (context_handle->more_flags & LOCAL) ? 0 : 0xFF, 4); - des_set_key (&key, schedule); - des_cbc_encrypt ((const void *)p, (void *)p, 8, + des_set_key (&deskey, schedule); + des_cbc_encrypt ((void *)p, (void *)p, 8, schedule, (des_cblock *)(p + 8), DES_ENCRYPT); krb5_auth_setlocalseqnumber (gssapi_krb5_context, @@ -148,22 +186,225 @@ OM_uint32 gss_wrap p += 16; if(conf_req_flag) { - gss_krb5_getsomekey(context_handle, &key); - for (i = 0; i < sizeof(key); ++i) - key[i] ^= 0xf0; - des_set_key (&key, schedule); + memcpy (&deskey, key->keyvalue.data, sizeof(deskey)); + + for (i = 0; i < sizeof(deskey); ++i) + deskey[i] ^= 0xf0; + des_set_key (&deskey, schedule); memset (&zero, 0, sizeof(zero)); - des_cbc_encrypt ((const void *)p, + des_cbc_encrypt ((void *)p, (void *)p, - 8 + input_message_buffer->length + padlength, + datalen, schedule, &zero, DES_ENCRYPT); - memset (key, 0, sizeof(key)); + memset (deskey, 0, sizeof(deskey)); memset (schedule, 0, sizeof(schedule)); } if(conf_state != NULL) *conf_state = conf_req_flag; return GSS_S_COMPLETE; } + +static OM_uint32 +wrap_des3 + (OM_uint32 * minor_status, + const gss_ctx_id_t context_handle, + int conf_req_flag, + gss_qop_t qop_req, + const gss_buffer_t input_message_buffer, + int * conf_state, + gss_buffer_t output_message_buffer, + krb5_keyblock *key + ) +{ + u_char *p; + u_char seq[8]; + int32_t seq_number; + size_t len, total_len, padlength, datalen; + u_int32_t ret; + krb5_crypto crypto; + Checksum cksum; + krb5_data encdata; + + padlength = 8 - (input_message_buffer->length % 8); + datalen = input_message_buffer->length + padlength + 8; + len = datalen + 34; + gssapi_krb5_encap_length (len, &len, &total_len); + + output_message_buffer->length = total_len; + output_message_buffer->value = malloc (total_len); + if (output_message_buffer->value == NULL) + return GSS_S_FAILURE; + + p = gssapi_krb5_make_header(output_message_buffer->value, + len, + "\x02\x01"); /* TOK_ID */ + + /* SGN_ALG */ + memcpy (p, "\x04\x00", 2); /* HMAC SHA1 DES3-KD */ + p += 2; + /* SEAL_ALG */ + if(conf_req_flag) + memcpy (p, "\x02\x00", 2); /* DES3-KD */ + else + memcpy (p, "\xff\xff", 2); + p += 2; + /* Filler */ + memcpy (p, "\xff\xff", 2); + p += 2; + + /* calculate checksum (the above + confounder + data + pad) */ + + memcpy (p + 20, p - 8, 8); + des_new_random_key((des_cblock*)(p + 28)); + memcpy (p + 28 + 8, input_message_buffer->value, + input_message_buffer->length); + memset (p + 28 + 8 + input_message_buffer->length, padlength, padlength); + + ret = krb5_crypto_init(gssapi_krb5_context, key, 0, &crypto); + if (ret) { + free (output_message_buffer->value); + *minor_status = ret; + return GSS_S_FAILURE; + } + + ret = krb5_create_checksum (gssapi_krb5_context, + crypto, + KRB5_KU_USAGE_SIGN, + p + 20, + datalen + 8, + &cksum); + krb5_crypto_destroy (gssapi_krb5_context, crypto); + if (ret) { + free (output_message_buffer->value); + *minor_status = ret; + return GSS_S_FAILURE; + } + + /* zero out SND_SEQ + SGN_CKSUM in case */ + memset (p, 0, 28); + + memcpy (p + 8, cksum.checksum.data, cksum.checksum.length); + free_Checksum (&cksum); + + /* sequence number */ + krb5_auth_getlocalseqnumber (gssapi_krb5_context, + context_handle->auth_context, + &seq_number); + + seq[0] = (seq_number >> 0) & 0xFF; + seq[1] = (seq_number >> 8) & 0xFF; + seq[2] = (seq_number >> 16) & 0xFF; + seq[3] = (seq_number >> 24) & 0xFF; + memset (seq + 4, + (context_handle->more_flags & LOCAL) ? 0 : 0xFF, + 4); + + + ret = krb5_crypto_init(gssapi_krb5_context, key, ETYPE_DES3_CBC_NONE_IVEC, + &crypto); + if (ret) { + free (output_message_buffer->value); + *minor_status = ret; + return GSS_S_FAILURE; + } + + { + des_cblock ivec; + + memcpy (&ivec, p + 8, 8); + ret = krb5_encrypt_ivec (gssapi_krb5_context, + crypto, + KRB5_KU_USAGE_SEQ, + seq, 8, &encdata, + &ivec); + } + krb5_crypto_destroy (gssapi_krb5_context, crypto); + if (ret) { + free (output_message_buffer->value); + *minor_status = ret; + return GSS_S_FAILURE; + } + + assert (encdata.length == 8); + + memcpy (p, encdata.data, encdata.length); + krb5_data_free (&encdata); + + krb5_auth_setlocalseqnumber (gssapi_krb5_context, + context_handle->auth_context, + ++seq_number); + + /* encrypt the data */ + p += 28; + + if(conf_req_flag) { + krb5_data tmp; + + ret = krb5_crypto_init(gssapi_krb5_context, key, + ETYPE_DES3_CBC_NONE, &crypto); + if (ret) { + free (output_message_buffer->value); + *minor_status = ret; + return GSS_S_FAILURE; + } + ret = krb5_encrypt(gssapi_krb5_context, crypto, KRB5_KU_USAGE_SEAL, + p, datalen, &tmp); + krb5_crypto_destroy(gssapi_krb5_context, crypto); + if (ret) { + free (output_message_buffer->value); + *minor_status = ret; + return GSS_S_FAILURE; + } + assert (tmp.length == datalen); + + memcpy (p, tmp.data, datalen); + krb5_data_free(&tmp); + } + if(conf_state != NULL) + *conf_state = conf_req_flag; + return GSS_S_COMPLETE; +} + +OM_uint32 gss_wrap + (OM_uint32 * minor_status, + const gss_ctx_id_t context_handle, + int conf_req_flag, + gss_qop_t qop_req, + const gss_buffer_t input_message_buffer, + int * conf_state, + gss_buffer_t output_message_buffer + ) +{ + krb5_keyblock *key; + OM_uint32 ret; + krb5_keytype keytype; + + ret = gss_krb5_getsomekey(context_handle, &key); + if (ret) { + *minor_status = ret; + return GSS_S_FAILURE; + } + krb5_enctype_to_keytype (gssapi_krb5_context, key->keytype, &keytype); + + switch (keytype) { + case KEYTYPE_DES : + ret = wrap_des (minor_status, context_handle, conf_req_flag, + qop_req, input_message_buffer, conf_state, + output_message_buffer, key); + break; + case KEYTYPE_DES3 : + ret = wrap_des3 (minor_status, context_handle, conf_req_flag, + qop_req, input_message_buffer, conf_state, + output_message_buffer, key); + break; + default : + *minor_status = KRB5_PROG_ETYPE_NOSUPP; + ret = GSS_S_FAILURE; + break; + } + krb5_free_keyblock (gssapi_krb5_context, key); + return ret; +} |