diff options
-rw-r--r-- | src/gss_creds.c | 110 | ||||
-rw-r--r-- | src/gss_ntlmssp.h | 15 | ||||
-rw-r--r-- | src/gss_spi.c | 32 | ||||
-rw-r--r-- | tests/ntlmssptest.c | 8 |
4 files changed, 165 insertions, 0 deletions
diff --git a/src/gss_creds.c b/src/gss_creds.c index 83c3066..1a3ccd0 100644 --- a/src/gss_creds.c +++ b/src/gss_creds.c @@ -358,6 +358,7 @@ done: gssntlm_release_cred(&tmpmin, (gss_cred_id_t *)&cred); } else { *output_cred_handle = (gss_cred_id_t)cred; + if (time_rec) *time_rec = GSS_C_INDEFINITE; } *minor_status = retmin; return retmaj; @@ -425,3 +426,112 @@ uint32_t gssntlm_acquire_cred_with_password(uint32_t *minor_status, actual_mechs, time_rec); } + +uint32_t gssntlm_inquire_cred(uint32_t *minor_status, + gss_cred_id_t cred_handle, + gss_name_t *name, + uint32_t *lifetime, + gss_cred_usage_t *cred_usage, + gss_OID_set *mechanisms) +{ + struct gssntlm_cred *cred; + uint32_t maj, min; + + if (minor_status == NULL) + return GSS_S_CALL_INACCESSIBLE_WRITE; + *minor_status = 0; + + if (cred_handle == GSS_C_NO_CREDENTIAL) + return GSS_S_NO_CRED; + + cred = (struct gssntlm_cred *)cred_handle; + + if (cred->type == GSSNTLM_CRED_NONE) + return GSS_S_NO_CRED; + + if (name) { + switch (cred->type) { + case GSSNTLM_CRED_NONE: + case GSSNTLM_CRED_ANON: + *name = GSS_C_NO_NAME; + break; + case GSSNTLM_CRED_USER: + maj = gssntlm_duplicate_name(minor_status, + (gss_name_t)&cred->cred.user.user, + name); + if (maj != GSS_S_COMPLETE) return maj; + break; + case GSSNTLM_CRED_SERVER: + maj = gssntlm_duplicate_name(minor_status, + (gss_name_t)&cred->cred.server.name, + name); + if (maj != GSS_S_COMPLETE) return maj; + break; + } + } + + if (lifetime) *lifetime = GSS_C_INDEFINITE; + if (cred_usage) { + if (cred->type == GSSNTLM_CRED_SERVER) { + *cred_usage = GSS_C_ACCEPT; + } else { + *cred_usage = GSS_C_INITIATE; + } + } + + if (mechanisms) { + maj = gss_create_empty_oid_set(minor_status, mechanisms); + if (maj != GSS_S_COMPLETE) { + gss_release_name(&min, name); + return maj; + } + maj = gss_add_oid_set_member(minor_status, + discard_const(&gssntlm_oid), + mechanisms); + if (maj != GSS_S_COMPLETE) { + gss_release_oid_set(&min, mechanisms); + gss_release_name(&min, name); + return maj; + } + } + + return GSS_S_COMPLETE; +} + +uint32_t gssntlm_inquire_cred_by_mech(uint32_t *minor_status, + gss_cred_id_t cred_handle, + gss_OID mech_type, + gss_name_t *name, + uint32_t *initiator_lifetime, + uint32_t *acceptor_lifetime, + gss_cred_usage_t *cred_usage) +{ + gss_cred_usage_t usage; + uint32_t lifetime; + uint32_t maj; + + maj = gssntlm_inquire_cred(minor_status, cred_handle, name, + &lifetime, &usage, NULL); + if (maj != GSS_S_COMPLETE) return maj; + + switch (usage) { + case GSS_C_INITIATE: + if (initiator_lifetime) *initiator_lifetime = lifetime; + if (acceptor_lifetime) *acceptor_lifetime = 0; + break; + case GSS_C_ACCEPT: + if (initiator_lifetime) *initiator_lifetime = 0; + if (acceptor_lifetime) *acceptor_lifetime = lifetime; + break; + case GSS_C_BOTH: + if (initiator_lifetime) *initiator_lifetime = lifetime; + if (acceptor_lifetime) *acceptor_lifetime = lifetime; + break; + default: + *minor_status = EINVAL; + return GSS_S_FAILURE; + } + + if (cred_usage) *cred_usage = usage; + return GSS_S_COMPLETE; +} diff --git a/src/gss_ntlmssp.h b/src/gss_ntlmssp.h index bba85f9..00ce908 100644 --- a/src/gss_ntlmssp.h +++ b/src/gss_ntlmssp.h @@ -303,4 +303,19 @@ uint32_t gssntlm_display_name(uint32_t *minor_status, gss_name_t input_name, gss_buffer_t output_name_buffer, gss_OID *output_name_type); + +uint32_t gssntlm_inquire_cred(uint32_t *minor_status, + gss_cred_id_t cred_handle, + gss_name_t *name, + uint32_t *lifetime, + gss_cred_usage_t *cred_usage, + gss_OID_set *mechanisms); + +uint32_t gssntlm_inquire_cred_by_mech(uint32_t *minor_status, + gss_cred_id_t cred_handle, + gss_OID mech_type, + gss_name_t *name, + uint32_t *initiator_lifetime, + uint32_t *acceptor_lifetime, + gss_cred_usage_t *cred_usage); #endif /* _GSS_NTLMSSP_H_ */ diff --git a/src/gss_spi.c b/src/gss_spi.c index 5818824..6cd2e06 100644 --- a/src/gss_spi.c +++ b/src/gss_spi.c @@ -296,3 +296,35 @@ OM_uint32 gss_set_sec_context_option(OM_uint32 *minor_status, desired_object, value); } + +OM_uint32 gss_inquire_cred(OM_uint32 *minor_status, + gss_cred_id_t cred_handle, + gss_name_t *name, + OM_uint32 *lifetime, + gss_cred_usage_t *cred_usage, + gss_OID_set *mechanisms) +{ + return gssntlm_inquire_cred(minor_status, + cred_handle, + name, + lifetime, + cred_usage, + mechanisms); +} + +OM_uint32 gss_inquire_cred_by_mech(OM_uint32 *minor_status, + gss_cred_id_t cred_handle, + gss_OID mech_type, + gss_name_t *name, + OM_uint32 *initiator_lifetime, + OM_uint32 *acceptor_lifetime, + gss_cred_usage_t *cred_usage) +{ + return gssntlm_inquire_cred_by_mech(minor_status, + cred_handle, + mech_type, + name, + initiator_lifetime, + acceptor_lifetime, + cred_usage); +} diff --git a/tests/ntlmssptest.c b/tests/ntlmssptest.c index e6b7748..f8af5d4 100644 --- a/tests/ntlmssptest.c +++ b/tests/ntlmssptest.c @@ -1164,6 +1164,14 @@ int test_gssapi_1(bool user_env_file) } } + retmaj = gssntlm_inquire_cred_by_mech(&retmin, cli_cred, GSS_C_NO_OID, + NULL, NULL, NULL, NULL); + if (retmaj != GSS_S_COMPLETE) { + fprintf(stderr, "gssntlm_import_cred_by_mech failed! (%d/%d, %s)", + retmaj, retmin, strerror(retmin)); + return EINVAL; + } + nbuf.value = discard_const(srvname); nbuf.length = strlen(srvname); retmaj = gssntlm_import_name(&retmin, &nbuf, |