mirror of
https://github.com/samba-team/samba.git
synced 2024-12-22 13:34:15 +03:00
r13860: - add support for SMB2 ("SMB 2.001") negotiation in SMB negprot requests
- the default max protocol is still NT1 metze
This commit is contained in:
parent
3a6568c366
commit
d1bae931b3
@ -89,7 +89,8 @@ enum protocol_types {
|
||||
PROTOCOL_COREPLUS,
|
||||
PROTOCOL_LANMAN1,
|
||||
PROTOCOL_LANMAN2,
|
||||
PROTOCOL_NT1
|
||||
PROTOCOL_NT1,
|
||||
PROTOCOL_SMB2
|
||||
};
|
||||
|
||||
/* passed to br lock code. FIXME: Move to one of the smb-specific headers */
|
||||
|
@ -279,6 +279,7 @@ static BOOL handle_copy(const char *pszParmValue, char **ptr);
|
||||
static void set_default_server_announce_type(void);
|
||||
|
||||
static const struct enum_list enum_protocol[] = {
|
||||
{PROTOCOL_SMB2, "SMB2"},
|
||||
{PROTOCOL_NT1, "NT1"},
|
||||
{PROTOCOL_LANMAN2, "LANMAN2"},
|
||||
{PROTOCOL_LANMAN1, "LANMAN1"},
|
||||
@ -595,7 +596,6 @@ static void init_globals(void)
|
||||
myname = get_myname();
|
||||
do_parameter("netbios name", myname, NULL);
|
||||
SAFE_FREE(myname);
|
||||
do_parameter("max protocol", "NT1", NULL);
|
||||
do_parameter("name resolve order", "lmhosts wins host bcast", NULL);
|
||||
|
||||
do_parameter("fstype", FSTYPE_STRING, NULL);
|
||||
@ -646,7 +646,8 @@ static void init_globals(void)
|
||||
do_parameter("max xmit", "12288", NULL);
|
||||
do_parameter("password level", "0", NULL);
|
||||
do_parameter("LargeReadwrite", "True", NULL);
|
||||
do_parameter("minprotocol", "CORE", NULL);
|
||||
do_parameter("min protocol", "CORE", NULL);
|
||||
do_parameter("max protocol", "NT1", NULL);
|
||||
do_parameter("security", "USER", NULL);
|
||||
do_parameter("paranoid server security", "True", NULL);
|
||||
do_parameter("EncryptPasswords", "True", NULL);
|
||||
|
@ -21,7 +21,10 @@
|
||||
#include "includes.h"
|
||||
#include "auth/auth.h"
|
||||
#include "smb_server/smb_server.h"
|
||||
#include "libcli/smb2/smb2.h"
|
||||
#include "smb_server/smb2/smb2_server.h"
|
||||
#include "smbd/service_stream.h"
|
||||
#include "lib/stream/packet.h"
|
||||
|
||||
|
||||
/* initialise the auth_context for this server and return the cryptkey */
|
||||
@ -415,7 +418,33 @@ static void reply_nt1(struct smbsrv_request *req, uint16_t choice)
|
||||
req_send_reply_nosign(req);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
after a SMB2 2.001 negprot reply to a SMB negprot request
|
||||
no (SMB or SMB2) requests are allowed anymore,
|
||||
vista resets the connection in this case
|
||||
*/
|
||||
static NTSTATUS smbsrv_recv_disabled_request(void *private, DATA_BLOB blob)
|
||||
{
|
||||
struct smbsrv_connection *smb_conn = talloc_get_type(private, struct smbsrv_connection);
|
||||
smbsrv_terminate_connection(smb_conn, "Receive Packet after SMB -> SMB2 negprot");
|
||||
return NT_STATUS_OK;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
Reply for the SMB2 2.001 protocol
|
||||
****************************************************************************/
|
||||
static void reply_smb2(struct smbsrv_request *req, uint16_t choice)
|
||||
{
|
||||
struct smbsrv_connection *smb_conn = req->smb_conn;
|
||||
|
||||
/* reply with a SMB2 packet */
|
||||
smb2srv_reply_smb_negprot(req);
|
||||
req = NULL;
|
||||
|
||||
/* disallow requests */
|
||||
packet_set_callback(smb_conn->packet, smbsrv_recv_disabled_request);
|
||||
}
|
||||
|
||||
/* List of supported protocols, most desired first */
|
||||
static const struct {
|
||||
const char *proto_name;
|
||||
@ -423,6 +452,7 @@ static const struct {
|
||||
void (*proto_reply_fn)(struct smbsrv_request *req, uint16_t choice);
|
||||
int protocol_level;
|
||||
} supported_protocols[] = {
|
||||
{"SMB 2.001", "SMB2", reply_smb2, PROTOCOL_SMB2},
|
||||
{"NT LANMAN 1.0", "NT1", reply_nt1, PROTOCOL_NT1},
|
||||
{"NT LM 0.12", "NT1", reply_nt1, PROTOCOL_NT1},
|
||||
{"LANMAN2.1", "LANMAN2", reply_lanman2, PROTOCOL_LANMAN2},
|
||||
|
@ -173,3 +173,56 @@ void smb2srv_negprot_recv(struct smb2srv_request *req)
|
||||
}
|
||||
smb2srv_negprot_send(req, io);
|
||||
}
|
||||
|
||||
/*
|
||||
* reply to a SMB negprot request with dialect "SMB 2.001"
|
||||
*/
|
||||
void smb2srv_reply_smb_negprot(struct smbsrv_request *smb_req)
|
||||
{
|
||||
struct smb2srv_request *req;
|
||||
uint32_t body_fixed_size = 0x26;
|
||||
|
||||
/* create a fake SMB2 negprot request */
|
||||
req = talloc_zero(smb_req->smb_conn, struct smb2srv_request);
|
||||
if (!req) goto nomem;
|
||||
req->smb_conn = smb_req->smb_conn;
|
||||
req->request_time = smb_req->request_time;
|
||||
talloc_steal(req, smb_req);
|
||||
|
||||
req->in.size = NBT_HDR_SIZE+SMB2_HDR_BODY+body_fixed_size;
|
||||
req->in.allocated = req->in.size;
|
||||
req->in.buffer = talloc_size(req, req->in.allocated);
|
||||
if (!req->in.buffer) goto nomem;
|
||||
req->in.hdr = req->in.buffer + NBT_HDR_SIZE;
|
||||
req->in.body = req->in.hdr + SMB2_HDR_BODY;
|
||||
req->in.body_size = body_fixed_size;
|
||||
req->in.dynamic = NULL;
|
||||
|
||||
SIVAL(req->in.hdr, 0, SMB2_MAGIC);
|
||||
SSVAL(req->in.hdr, SMB2_HDR_LENGTH, SMB2_HDR_BODY);
|
||||
SSVAL(req->in.hdr, SMB2_HDR_PAD1, 0);
|
||||
SIVAL(req->in.hdr, SMB2_HDR_STATUS, 0);
|
||||
SSVAL(req->in.hdr, SMB2_HDR_OPCODE, SMB2_OP_NEGPROT);
|
||||
SSVAL(req->in.hdr, SMB2_HDR_PAD2, 0);
|
||||
SIVAL(req->in.hdr, SMB2_HDR_FLAGS, 0);
|
||||
SIVAL(req->in.hdr, SMB2_HDR_UNKNOWN, 0);
|
||||
SBVAL(req->in.hdr, SMB2_HDR_SEQNUM, 0);
|
||||
SIVAL(req->in.hdr, SMB2_HDR_PID, 0);
|
||||
SIVAL(req->in.hdr, SMB2_HDR_TID, 0);
|
||||
SBVAL(req->in.hdr, SMB2_HDR_UID, 0);
|
||||
memset(req->in.hdr+SMB2_HDR_SIG, 0, 16);
|
||||
|
||||
/* this seems to be a bug, they use 0x24 but the length is 0x26 */
|
||||
SSVAL(req->in.body, 0x00, 0x24);
|
||||
|
||||
SSVAL(req->in.body, 0x02, 1);
|
||||
memset(req->in.body+0x04, 0, 32);
|
||||
SSVAL(req->in.body, 0x24, 0);
|
||||
|
||||
smb2srv_negprot_recv(req);
|
||||
return;
|
||||
nomem:
|
||||
smbsrv_terminate_connection(smb_req->smb_conn, nt_errstr(NT_STATUS_NO_MEMORY));
|
||||
talloc_free(req);
|
||||
return;
|
||||
}
|
||||
|
@ -56,14 +56,14 @@ static NTSTATUS smbsrv_recv_generic_request(void *private, DATA_BLOB blob)
|
||||
packet_set_callback(smb_conn->packet, smbsrv_recv_smb_request);
|
||||
return smbsrv_recv_smb_request(smb_conn, blob);
|
||||
case SMB2_MAGIC:
|
||||
if (!lp_parm_bool(-1, "smbsrv", "enable smb2", False)) break;
|
||||
if (lp_maxprotocol() < PROTOCOL_SMB2) break;
|
||||
status = smbsrv_init_smb2_connection(smb_conn);
|
||||
NT_STATUS_NOT_OK_RETURN(status);
|
||||
packet_set_callback(smb_conn->packet, smbsrv_recv_smb2_request);
|
||||
return smbsrv_recv_smb2_request(smb_conn, blob);
|
||||
}
|
||||
|
||||
DEBUG(2,("Invalid SMB packet: protocl prefix: 0x%08X\n", protocol_version));
|
||||
DEBUG(2,("Invalid SMB packet: protocol prefix: 0x%08X\n", protocol_version));
|
||||
smbsrv_terminate_connection(smb_conn, "NON-SMB packet");
|
||||
return NT_STATUS_OK;
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user