root/source4/heimdal/lib/gssapi/mech/gss_import_name.c

/* [<][>][^][v][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. _gss_import_export_name
  2. gss_import_name

   1 /*-
   2  * Copyright (c) 2005 Doug Rabson
   3  * All rights reserved.
   4  *
   5  * Redistribution and use in source and binary forms, with or without
   6  * modification, are permitted provided that the following conditions
   7  * are met:
   8  * 1. Redistributions of source code must retain the above copyright
   9  *    notice, this list of conditions and the following disclaimer.
  10  * 2. Redistributions in binary form must reproduce the above copyright
  11  *    notice, this list of conditions and the following disclaimer in the
  12  *    documentation and/or other materials provided with the distribution.
  13  *
  14  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
  15  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  16  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
  17  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
  18  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
  19  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
  20  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
  21  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
  22  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
  23  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
  24  * SUCH DAMAGE.
  25  *
  26  *      $FreeBSD: src/lib/libgssapi/gss_import_name.c,v 1.1 2005/12/29 14:40:20 dfr Exp $
  27  */
  28 
  29 #include "mech_locl.h"
  30 RCSID("$Id$");
  31 
  32 static OM_uint32
  33 _gss_import_export_name(OM_uint32 *minor_status,
     /* [<][>][^][v][top][bottom][index][help] */
  34     const gss_buffer_t input_name_buffer,
  35     gss_name_t *output_name)
  36 {
  37         OM_uint32 major_status;
  38         unsigned char *p = input_name_buffer->value;
  39         size_t len = input_name_buffer->length;
  40         size_t t;
  41         gss_OID_desc mech_oid;
  42         gssapi_mech_interface m;
  43         struct _gss_name *name;
  44         gss_name_t new_canonical_name;
  45 
  46         *minor_status = 0;
  47         *output_name = 0;
  48 
  49         /*
  50          * Make sure that TOK_ID is {4, 1}.
  51          */
  52         if (len < 2)
  53                 return (GSS_S_BAD_NAME);
  54         if (p[0] != 4 || p[1] != 1)
  55                 return (GSS_S_BAD_NAME);
  56         p += 2;
  57         len -= 2;
  58 
  59         /*
  60          * Get the mech length and the name length and sanity
  61          * check the size of of the buffer.
  62          */
  63         if (len < 2)
  64                 return (GSS_S_BAD_NAME);
  65         t = (p[0] << 8) + p[1];
  66         p += 2;
  67         len -= 2;
  68 
  69         /*
  70          * Check the DER encoded OID to make sure it agrees with the
  71          * length we just decoded.
  72          */
  73         if (p[0] != 6)          /* 6=OID */
  74                 return (GSS_S_BAD_NAME);
  75         p++;
  76         len--;
  77         t--;
  78         if (p[0] & 0x80) {
  79                 int digits = p[0];
  80                 p++;
  81                 len--;
  82                 t--;
  83                 mech_oid.length = 0;
  84                 while (digits--) {
  85                         mech_oid.length = (mech_oid.length << 8) | p[0];
  86                         p++;
  87                         len--;
  88                         t--;
  89                 }
  90         } else {
  91                 mech_oid.length = p[0];
  92                 p++;
  93                 len--;
  94                 t--;
  95         }
  96         if (mech_oid.length != t)
  97                 return (GSS_S_BAD_NAME);
  98 
  99         mech_oid.elements = p;
 100 
 101         if (len < t + 4)
 102                 return (GSS_S_BAD_NAME);
 103         p += t;
 104         len -= t;
 105 
 106         t = (p[0] << 24) | (p[1] << 16) | (p[2] << 8) | p[3];
 107         p += 4;
 108         len -= 4;
 109 
 110         if (len != t)
 111                 return (GSS_S_BAD_NAME);
 112 
 113         m = __gss_get_mechanism(&mech_oid);
 114         if (!m)
 115                 return (GSS_S_BAD_MECH);
 116 
 117         /*
 118          * Ask the mechanism to import the name.
 119          */
 120         major_status = m->gm_import_name(minor_status,
 121             input_name_buffer, GSS_C_NT_EXPORT_NAME, &new_canonical_name);
 122         if (major_status != GSS_S_COMPLETE) {
 123                 _gss_mg_error(m, major_status, *minor_status);
 124                 return major_status;
 125         }
 126 
 127         /*
 128          * Now we make a new name and mark it as an MN.
 129          */
 130         name = _gss_make_name(m, new_canonical_name);
 131         if (!name) {
 132                 m->gm_release_name(minor_status, &new_canonical_name);
 133                 return (GSS_S_FAILURE);
 134         }
 135 
 136         *output_name = (gss_name_t) name;
 137 
 138         *minor_status = 0;
 139         return (GSS_S_COMPLETE);
 140 }
 141 
 142 OM_uint32 GSSAPI_LIB_FUNCTION
 143 gss_import_name(OM_uint32 *minor_status,
     /* [<][>][^][v][top][bottom][index][help] */
 144     const gss_buffer_t input_name_buffer,
 145     const gss_OID input_name_type,
 146     gss_name_t *output_name)
 147 {
 148         gss_OID                 name_type = input_name_type;
 149         OM_uint32               major_status;
 150         struct _gss_name        *name;
 151 
 152         *output_name = GSS_C_NO_NAME;
 153 
 154         if (input_name_buffer->length == 0) {
 155                 *minor_status = 0;
 156                 return (GSS_S_BAD_NAME);
 157         }
 158 
 159         /*
 160          * Use GSS_NT_USER_NAME as default name type.
 161          */
 162         if (name_type == GSS_C_NO_OID)
 163                 name_type = GSS_C_NT_USER_NAME;
 164 
 165         /*
 166          * If this is an exported name, we need to parse it to find
 167          * the mechanism and then import it as an MN. See RFC 2743
 168          * section 3.2 for a description of the format.
 169          */
 170         if (gss_oid_equal(name_type, GSS_C_NT_EXPORT_NAME)) {
 171                 return _gss_import_export_name(minor_status,
 172                     input_name_buffer, output_name);
 173         }
 174 
 175         /*
 176          * Only allow certain name types. This is pretty bogus - we
 177          * should figure out the list of supported name types using
 178          * gss_inquire_names_for_mech.
 179          */
 180         if (!gss_oid_equal(name_type, GSS_C_NT_USER_NAME)
 181             && !gss_oid_equal(name_type, GSS_C_NT_MACHINE_UID_NAME)
 182             && !gss_oid_equal(name_type, GSS_C_NT_STRING_UID_NAME)
 183             && !gss_oid_equal(name_type, GSS_C_NT_HOSTBASED_SERVICE_X)
 184             && !gss_oid_equal(name_type, GSS_C_NT_HOSTBASED_SERVICE)
 185             && !gss_oid_equal(name_type, GSS_C_NT_ANONYMOUS)
 186             && !gss_oid_equal(name_type, GSS_KRB5_NT_PRINCIPAL_NAME)) {
 187                 *minor_status = 0;
 188                 return (GSS_S_BAD_NAMETYPE);
 189         }
 190 
 191         *minor_status = 0;
 192         name = malloc(sizeof(struct _gss_name));
 193         if (!name) {
 194                 *minor_status = ENOMEM;
 195                 return (GSS_S_FAILURE);
 196         }
 197         memset(name, 0, sizeof(struct _gss_name));
 198 
 199         major_status = _gss_copy_oid(minor_status,
 200             name_type, &name->gn_type);
 201         if (major_status) {
 202                 free(name);
 203                 return (GSS_S_FAILURE);
 204         }
 205 
 206         major_status = _gss_copy_buffer(minor_status,
 207             input_name_buffer, &name->gn_value);
 208         if (major_status) {
 209                 gss_name_t rname = (gss_name_t)name;
 210                 gss_release_name(minor_status, &rname);
 211                 return (GSS_S_FAILURE);
 212         }
 213 
 214         SLIST_INIT(&name->gn_mn);
 215 
 216         *output_name = (gss_name_t) name;
 217         return (GSS_S_COMPLETE);
 218 }

/* [<][>][^][v][top][bottom][index][help] */