aboutsummaryrefslogtreecommitdiffstats
path: root/lib/gssapi/mech/gss_pname_to_uid.c
diff options
context:
space:
mode:
Diffstat (limited to 'lib/gssapi/mech/gss_pname_to_uid.c')
-rw-r--r--lib/gssapi/mech/gss_pname_to_uid.c174
1 files changed, 100 insertions, 74 deletions
diff --git a/lib/gssapi/mech/gss_pname_to_uid.c b/lib/gssapi/mech/gss_pname_to_uid.c
index c5f26949f2ae..315f0e0d8147 100644
--- a/lib/gssapi/mech/gss_pname_to_uid.c
+++ b/lib/gssapi/mech/gss_pname_to_uid.c
@@ -33,21 +33,21 @@
#include "mech_locl.h"
static OM_uint32
-mech_pname_to_uid(OM_uint32 *minor_status,
- struct _gss_mechanism_name *mn,
- uid_t *uidp)
+mech_localname(OM_uint32 *minor_status,
+ struct _gss_mechanism_name *mn,
+ gss_buffer_t localname)
{
OM_uint32 major_status = GSS_S_UNAVAILABLE;
*minor_status = 0;
- if (mn->gmn_mech->gm_pname_to_uid == NULL)
+ if (mn->gmn_mech->gm_localname == NULL)
return GSS_S_UNAVAILABLE;
- major_status = mn->gmn_mech->gm_pname_to_uid(minor_status,
- mn->gmn_name,
- mn->gmn_mech_oid,
- uidp);
+ major_status = mn->gmn_mech->gm_localname(minor_status,
+ mn->gmn_name,
+ mn->gmn_mech_oid,
+ localname);
if (GSS_ERROR(major_status))
_gss_mg_error(mn->gmn_mech, major_status, *minor_status);
@@ -55,86 +55,55 @@ mech_pname_to_uid(OM_uint32 *minor_status,
}
static OM_uint32
-attr_pname_to_uid(OM_uint32 *minor_status,
- struct _gss_mechanism_name *mn,
- uid_t *uidp)
+attr_localname(OM_uint32 *minor_status,
+ struct _gss_mechanism_name *mn,
+ gss_buffer_t localname)
{
-#ifdef NO_LOCALNAME
- return GSS_S_UNAVAILABLE;
-#else
OM_uint32 major_status = GSS_S_UNAVAILABLE;
OM_uint32 tmpMinor;
+ gss_buffer_desc value = GSS_C_EMPTY_BUFFER;
+ gss_buffer_desc display_value = GSS_C_EMPTY_BUFFER;
+ int authenticated = 0, complete = 0;
int more = -1;
*minor_status = 0;
+ localname->length = 0;
+ localname->value = NULL;
+
if (mn->gmn_mech->gm_get_name_attribute == NULL)
return GSS_S_UNAVAILABLE;
- while (more != 0) {
- gss_buffer_desc value;
- gss_buffer_desc display_value;
- int authenticated = 0, complete = 0;
-#ifdef POSIX_GETPWNAM_R
- char pwbuf[2048];
- struct passwd pw, *pwd;
-#else
- struct passwd *pwd;
-#endif
- char *localname;
-
- major_status = mn->gmn_mech->gm_get_name_attribute(minor_status,
- mn->gmn_name,
- GSS_C_ATTR_LOCAL_LOGIN_USER,
- &authenticated,
- &complete,
- &value,
- &display_value,
- &more);
- if (GSS_ERROR(major_status)) {
- _gss_mg_error(mn->gmn_mech, major_status, *minor_status);
- break;
- }
-
- localname = malloc(value.length + 1);
- if (localname == NULL) {
- major_status = GSS_S_FAILURE;
- *minor_status = ENOMEM;
- break;
- }
-
- memcpy(localname, value.value, value.length);
- localname[value.length] = '\0';
-
-#ifdef POSIX_GETPWNAM_R
- if (getpwnam_r(localname, &pw, pwbuf, sizeof(pwbuf), &pwd) != 0)
- pwd = NULL;
-#else
- pwd = getpwnam(localname);
-#endif
+ major_status = mn->gmn_mech->gm_get_name_attribute(minor_status,
+ mn->gmn_name,
+ GSS_C_ATTR_LOCAL_LOGIN_USER,
+ &authenticated,
+ &complete,
+ &value,
+ &display_value,
+ &more);
+ if (GSS_ERROR(major_status)) {
+ _gss_mg_error(mn->gmn_mech, major_status, *minor_status);
+ return major_status;
+ }
- free(localname);
+ if (authenticated) {
+ *localname = value;
+ } else {
+ major_status = GSS_S_UNAVAILABLE;
gss_release_buffer(&tmpMinor, &value);
- gss_release_buffer(&tmpMinor, &display_value);
-
- if (pwd != NULL) {
- *uidp = pwd->pw_uid;
- major_status = GSS_S_COMPLETE;
- *minor_status = 0;
- break;
- } else
- major_status = GSS_S_UNAVAILABLE;
}
+ gss_release_buffer(&tmpMinor, &display_value);
+
return major_status;
-#endif /* NO_LOCALNAME */
}
GSSAPI_LIB_FUNCTION OM_uint32 GSSAPI_LIB_CALL
-gss_pname_to_uid(OM_uint32 *minor_status,
- const gss_name_t pname,
- const gss_OID mech_type,
- uid_t *uidp)
+gss_localname(OM_uint32 *minor_status,
+ gss_const_name_t pname,
+ const gss_OID mech_type,
+ gss_buffer_t localname)
{
OM_uint32 major_status = GSS_S_UNAVAILABLE;
struct _gss_name *name = (struct _gss_name *) pname;
@@ -147,14 +116,14 @@ gss_pname_to_uid(OM_uint32 *minor_status,
if (GSS_ERROR(major_status))
return major_status;
- major_status = mech_pname_to_uid(minor_status, mn, uidp);
+ major_status = mech_localname(minor_status, mn, localname);
if (major_status != GSS_S_COMPLETE)
- major_status = attr_pname_to_uid(minor_status, mn, uidp);
+ major_status = attr_localname(minor_status, mn, localname);
} else {
HEIM_SLIST_FOREACH(mn, &name->gn_mn, gmn_link) {
- major_status = mech_pname_to_uid(minor_status, mn, uidp);
+ major_status = mech_localname(minor_status, mn, localname);
if (major_status != GSS_S_COMPLETE)
- major_status = attr_pname_to_uid(minor_status, mn, uidp);
+ major_status = attr_localname(minor_status, mn, localname);
if (major_status != GSS_S_UNAVAILABLE)
break;
}
@@ -165,3 +134,60 @@ gss_pname_to_uid(OM_uint32 *minor_status,
return major_status;
}
+
+
+GSSAPI_LIB_FUNCTION OM_uint32 GSSAPI_LIB_CALL
+gss_pname_to_uid(OM_uint32 *minor_status,
+ gss_const_name_t pname,
+ const gss_OID mech_type,
+ uid_t *uidp)
+{
+#ifdef NO_LOCALNAME
+ return GSS_S_UNAVAILABLE;
+#else
+ OM_uint32 major, tmpMinor;
+ gss_buffer_desc localname = GSS_C_EMPTY_BUFFER;
+ char *szLocalname;
+#ifdef POSIX_GETPWNAM_R
+ char pwbuf[2048];
+ struct passwd pw, *pwd;
+#else
+ struct passwd *pwd;
+#endif
+
+ major = gss_localname(minor_status, pname, mech_type, &localname);
+ if (GSS_ERROR(major))
+ return major;
+
+ szLocalname = malloc(localname.length + 1);
+ if (szLocalname == NULL) {
+ gss_release_buffer(&tmpMinor, &localname);
+ *minor_status = ENOMEM;
+ return GSS_S_FAILURE;
+ }
+
+ memcpy(szLocalname, localname.value, localname.length);
+ szLocalname[localname.length] = '\0';
+
+#ifdef POSIX_GETPWNAM_R
+ if (getpwnam_r(szLocalname, &pw, pwbuf, sizeof(pwbuf), &pwd) != 0)
+ pwd = NULL;
+#else
+ pwd = getpwnam(szLocalname);
+#endif
+
+ gss_release_buffer(&tmpMinor, &localname);
+ free(szLocalname);
+
+ *minor_status = 0;
+
+ if (pwd != NULL) {
+ *uidp = pwd->pw_uid;
+ major = GSS_S_COMPLETE;
+ } else {
+ major = GSS_S_UNAVAILABLE;
+ }
+
+ return major;
+#endif
+}