Print this page
NEX-10231 SMB logon fails in fksmbd
Reviewed by: Evan Layton <evan.layton@nexenta.com>
Reviewed by: Gordon Ross <gordon.ross@nexenta.com>
NEX-5273 SMB 3 Encryption
Reviewed by: Gordon Ross <gordon.ross@nexenta.com>
Reviewed by: Evan Layton <evan.layton@nexenta.com>
Reviewed by: Roman Strashkin <roman.strashkin@nexenta.com>
NEX-3728 SMB1 signing should use KCF like SMB2/3
Reviewed by: Matt Barden <matt.barden@nexenta.com>
Reviewed by: Dan Fields <dan.fields@nexenta.com>
NEX-3610 CLONE NEX-3591 SMB3 signing
Reviewed by: Gordon Ross <gwr@nexenta.com>
Reviewed by: Dan Fields <dan.fields@nexenta.com>
NEX-3080 SMB1 signing problem with Kerberos auth.
Reviewed by: Bayard Bell <bayard.bell@nexenta.com>
Reviewed by: Dan Fields <dan.fields@nexenta.com>
Reviewed by: Kevin Crowe <kevin.crowe@nexenta.com>
Reviewed by: Matt Barden <Matt.Barden@nexenta.com>
SMB-55 SMB2 signing
SMB-56 extended security NTLMSSP, inbound
SMB-50 User-mode SMB server
 Includes work by these authors:
 Thomas Keiser <thomas.keiser@nexenta.com>
 Albert Lee <trisk@nexenta.com>
SMB-65 SMB server in non-global zones (kmem_caches)
common kmem_cache instances across zones
separate GZ-only init from NGZ init
        
*** 18,28 ****
   *
   * CDDL HEADER END
   */
  /*
   * Copyright (c) 2007, 2010, Oracle and/or its affiliates. All rights reserved.
!  * Copyright 2015 Nexenta Systems, Inc.  All rights reserved.
   */
  /*
   * These routines provide the SMB MAC signing for the SMB server.
   * The routines calculate the signature of a SMB message in an mbuf chain.
   *
--- 18,28 ----
   *
   * CDDL HEADER END
   */
  /*
   * Copyright (c) 2007, 2010, Oracle and/or its affiliates. All rights reserved.
!  * Copyright 2017 Nexenta Systems, Inc.  All rights reserved.
   */
  /*
   * These routines provide the SMB MAC signing for the SMB server.
   * The routines calculate the signature of a SMB message in an mbuf chain.
   *
*** 38,48 ****
   * Disabled     | Fail          | Not Signed  | Not Signed
   */
  
  #include <sys/uio.h>
  #include <smbsrv/smb_kproto.h>
! #include <smbsrv/smb_signing.h>
  #include <sys/isa_defs.h>
  #include <sys/byteorder.h>
  
  #define SMB_SIG_SIZE    8
  #define SMB_SIG_OFFS    14
--- 38,48 ----
   * Disabled     | Fail          | Not Signed  | Not Signed
   */
  
  #include <sys/uio.h>
  #include <smbsrv/smb_kproto.h>
! #include <smbsrv/smb_kcrypt.h>
  #include <sys/isa_defs.h>
  #include <sys/byteorder.h>
  
  #define SMB_SIG_SIZE    8
  #define SMB_SIG_OFFS    14
*** 102,112 ****
   * Called during session destroy.
   */
  static void
  smb_sign_fini(smb_session_t *s)
  {
!         smb_sign_mech_t *mech;
  
          if ((mech = s->sign_mech) != NULL) {
                  kmem_free(mech, sizeof (*mech));
                  s->sign_mech = NULL;
          }
--- 102,112 ----
   * Called during session destroy.
   */
  static void
  smb_sign_fini(smb_session_t *s)
  {
!         smb_crypto_mech_t *mech;
  
          if ((mech = s->sign_mech) != NULL) {
                  kmem_free(mech, sizeof (*mech));
                  s->sign_mech = NULL;
          }
*** 117,143 ****
   *
   * Intializes MAC key based on the user session key and
   * NTLM response and store it in the signing structure.
   * This is what begins SMB signing.
   */
! int
  smb_sign_begin(smb_request_t *sr, smb_token_t *token)
  {
          smb_arg_sessionsetup_t *sinfo = sr->sr_ssetup;
          smb_session_t *session = sr->session;
          struct smb_sign *sign = &session->signing;
!         smb_sign_mech_t *mech;
          int rc;
  
          /*
           * We should normally have a session key here because
           * our caller filters out Anonymous and Guest logons.
           * However, buggy clients could get us here without a
           * session key, in which case: just don't sign.
           */
          if (token->tkn_ssnkey.val == NULL || token->tkn_ssnkey.len == 0)
!                 return (0);
  
          /*
           * Session-level initialization (once per session)
           */
          smb_rwx_rwenter(&session->s_lock, RW_WRITER);
--- 117,143 ----
   *
   * Intializes MAC key based on the user session key and
   * NTLM response and store it in the signing structure.
   * This is what begins SMB signing.
   */
! void
  smb_sign_begin(smb_request_t *sr, smb_token_t *token)
  {
          smb_arg_sessionsetup_t *sinfo = sr->sr_ssetup;
          smb_session_t *session = sr->session;
          struct smb_sign *sign = &session->signing;
!         smb_crypto_mech_t *mech;
          int rc;
  
          /*
           * We should normally have a session key here because
           * our caller filters out Anonymous and Guest logons.
           * However, buggy clients could get us here without a
           * session key, in which case: just don't sign.
           */
          if (token->tkn_ssnkey.val == NULL || token->tkn_ssnkey.len == 0)
!                 return;
  
          /*
           * Session-level initialization (once per session)
           */
          smb_rwx_rwenter(&session->s_lock, RW_WRITER);
*** 146,156 ****
           * Signing may already have been setup by a prior logon,
           * in which case we're done here.
           */
          if (sign->mackey != NULL) {
                  smb_rwx_rwexit(&session->s_lock);
!                 return (0);
          }
  
          /*
           * Get the mech handle
           */
--- 146,156 ----
           * Signing may already have been setup by a prior logon,
           * in which case we're done here.
           */
          if (sign->mackey != NULL) {
                  smb_rwx_rwexit(&session->s_lock);
!                 return;
          }
  
          /*
           * Get the mech handle
           */
*** 158,168 ****
                  mech = kmem_zalloc(sizeof (*mech), KM_SLEEP);
                  rc = smb_md5_getmech(mech);
                  if (rc != 0) {
                          kmem_free(mech, sizeof (*mech));
                          smb_rwx_rwexit(&session->s_lock);
!                         return (rc);
                  }
                  session->sign_mech = mech;
                  session->sign_fini = smb_sign_fini;
          }
  
--- 158,168 ----
                  mech = kmem_zalloc(sizeof (*mech), KM_SLEEP);
                  rc = smb_md5_getmech(mech);
                  if (rc != 0) {
                          kmem_free(mech, sizeof (*mech));
                          smb_rwx_rwexit(&session->s_lock);
!                         return;
                  }
                  session->sign_mech = mech;
                  session->sign_fini = smb_sign_fini;
          }
  
*** 185,202 ****
          session->signing.seqnum = 0;
          sr->sr_seqnum = 2;
          sr->reply_seqnum = 1;
          sign->flags = 0;
  
!         if (session->secmode & NEGOTIATE_SECURITY_SIGNATURES_ENABLED) {
                  sign->flags |= SMB_SIGNING_ENABLED;
!                 if (session->secmode & NEGOTIATE_SECURITY_SIGNATURES_REQUIRED)
                          sign->flags |= SMB_SIGNING_CHECK;
          }
  
          smb_rwx_rwexit(&session->s_lock);
-         return (0);
  }
  
  /*
   * smb_sign_calc
   *
--- 185,202 ----
          session->signing.seqnum = 0;
          sr->sr_seqnum = 2;
          sr->reply_seqnum = 1;
          sign->flags = 0;
  
!         if (session->srv_secmode & NEGOTIATE_SECURITY_SIGNATURES_ENABLED) {
                  sign->flags |= SMB_SIGNING_ENABLED;
!                 if (session->srv_secmode &
!                     NEGOTIATE_SECURITY_SIGNATURES_REQUIRED)
                          sign->flags |= SMB_SIGNING_CHECK;
          }
  
          smb_rwx_rwexit(&session->s_lock);
  }
  
  /*
   * smb_sign_calc
   *