From: Nikolay Sivov nsivov@codeweavers.com
Signed-off-by: Nikolay Sivov nsivov@codeweavers.com --- dlls/kerberos/krb5_ap.c | 59 ++++++++++++++++++++++++++++++++++++----- dlls/kerberos/unixlib.c | 11 ++++---- dlls/kerberos/unixlib.h | 11 +++++--- 3 files changed, 66 insertions(+), 15 deletions(-)
diff --git a/dlls/kerberos/krb5_ap.c b/dlls/kerberos/krb5_ap.c index efd425dc0ee..9fea8c85d89 100644 --- a/dlls/kerberos/krb5_ap.c +++ b/dlls/kerberos/krb5_ap.c @@ -77,6 +77,11 @@ static const SecPkgInfoW infoW = static ULONG kerberos_package_id; static LSA_DISPATCH_TABLE lsa_dispatch;
+struct cred_handle +{ + UINT64 handle; +}; + static const char *debugstr_us( const UNICODE_STRING *us ) { if (!us) return "<null>"; @@ -285,6 +290,7 @@ static NTSTATUS NTAPI kerberos_SpAcquireCredentialsHandle( char *principal = NULL, *username = NULL, *password = NULL; SEC_WINNT_AUTH_IDENTITY_W *id = auth_data; NTSTATUS status = SEC_E_INSUFFICIENT_MEMORY; + struct cred_handle *cred_handle; ULONG exptime;
TRACE( "%s, %#lx, %p, %p, %p, %p, %p, %p\n", debugstr_us(principal_us), credential_use, @@ -303,10 +309,19 @@ static NTSTATUS NTAPI kerberos_SpAcquireCredentialsHandle( if (!(password = get_password_unixcp( id->Password, id->PasswordLength ))) goto done; }
+ if (!(cred_handle = calloc( 1, sizeof(*cred_handle) ))) + { + status = SEC_E_INSUFFICIENT_MEMORY; + goto done; + } + { struct acquire_credentials_handle_params params = { principal, credential_use, username, password, - credential, &exptime }; - status = KRB5_CALL( acquire_credentials_handle, ¶ms ); + &cred_handle->handle, &exptime }; + if (!(status = KRB5_CALL( acquire_credentials_handle, ¶ms ))) + *credential = (LSA_SEC_HANDLE)cred_handle; + else + free( cred_handle ); expiry_to_timestamp( exptime, expiry ); }
@@ -319,9 +334,18 @@ done:
static NTSTATUS NTAPI kerberos_SpFreeCredentialsHandle( LSA_SEC_HANDLE credential ) { + struct cred_handle *cred_handle = (void *)credential; + struct free_credentials_handle_params params; + NTSTATUS status; + TRACE( "%Ix\n", credential ); - if (!credential) return SEC_E_INVALID_HANDLE; - return KRB5_CALL( free_credentials_handle, (void *)credential ); + + if (!cred_handle) return SEC_E_INVALID_HANDLE; + + params.credential = cred_handle->handle; + status = KRB5_CALL( free_credentials_handle, ¶ms ); + free(cred_handle); + return status; }
static NTSTATUS NTAPI kerberos_SpInitLsaModeContext( LSA_SEC_HANDLE credential, LSA_SEC_HANDLE context, @@ -345,8 +369,19 @@ static NTSTATUS NTAPI kerberos_SpInitLsaModeContext( LSA_SEC_HANDLE credential, if (target_name && !(target = get_str_unixcp( target_name ))) return SEC_E_INSUFFICIENT_MEMORY; else { - struct initialize_context_params params = { credential, context, target, context_req, input, - new_context, output, context_attr, &exptime }; + struct cred_handle *cred_handle = (struct cred_handle *)credential; + struct initialize_context_params params; + + params.credential = cred_handle ? cred_handle->handle : 0; + params.context = context; + params.target_name = target; + params.context_req = context_req; + params.input = input; + params.new_context = new_context; + params.output = output; + params.context_attr = context_attr; + params.expiry = &exptime; + status = KRB5_CALL( initialize_context, ¶ms ); if (!status) { @@ -372,7 +407,17 @@ static NTSTATUS NTAPI kerberos_SpAcceptLsaModeContext( LSA_SEC_HANDLE credential
if (context || input || credential) { - struct accept_context_params params = { credential, context, input, new_context, output, context_attr, &exptime }; + struct cred_handle *cred_handle = (struct cred_handle *)credential; + struct accept_context_params params; + + params.credential = cred_handle ? cred_handle->handle : 0; + params.context = context; + params.input = input; + params.new_context = new_context; + params.output = output; + params.context_attr = context_attr; + params.expiry = &exptime; + status = KRB5_CALL( accept_context, ¶ms ); if (!status) { diff --git a/dlls/kerberos/unixlib.c b/dlls/kerberos/unixlib.c index 10d2628b794..66d151488b3 100644 --- a/dlls/kerberos/unixlib.c +++ b/dlls/kerberos/unixlib.c @@ -491,9 +491,9 @@ static inline gss_ctx_id_t ctxhandle_sspi_to_gss( LSA_SEC_HANDLE handle ) return (gss_ctx_id_t)handle; }
-static inline gss_cred_id_t credhandle_sspi_to_gss( LSA_SEC_HANDLE handle ) +static inline gss_cred_id_t credhandle_sspi_to_gss( UINT64 handle ) { - return (gss_cred_id_t)handle; + return (gss_cred_id_t)(ULONG_PTR)handle; }
static inline void ctxhandle_gss_to_sspi( gss_ctx_id_t handle, LSA_SEC_HANDLE *ctx ) @@ -501,9 +501,9 @@ static inline void ctxhandle_gss_to_sspi( gss_ctx_id_t handle, LSA_SEC_HANDLE *c *ctx = (LSA_SEC_HANDLE)handle; }
-static inline void credhandle_gss_to_sspi( gss_cred_id_t handle, LSA_SEC_HANDLE *cred ) +static inline void credhandle_gss_to_sspi( gss_cred_id_t handle, UINT64 *cred ) { - *cred = (LSA_SEC_HANDLE)handle; + *cred = (ULONG_PTR)handle; }
static ULONG flags_gss_to_asc_ret( ULONG flags ) @@ -665,8 +665,9 @@ static NTSTATUS delete_context( void *args )
static NTSTATUS free_credentials_handle( void *args ) { + const struct free_credentials_handle_params *params = args; OM_uint32 ret, minor_status; - gss_cred_id_t cred = credhandle_sspi_to_gss( (LSA_SEC_HANDLE)args ); + gss_cred_id_t cred = credhandle_sspi_to_gss( params->credential );
ret = pgss_release_cred( &minor_status, &cred ); TRACE( "gss_release_cred returned %#x minor status %#x\n", ret, minor_status ); diff --git a/dlls/kerberos/unixlib.h b/dlls/kerberos/unixlib.h index 4a31712bfe8..7c3f97f436d 100644 --- a/dlls/kerberos/unixlib.h +++ b/dlls/kerberos/unixlib.h @@ -25,7 +25,7 @@
struct accept_context_params { - LSA_SEC_HANDLE credential; + UINT64 credential; LSA_SEC_HANDLE context; SecBufferDesc *input; LSA_SEC_HANDLE *new_context; @@ -40,13 +40,18 @@ struct acquire_credentials_handle_params ULONG credential_use; const char *username; const char *password; - LSA_SEC_HANDLE *credential; + UINT64 *credential; ULONG *expiry; };
+struct free_credentials_handle_params +{ + UINT64 credential; +}; + struct initialize_context_params { - LSA_SEC_HANDLE credential; + UINT64 credential; LSA_SEC_HANDLE context; const char *target_name; ULONG context_req;