diff options
author | Jerry Jelinek <jerry.jelinek@joyent.com> | 2019-03-15 13:22:00 +0000 |
---|---|---|
committer | Jerry Jelinek <jerry.jelinek@joyent.com> | 2019-03-15 13:22:00 +0000 |
commit | a062971fb96ae7154d88ab408f899f56aaf6df6b (patch) | |
tree | 9907dea0824c38373ef2913fd84385ed07a56c3a /usr/src/lib/libsmbfs/smb/ntlmssp.c | |
parent | 0b570b3cb1c0bf505f1b1bd352664d638b8cc359 (diff) | |
parent | b4a8b33babbf9a7a5de61ea06d09e1eb537f1f6e (diff) | |
download | illumos-joyent-a062971fb96ae7154d88ab408f899f56aaf6df6b.tar.gz |
[illumos-gate merge]
commit b4a8b33babbf9a7a5de61ea06d09e1eb537f1f6e
10483 aac: cast between incompatible function types
commit a00b240dc61ea7ab64e3881b755fca973a531e89
10146 core_pcbe_event_coverage() is missing an else
commit 542a7b7f5ccc44e3c95d6dce4ec0566f60bd9ff4
7780 mdb could extract NT_PRPSINFO information from core files
commit 2f7dba3e6747cbaaf1deb86e6ca1e2a5c96332ac
10524 wsdiff much slower after move from deprecated commands module
10448 wsdiff explodes on encoding error
10525 wsdiff output is not correct for a binary file
10526 wsdiff tries to spawn 4.8 threads
commit adee678425979226b2b55d1a0b39ce4c989382e9
9735 Need to provide SMB 2.1 Client
commit 40c0e2317898b8c774791bdc2b30bd50111ab1fa
9875 SMB client connection setup rework
commit 8329232e00f1048795bae53acb230316243aadb5
9874 Add fksmbcl development tool
Conflicts:
usr/src/cmd/mdb/common/modules/libc/libc.c
Diffstat (limited to 'usr/src/lib/libsmbfs/smb/ntlmssp.c')
-rw-r--r-- | usr/src/lib/libsmbfs/smb/ntlmssp.c | 113 |
1 files changed, 58 insertions, 55 deletions
diff --git a/usr/src/lib/libsmbfs/smb/ntlmssp.c b/usr/src/lib/libsmbfs/smb/ntlmssp.c index f39fa594ec..5ae583114d 100644 --- a/usr/src/lib/libsmbfs/smb/ntlmssp.c +++ b/usr/src/lib/libsmbfs/smb/ntlmssp.c @@ -21,7 +21,7 @@ /* * Copyright (c) 2009, 2010, Oracle and/or its affiliates. All rights reserved. - * Copyright 2013 Nexenta Systems, Inc. All rights reserved. + * Copyright 2018 Nexenta Systems, Inc. All rights reserved. */ /* @@ -67,13 +67,14 @@ #include "ntlmssp.h" /* A shorter alias for a crazy long name from [MS-NLMP] */ -#define NTLMSSP_NEGOTIATE_NTLM2 \ +#define NTLMSSP_NEGOTIATE_ESS \ NTLMSSP_NEGOTIATE_EXTENDED_SESSIONSECURITY typedef struct ntlmssp_state { uint32_t ss_flags; char *ss_target_name; /* Primary domain or server name */ struct mbuf *ss_target_info; + uchar_t ss_ssnkey[NTLM_HASH_SZ]; uchar_t ss_kxkey[NTLM_HASH_SZ]; } ntlmssp_state_t; @@ -90,8 +91,7 @@ struct sec_buf { static const char ntlmssp_id[ID_SZ] = "NTLMSSP"; static int -ntlm_rand_ssn_key(struct smb_ctx *ctx, - ntlmssp_state_t *ssp_st, struct mbdata *ek_mbp); +ntlm_rand_ssn_key(ntlmssp_state_t *ssp_st, struct mbdata *ek_mbp); /* * Get a "security buffer" (header part) @@ -249,16 +249,14 @@ ntlmssp_put_type1(struct ssp_ctx *sp, struct mbdata *out_mb) NTLMSSP_NEGOTIATE_SEAL | /* NTLMSSP_NEGOTIATE_LM_KEY (never) */ NTLMSSP_NEGOTIATE_NTLM | - /* NTLMSSP_NEGOTIATE_ALWAYS_SIGN (set below) */ - NTLMSSP_NEGOTIATE_NTLM2 | + NTLMSSP_NEGOTIATE_ALWAYS_SIGN | + NTLMSSP_NEGOTIATE_ESS | NTLMSSP_NEGOTIATE_128 | NTLMSSP_NEGOTIATE_KEY_EXCH | NTLMSSP_NEGOTIATE_56; - if (ctx->ct_vcflags & SMBV_WILL_SIGN) { - ssp_st->ss_flags |= NTLMSSP_NEGOTIATE_ALWAYS_SIGN; - ctx->ct_hflags2 |= SMB_FLAGS2_SECURITY_SIGNATURE; - } + if ((ctx->ct_vopt & SMBVOPT_SIGNING_ENABLED) == 0) + ssp_st->ss_flags &= ~NTLMSSP_NEGOTIATE_ALWAYS_SIGN; bcopy(ntlmssp_id, &hdr.h_id, ID_SZ); hdr.h_type = NTLMSSP_MSGTYPE_NEGOTIATE; @@ -447,15 +445,20 @@ ntlmssp_put_type3(struct ssp_ctx *sp, struct mbdata *out_mb) /* * We're setting up a NULL session, meaning * the lm_mbc, nt_mbc parts remain empty. - * Let's add the "anon" flag (hint). - * As there is no session key, disable the - * fancy session key stuff. + * Let's add the "anon" flag (hint), and + * as we have no OWF hashes, we can't use + * "extended session security" (_ESS). + * The SessionBaseKey is all zeros, so + * the KeyExchangeKey is too. Otherwise + * this is like NTLMv2/LMv2 */ - hdr.h_flags |= NTLMSSP_NEGOTIATE_NULL_SESSION; - ssp_st->ss_flags &= ~( - NTLMSSP_NEGOTIATE_NTLM2 | - NTLMSSP_NEGOTIATE_KEY_EXCH); + ssp_st->ss_flags |= NTLMSSP_NEGOTIATE_NULL_SESSION; + ssp_st->ss_flags &= ~NTLMSSP_NEGOTIATE_ESS; + hdr.h_flags = ssp_st->ss_flags; err = 0; + /* KeyExchangeKey = SessionBaseKey = (zeros) */ + memset(ssp_st->ss_ssnkey, 0, NTLM_HASH_SZ); + memset(ssp_st->ss_kxkey, 0, NTLM_HASH_SZ); } else if (ctx->ct_authflags & SMB_AT_NTLM2) { /* * Doing NTLMv2/LMv2 @@ -465,47 +468,49 @@ ntlmssp_put_type3(struct ssp_ctx *sp, struct mbdata *out_mb) if (err) goto out; err = ntlm_put_v2_responses(ctx, &ti_mbc, - &lm_mbc, &nt_mbc); + &lm_mbc, &nt_mbc, ssp_st->ss_ssnkey); if (err) goto out; - /* The "key exg. key" is the session base key */ - memcpy(ssp_st->ss_kxkey, ctx->ct_ssn_key, NTLM_HASH_SZ); - - } else if (ssp_st->ss_flags & NTLMSSP_NEGOTIATE_NTLM2) { + /* KeyExchangeKey = SessionBaseKey (v2) */ + memcpy(ssp_st->ss_kxkey, ssp_st->ss_ssnkey, NTLM_HASH_SZ); + } else if (ssp_st->ss_flags & NTLMSSP_NEGOTIATE_ESS) { /* * Doing NTLM ("v1x") which is NTLM with * "Extended Session Security" */ err = ntlm_put_v1x_responses(ctx, - &lm_mbc, &nt_mbc); + &lm_mbc, &nt_mbc, ssp_st->ss_ssnkey); if (err) goto out; - /* Compute the "Key exchange key". */ - ntlm2_kxkey(ctx, &lm_mbc, ssp_st->ss_kxkey); + /* + * "v1x computes the KeyExchangeKey from both the + * server and client nonce and (v1) SessionBaseKey. + */ + ntlm2_kxkey(ctx, &lm_mbc, ssp_st->ss_ssnkey, + ssp_st->ss_kxkey); } else { /* * Doing plain old NTLM (and LM if enabled) */ err = ntlm_put_v1_responses(ctx, - &lm_mbc, &nt_mbc); + &lm_mbc, &nt_mbc, ssp_st->ss_ssnkey); if (err) goto out; - /* The "key exg. key" is the session base key */ - memcpy(ssp_st->ss_kxkey, ctx->ct_ssn_key, NTLM_HASH_SZ); + /* KeyExchangeKey = SessionBaseKey (v1) */ + memcpy(ssp_st->ss_kxkey, ssp_st->ss_ssnkey, NTLM_HASH_SZ); } /* - * Compute the "Exported Session Key" and (possibly) - * the "Encrypted Random Sesion Key". - * [MS-NLMP 3.1.5.1.2] + * Compute the "ExportedSessionKey" and (possibly) the + * "EncryptedRandomSesionKey". [MS-NLMP 3.1.5.1.2] */ if (ssp_st->ss_flags & NTLMSSP_NEGOTIATE_KEY_EXCH) { - err = ntlm_rand_ssn_key(ctx, ssp_st, &ek_mbc); + err = ntlm_rand_ssn_key(ssp_st, &ek_mbc); if (err) goto out; } else { /* ExportedSessionKey is the KeyExchangeKey */ - memcpy(ctx->ct_ssn_key, ssp_st->ss_kxkey, NTLM_HASH_SZ); + memcpy(ssp_st->ss_ssnkey, ssp_st->ss_kxkey, NTLM_HASH_SZ); /* EncryptedRandomSessionKey remains NULL */ } @@ -590,7 +595,6 @@ out: */ static int ntlm_rand_ssn_key( - struct smb_ctx *ctx, ntlmssp_state_t *ssp_st, struct mbdata *ek_mbp) { @@ -603,12 +607,12 @@ ntlm_rand_ssn_key( encr_ssn_key = mb_reserve(ek_mbp, NTLM_HASH_SZ); /* Set "ExportedSessionKey to NONCE(16) */ - (void) smb_get_urandom(ctx->ct_ssn_key, NTLM_HASH_SZ); + (void) smb_get_urandom(ssp_st->ss_ssnkey, NTLM_HASH_SZ); /* Set "EncryptedRandomSessionKey" to RC4(...) */ err = smb_encrypt_RC4(encr_ssn_key, NTLM_HASH_SZ, ssp_st->ss_kxkey, NTLM_HASH_SZ, - ctx->ct_ssn_key, NTLM_HASH_SZ); + ssp_st->ss_ssnkey, NTLM_HASH_SZ); return (err); } @@ -617,34 +621,29 @@ ntlm_rand_ssn_key( * ntlmssp_final * * Called after successful authentication. - * Setup the MAC key for signing. + * Save the session key. */ int ntlmssp_final(struct ssp_ctx *sp) { struct smb_ctx *ctx = sp->smb_ctx; + ntlmssp_state_t *ssp_st = sp->sp_private; int err = 0; /* - * MAC_key is just the session key, but - * Only on the first successful auth. + * Update/save the session key. */ - if ((ctx->ct_hflags2 & SMB_FLAGS2_SECURITY_SIGNATURE) && - (ctx->ct_mackey == NULL)) { - ctx->ct_mackeylen = NTLM_HASH_SZ; - ctx->ct_mackey = malloc(ctx->ct_mackeylen); - if (ctx->ct_mackey == NULL) { - ctx->ct_mackeylen = 0; - err = ENOMEM; - goto out; - } - memcpy(ctx->ct_mackey, ctx->ct_ssn_key, NTLM_HASH_SZ); - /* - * Apparently, the server used seq. no. zero - * for our previous message, so next is two. - */ - ctx->ct_mac_seqno = 2; + if (ctx->ct_ssnkey_buf != NULL) { + free(ctx->ct_ssnkey_buf); + ctx->ct_ssnkey_buf = NULL; } + ctx->ct_ssnkey_buf = malloc(NTLM_HASH_SZ); + if (ctx->ct_ssnkey_buf == NULL) { + err = ENOMEM; + goto out; + } + ctx->ct_ssnkey_len = NTLM_HASH_SZ; + memcpy(ctx->ct_ssnkey_buf, ssp_st->ss_ssnkey, NTLM_HASH_SZ); out: return (err); @@ -728,13 +727,17 @@ int ntlmssp_init_client(struct ssp_ctx *sp) { ntlmssp_state_t *ssp_st; + smb_ctx_t *ctx = sp->smb_ctx; - if ((sp->smb_ctx->ct_authflags & + if ((ctx->ct_authflags & (SMB_AT_NTLM2 | SMB_AT_NTLM1 | SMB_AT_ANON)) == 0) { DPRINT("No NTLM authflags"); return (EINVAL); } + /* Get the client nonce. */ + (void) smb_get_urandom(ctx->ct_clnonce, NTLM_CHAL_SZ); + ssp_st = calloc(1, sizeof (*ssp_st)); if (ssp_st == NULL) return (ENOMEM); |