auth: Permit NULL fallback in localauth case
[openafs.git] / src / auth / authcon.c
index 36b0670..54e842d 100644 (file)
@@ -1,61 +1,40 @@
 /*
  * Copyright 2000, International Business Machines Corporation and others.
  * All Rights Reserved.
- * 
+ *
  * This software has been released under the terms of the IBM Public
  * License.  For details, see the LICENSE file in the top-level source
  * directory or online at http://www.openafs.org/dl/license10.html
  */
 
 #include <afsconfig.h>
-#if defined(UKERNEL)
-#include "afs/param.h"
-#else
 #include <afs/param.h>
-#endif
+#include <afs/stds.h>
 
+#include <roken.h>
 
-#if defined(UKERNEL)
-#include "afs/sysincludes.h"
-#include "afsincludes.h"
-#include "afs/stds.h"
-#include "afs/pthread_glock.h"
-#include "rx/rxkad.h"
-#include "rx/rx.h"
-#include "afs/cellconfig.h"
-#include "afs/keys.h"
-#include "afs/auth.h"
-#include "afs/pthread_glock.h"
-#include "des.h"
-#include "des_prototypes.h"
-#else /* defined(UKERNEL) */
-#include <afs/stds.h>
-#include <afs/pthread_glock.h>
-#include <sys/types.h>
-#ifdef AFS_NT40_ENV
-#include <winsock2.h>
-#else
-#include <sys/file.h>
-#include <sys/time.h>
-#include <netinet/in.h>
-#include <netdb.h>
+#ifdef IGNORE_SOME_GCC_WARNINGS
+# pragma GCC diagnostic warning "-Wdeprecated-declarations"
 #endif
-#include <string.h>
-#include <stdio.h>
-#include <des.h>
-#include <des_prototypes.h>
+
+#define HC_DEPRECATED
+#include <hcrypto/des.h>
+
 #include <rx/rxkad.h>
 #include <rx/rx.h>
+
+#include <afs/pthread_glock.h>
+
 #include "cellconfig.h"
 #include "keys.h"
+#include "ktc.h"
 #include "auth.h"
-#endif /* defined(UKERNEL) */
 
 /* return a null security object if nothing else can be done */
 static afs_int32
 QuickAuth(struct rx_securityClass **astr, afs_int32 *aindex)
 {
-    register struct rx_securityClass *tc;
+    struct rx_securityClass *tc;
     tc = rxnull_NewClientSecurityObject();
     *astr = tc;
     *aindex = RX_SECIDX_NULL;
@@ -66,11 +45,11 @@ QuickAuth(struct rx_securityClass **astr, afs_int32 *aindex)
 /* Return an appropriate security class and index */
 afs_int32
 afsconf_ServerAuth(void *arock,
-                  struct rx_securityClass **astr, 
+                  struct rx_securityClass **astr,
                   afs_int32 *aindex)
 {
     struct afsconf_dir *adir = (struct afsconf_dir *) arock;
-    register struct rx_securityClass *tclass;
+    struct rx_securityClass *tclass;
 
     LOCK_GLOBAL_MUTEX;
     tclass = (struct rx_securityClass *)
@@ -88,9 +67,9 @@ afsconf_ServerAuth(void *arock,
 #endif /* !defined(UKERNEL) */
 
 static afs_int32
-GenericAuth(struct afsconf_dir *adir, 
-           struct rx_securityClass **astr, 
-           afs_int32 *aindex, 
+GenericAuth(struct afsconf_dir *adir,
+           struct rx_securityClass **astr,
+           afs_int32 *aindex,
            rxkad_level enclevel)
 {
     char tbuffer[256];
@@ -98,7 +77,7 @@ GenericAuth(struct afsconf_dir *adir,
     struct rx_securityClass *tclass;
     afs_int32 kvno;
     afs_int32 ticketLen;
-    register afs_int32 code;
+    afs_int32 code;
 
     /* first, find the right key and kvno to use */
     code = afsconf_GetLatestKey(adir, &kvno, &key);
@@ -107,8 +86,8 @@ GenericAuth(struct afsconf_dir *adir,
     }
 
     /* next create random session key, using key for seed to good random */
-    des_init_random_number_generator(ktc_to_cblock(&key));
-    code = des_random_key(ktc_to_cblock(&session));
+    DES_init_random_number_generator((DES_cblock *) &key);
+    code = DES_new_random_key((DES_cblock *) &session);
     if (code) {
        return QuickAuth(astr, aindex);
     }
@@ -159,8 +138,8 @@ afsconf_ClientAuth(void *arock, struct rx_securityClass ** astr,
  * tells rxkad to encrypt the data, too.
  */
 afs_int32
-afsconf_ClientAuthSecure(void *arock, 
-                        struct rx_securityClass **astr, 
+afsconf_ClientAuthSecure(void *arock,
+                        struct rx_securityClass **astr,
                         afs_int32 *aindex)
 {
     struct afsconf_dir *adir = (struct afsconf_dir *) arock;
@@ -201,7 +180,7 @@ afsconf_ClientAuthToken(struct afsconf_cell *info,
                        afs_int32 *scIndex,
                        time_t *expires)
 {
-    struct ktc_principal sname;
+    struct ktc_setTokenData *tokenSet = NULL;
     struct ktc_token ttoken;
     int encryptLevel;
     afs_int32 code;
@@ -209,11 +188,11 @@ afsconf_ClientAuthToken(struct afsconf_cell *info,
     *sc = NULL;
     *scIndex = RX_SECIDX_NULL;
 
-    strcpy(sname.cell, info->name);
-    sname.instance[0] = 0;
-    strcpy(sname.name, "afs");
-    code = ktc_GetToken(&sname, &ttoken, sizeof(ttoken), NULL);
+    code = ktc_GetTokenEx(info->name, &tokenSet);
+    if (code)
+       goto out;
 
+    code = token_extractRxkad(tokenSet, &ttoken, NULL, NULL);
     if (code == 0) {
        /* XXX - We should think about how to handle this */
        if (ttoken.kvno < 0 || ttoken.kvno > 256) {
@@ -234,6 +213,10 @@ afsconf_ClientAuthToken(struct afsconf_cell *info,
        if (expires)
            *expires = ttoken.endTime;
     }
+
+out:
+    token_FreeSet(&tokenSet);
+
     if (*sc == NULL)
        return AFSCONF_NO_SECURITY_CLASS;
 
@@ -241,17 +224,28 @@ afsconf_ClientAuthToken(struct afsconf_cell *info,
 }
 
 /*!
+ * Set the security flags to be used for a particular configuration
+ */
+void
+afsconf_SetSecurityFlags(struct afsconf_dir *dir,
+                        afsconf_secflags flags)
+{
+    dir->securityFlags = flags;
+}
+
+/*!
  * Build a set of security classes suitable for a server accepting
  * incoming connections
  */
 #if !defined(UKERNEL)
 void
-afsconf_BuildServerSecurityObjects(struct afsconf_dir *dir,
-                                  afs_uint32 flags,
+afsconf_BuildServerSecurityObjects(void *rock,
                                   struct rx_securityClass ***classes,
                                   afs_int32 *numClasses)
 {
-    if (flags & AFSCONF_SEC_OBJS_RXKAD_CRYPT)
+    struct afsconf_dir *dir = rock;
+
+    if (dir->securityFlags & AFSCONF_SECOPTS_ALWAYSENCRYPT)
        *numClasses = 4;
     else
        *numClasses = 3;
@@ -262,7 +256,8 @@ afsconf_BuildServerSecurityObjects(struct afsconf_dir *dir,
     (*classes)[1] = NULL;
     (*classes)[2] = rxkad_NewServerSecurityObject(0, dir,
                                                  afsconf_GetKey, NULL);
-    if (flags & AFSCONF_SEC_OBJS_RXKAD_CRYPT)
+
+    if (dir->securityFlags & AFSCONF_SECOPTS_ALWAYSENCRYPT)
        (*classes)[3] = rxkad_NewServerSecurityObject(rxkad_crypt, dir,
                                                      afsconf_GetKey, NULL);
 }
@@ -316,17 +311,13 @@ afsconf_PickClientSecObj(struct afsconf_dir *dir, afsconf_secflags flags,
     *sc = NULL;
     *scIndex = RX_SECIDX_NULL;
     if (expires)
-       expires = 0;
+       *expires = 0;
 
     if ( !(flags & AFSCONF_SECOPTS_NOAUTH) ) {
        if (!dir)
            return AFSCONF_NOCELLDB;
 
        if (flags & AFSCONF_SECOPTS_LOCALAUTH) {
-           code = afsconf_GetLatestKey(dir, 0, 0);
-           if (code)
-               goto out;
-
            if (flags & AFSCONF_SECOPTS_ALWAYSENCRYPT)
                code = afsconf_ClientAuthSecure(dir, sc, scIndex);
            else
@@ -335,6 +326,18 @@ afsconf_PickClientSecObj(struct afsconf_dir *dir, afsconf_secflags flags,
            if (code)
                goto out;
 
+           /* The afsconf_ClientAuth functions will fall back to giving
+            * a rxnull object, which we don't want if localauth has been
+            * explicitly requested. Check for this, and bail out if we
+            * get one. Note that this leaks a security object at present
+            */
+           if (!(flags & AFSCONF_SECOPTS_FALLBACK_NULL) &&
+               *scIndex == RX_SECIDX_NULL) {
+               sc = NULL;
+               code = AFSCONF_NOTFOUND;
+               goto out;
+           }
+
            if (expires)
                *expires = NEVERDATE;
        } else {