s3:smbd: allow "server min protocol = SMB3_00" to go via "SMB 2.???" negprot
[Samba.git] / source3 / smbd / negprot.c
blobcdde334ccba62cae9f84a50565344c5b5d0e2d86
1 /*
2 Unix SMB/CIFS implementation.
3 negprot reply code
4 Copyright (C) Andrew Tridgell 1992-1998
5 Copyright (C) Volker Lendecke 2007
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 3 of the License, or
10 (at your option) any later version.
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this program. If not, see <http://www.gnu.org/licenses/>.
21 #include "includes.h"
22 #include "smbd/smbd.h"
23 #include "smbd/globals.h"
24 #include "serverid.h"
25 #include "auth.h"
26 #include "messages.h"
27 #include "smbprofile.h"
28 #include "auth/gensec/gensec.h"
29 #include "../libcli/smb/smb_signing.h"
31 extern fstring remote_proto;
33 static void get_challenge(struct smbXsrv_connection *xconn, uint8_t buff[8])
35 NTSTATUS nt_status;
37 /* We might be called more than once, multiple negprots are
38 * permitted */
39 if (xconn->smb1.negprot.auth_context) {
40 DEBUG(3, ("get challenge: is this a secondary negprot? "
41 "sconn->negprot.auth_context is non-NULL!\n"));
42 TALLOC_FREE(xconn->smb1.negprot.auth_context);
45 DEBUG(10, ("get challenge: creating negprot_global_auth_context\n"));
46 nt_status = make_auth4_context(
47 xconn, &xconn->smb1.negprot.auth_context);
48 if (!NT_STATUS_IS_OK(nt_status)) {
49 DEBUG(0, ("make_auth_context_subsystem returned %s",
50 nt_errstr(nt_status)));
51 smb_panic("cannot make_negprot_global_auth_context!");
53 DEBUG(10, ("get challenge: getting challenge\n"));
54 xconn->smb1.negprot.auth_context->get_ntlm_challenge(
55 xconn->smb1.negprot.auth_context, buff);
58 /****************************************************************************
59 Reply for the lanman 1.0 protocol.
60 ****************************************************************************/
62 static void reply_lanman1(struct smb_request *req, uint16_t choice)
64 int secword=0;
65 time_t t = time(NULL);
66 struct smbXsrv_connection *xconn = req->xconn;
67 uint16_t raw;
68 if (lp_async_smb_echo_handler()) {
69 raw = 0;
70 } else {
71 raw = (lp_read_raw()?1:0) | (lp_write_raw()?2:0);
74 xconn->smb1.negprot.encrypted_passwords = lp_encrypt_passwords();
76 secword |= NEGOTIATE_SECURITY_USER_LEVEL;
77 if (xconn->smb1.negprot.encrypted_passwords) {
78 secword |= NEGOTIATE_SECURITY_CHALLENGE_RESPONSE;
81 reply_outbuf(req, 13, xconn->smb1.negprot.encrypted_passwords?8:0);
83 SSVAL(req->outbuf,smb_vwv0,choice);
84 SSVAL(req->outbuf,smb_vwv1,secword);
85 /* Create a token value and add it to the outgoing packet. */
86 if (xconn->smb1.negprot.encrypted_passwords) {
87 get_challenge(xconn, (uint8_t *)smb_buf(req->outbuf));
88 SSVAL(req->outbuf,smb_vwv11, 8);
91 smbXsrv_connection_init_tables(xconn, PROTOCOL_LANMAN1);
93 /* Reply, SMBlockread, SMBwritelock supported. */
94 SCVAL(req->outbuf,smb_flg, FLAG_REPLY|FLAG_SUPPORT_LOCKREAD);
95 SSVAL(req->outbuf,smb_vwv2, xconn->smb1.negprot.max_recv);
96 SSVAL(req->outbuf,smb_vwv3, lp_max_mux()); /* maxmux */
97 SSVAL(req->outbuf,smb_vwv4, 1);
98 SSVAL(req->outbuf,smb_vwv5, raw); /* tell redirector we support
99 readbraw writebraw (possibly) */
100 SIVAL(req->outbuf,smb_vwv6, getpid());
101 SSVAL(req->outbuf,smb_vwv10, set_server_zone_offset(t)/60);
103 srv_put_dos_date((char *)req->outbuf,smb_vwv8,t);
105 return;
108 /****************************************************************************
109 Reply for the lanman 2.0 protocol.
110 ****************************************************************************/
112 static void reply_lanman2(struct smb_request *req, uint16_t choice)
114 int secword=0;
115 time_t t = time(NULL);
116 struct smbXsrv_connection *xconn = req->xconn;
117 uint16_t raw;
118 if (lp_async_smb_echo_handler()) {
119 raw = 0;
120 } else {
121 raw = (lp_read_raw()?1:0) | (lp_write_raw()?2:0);
124 xconn->smb1.negprot.encrypted_passwords = lp_encrypt_passwords();
126 secword |= NEGOTIATE_SECURITY_USER_LEVEL;
127 if (xconn->smb1.negprot.encrypted_passwords) {
128 secword |= NEGOTIATE_SECURITY_CHALLENGE_RESPONSE;
131 reply_outbuf(req, 13, xconn->smb1.negprot.encrypted_passwords?8:0);
133 SSVAL(req->outbuf,smb_vwv0, choice);
134 SSVAL(req->outbuf,smb_vwv1, secword);
135 SIVAL(req->outbuf,smb_vwv6, getpid());
137 /* Create a token value and add it to the outgoing packet. */
138 if (xconn->smb1.negprot.encrypted_passwords) {
139 get_challenge(xconn, (uint8_t *)smb_buf(req->outbuf));
140 SSVAL(req->outbuf,smb_vwv11, 8);
143 smbXsrv_connection_init_tables(xconn, PROTOCOL_LANMAN2);
145 /* Reply, SMBlockread, SMBwritelock supported. */
146 SCVAL(req->outbuf,smb_flg,FLAG_REPLY|FLAG_SUPPORT_LOCKREAD);
147 SSVAL(req->outbuf,smb_vwv2,xconn->smb1.negprot.max_recv);
148 SSVAL(req->outbuf,smb_vwv3,lp_max_mux());
149 SSVAL(req->outbuf,smb_vwv4,1);
150 SSVAL(req->outbuf,smb_vwv5,raw); /* readbraw and/or writebraw */
151 SSVAL(req->outbuf,smb_vwv10, set_server_zone_offset(t)/60);
152 srv_put_dos_date((char *)req->outbuf,smb_vwv8,t);
155 /****************************************************************************
156 Generate the spnego negprot reply blob. Return the number of bytes used.
157 ****************************************************************************/
159 DATA_BLOB negprot_spnego(TALLOC_CTX *ctx, struct smbXsrv_connection *xconn)
161 DATA_BLOB blob = data_blob_null;
162 DATA_BLOB blob_out = data_blob_null;
163 nstring dos_name;
164 fstring unix_name;
165 NTSTATUS status;
166 #ifdef DEVELOPER
167 size_t slen;
168 #endif
169 struct gensec_security *gensec_security;
171 /* See if we can get an SPNEGO blob */
172 status = auth_generic_prepare(talloc_tos(),
173 xconn->remote_address,
174 &gensec_security);
175 if (NT_STATUS_IS_OK(status)) {
176 status = gensec_start_mech_by_oid(gensec_security, GENSEC_OID_SPNEGO);
177 if (NT_STATUS_IS_OK(status)) {
178 status = gensec_update(gensec_security, ctx,
179 data_blob_null, &blob);
180 /* If we get the list of OIDs, the 'OK' answer
181 * is NT_STATUS_MORE_PROCESSING_REQUIRED */
182 if (!NT_STATUS_EQUAL(status, NT_STATUS_MORE_PROCESSING_REQUIRED)) {
183 DEBUG(0, ("Failed to start SPNEGO handler for negprot OID list!\n"));
184 blob = data_blob_null;
187 TALLOC_FREE(gensec_security);
190 xconn->smb1.negprot.spnego = true;
192 /* strangely enough, NT does not sent the single OID NTLMSSP when
193 not a ADS member, it sends no OIDs at all
195 OLD COMMENT : "we can't do this until we teach our sesssion setup parser to know
196 about raw NTLMSSP (clients send no ASN.1 wrapping if we do this)"
198 Our sessionsetup code now handles raw NTLMSSP connects, so we can go
199 back to doing what W2K3 does here. This is needed to make PocketPC 2003
200 CIFS connections work with SPNEGO. See bugzilla bugs #1828 and #3133
201 for details. JRA.
205 if (blob.length == 0 || blob.data == NULL) {
206 return data_blob_null;
209 blob_out = data_blob_talloc(ctx, NULL, 16 + blob.length);
210 if (blob_out.data == NULL) {
211 data_blob_free(&blob);
212 return data_blob_null;
215 memset(blob_out.data, '\0', 16);
217 checked_strlcpy(unix_name, lp_netbios_name(), sizeof(unix_name));
218 (void)strlower_m(unix_name);
219 push_ascii_nstring(dos_name, unix_name);
220 strlcpy((char *)blob_out.data, dos_name, 17);
222 #ifdef DEVELOPER
223 /* Fix valgrind 'uninitialized bytes' issue. */
224 slen = strlen(dos_name);
225 if (slen < 16) {
226 memset(blob_out.data+slen, '\0', 16 - slen);
228 #endif
230 memcpy(&blob_out.data[16], blob.data, blob.length);
232 data_blob_free(&blob);
234 return blob_out;
237 /****************************************************************************
238 Reply for the nt protocol.
239 ****************************************************************************/
241 static void reply_nt1(struct smb_request *req, uint16_t choice)
243 /* dual names + lock_and_read + nt SMBs + remote API calls */
244 int capabilities = CAP_NT_FIND|CAP_LOCK_AND_READ|
245 CAP_LEVEL_II_OPLOCKS;
247 int secword=0;
248 bool negotiate_spnego = False;
249 struct timespec ts;
250 ssize_t ret;
251 struct smbXsrv_connection *xconn = req->xconn;
252 bool signing_desired = false;
253 bool signing_required = false;
255 xconn->smb1.negprot.encrypted_passwords = lp_encrypt_passwords();
257 /* Check the flags field to see if this is Vista.
258 WinXP sets it and Vista does not. But we have to
259 distinguish from NT which doesn't set it either. */
261 if ( (req->flags2 & FLAGS2_EXTENDED_SECURITY) &&
262 ((req->flags2 & FLAGS2_SMB_SECURITY_SIGNATURES_REQUIRED) == 0) )
264 if ((get_remote_arch() != RA_SAMBA) &&
265 (get_remote_arch() != RA_CIFSFS)) {
266 set_remote_arch( RA_VISTA );
270 reply_outbuf(req,17,0);
272 /* do spnego in user level security if the client
273 supports it and we can do encrypted passwords */
275 if (xconn->smb1.negprot.encrypted_passwords &&
276 lp_use_spnego() &&
277 (req->flags2 & FLAGS2_EXTENDED_SECURITY)) {
278 negotiate_spnego = True;
279 capabilities |= CAP_EXTENDED_SECURITY;
280 add_to_common_flags2(FLAGS2_EXTENDED_SECURITY);
281 /* Ensure FLAGS2_EXTENDED_SECURITY gets set in this reply
282 (already partially constructed. */
283 SSVAL(req->outbuf, smb_flg2,
284 req->flags2 | FLAGS2_EXTENDED_SECURITY);
287 capabilities |= CAP_NT_SMBS|CAP_RPC_REMOTE_APIS;
289 if (lp_unicode()) {
290 capabilities |= CAP_UNICODE;
293 if (lp_unix_extensions()) {
294 capabilities |= CAP_UNIX;
297 if (lp_large_readwrite())
298 capabilities |= CAP_LARGE_READX|CAP_LARGE_WRITEX|CAP_W2K_SMBS;
300 capabilities |= CAP_LARGE_FILES;
302 if (!lp_async_smb_echo_handler() && lp_read_raw() && lp_write_raw())
303 capabilities |= CAP_RAW_MODE;
305 if (lp_nt_status_support())
306 capabilities |= CAP_STATUS32;
308 if (lp_host_msdfs())
309 capabilities |= CAP_DFS;
311 secword |= NEGOTIATE_SECURITY_USER_LEVEL;
312 if (xconn->smb1.negprot.encrypted_passwords) {
313 secword |= NEGOTIATE_SECURITY_CHALLENGE_RESPONSE;
316 signing_desired = smb_signing_is_desired(xconn->smb1.signing_state);
317 signing_required = smb_signing_is_mandatory(xconn->smb1.signing_state);
319 if (signing_desired) {
320 secword |= NEGOTIATE_SECURITY_SIGNATURES_ENABLED;
321 /* No raw mode with smb signing. */
322 capabilities &= ~CAP_RAW_MODE;
323 if (signing_required) {
324 secword |=NEGOTIATE_SECURITY_SIGNATURES_REQUIRED;
328 SSVAL(req->outbuf,smb_vwv0,choice);
329 SCVAL(req->outbuf,smb_vwv1,secword);
331 smbXsrv_connection_init_tables(xconn, PROTOCOL_NT1);
333 SSVAL(req->outbuf,smb_vwv1+1, lp_max_mux()); /* maxmpx */
334 SSVAL(req->outbuf,smb_vwv2+1, 1); /* num vcs */
335 SIVAL(req->outbuf,smb_vwv3+1,
336 xconn->smb1.negprot.max_recv); /* max buffer. LOTS! */
337 SIVAL(req->outbuf,smb_vwv5+1, 0x10000); /* raw size. full 64k */
338 SIVAL(req->outbuf,smb_vwv7+1, getpid()); /* session key */
339 SIVAL(req->outbuf,smb_vwv9+1, capabilities); /* capabilities */
340 clock_gettime(CLOCK_REALTIME,&ts);
341 put_long_date_timespec(TIMESTAMP_SET_NT_OR_BETTER,(char *)req->outbuf+smb_vwv11+1,ts);
342 SSVALS(req->outbuf,smb_vwv15+1,set_server_zone_offset(ts.tv_sec)/60);
344 if (!negotiate_spnego) {
345 /* Create a token value and add it to the outgoing packet. */
346 if (xconn->smb1.negprot.encrypted_passwords) {
347 uint8_t chal[8];
348 /* note that we do not send a challenge at all if
349 we are using plaintext */
350 get_challenge(xconn, chal);
351 ret = message_push_blob(
352 &req->outbuf, data_blob_const(chal, sizeof(chal)));
353 if (ret == -1) {
354 DEBUG(0, ("Could not push challenge\n"));
355 reply_nterror(req, NT_STATUS_NO_MEMORY);
356 return;
358 SCVAL(req->outbuf, smb_vwv16+1, ret);
360 ret = message_push_string(&req->outbuf, lp_workgroup(),
361 STR_UNICODE|STR_TERMINATE
362 |STR_NOALIGN);
363 if (ret == -1) {
364 DEBUG(0, ("Could not push workgroup string\n"));
365 reply_nterror(req, NT_STATUS_NO_MEMORY);
366 return;
368 ret = message_push_string(&req->outbuf, lp_netbios_name(),
369 STR_UNICODE|STR_TERMINATE
370 |STR_NOALIGN);
371 if (ret == -1) {
372 DEBUG(0, ("Could not push netbios name string\n"));
373 reply_nterror(req, NT_STATUS_NO_MEMORY);
374 return;
376 DEBUG(3,("not using SPNEGO\n"));
377 } else {
378 DATA_BLOB spnego_blob = negprot_spnego(req, xconn);
380 if (spnego_blob.data == NULL) {
381 reply_nterror(req, NT_STATUS_NO_MEMORY);
382 return;
385 ret = message_push_blob(&req->outbuf, spnego_blob);
386 if (ret == -1) {
387 DEBUG(0, ("Could not push spnego blob\n"));
388 reply_nterror(req, NT_STATUS_NO_MEMORY);
389 return;
391 data_blob_free(&spnego_blob);
393 SCVAL(req->outbuf,smb_vwv16+1, 0);
394 DEBUG(3,("using SPNEGO\n"));
397 return;
400 /* these are the protocol lists used for auto architecture detection:
402 WinNT 3.51:
403 protocol [PC NETWORK PROGRAM 1.0]
404 protocol [XENIX CORE]
405 protocol [MICROSOFT NETWORKS 1.03]
406 protocol [LANMAN1.0]
407 protocol [Windows for Workgroups 3.1a]
408 protocol [LM1.2X002]
409 protocol [LANMAN2.1]
410 protocol [NT LM 0.12]
412 Win95:
413 protocol [PC NETWORK PROGRAM 1.0]
414 protocol [XENIX CORE]
415 protocol [MICROSOFT NETWORKS 1.03]
416 protocol [LANMAN1.0]
417 protocol [Windows for Workgroups 3.1a]
418 protocol [LM1.2X002]
419 protocol [LANMAN2.1]
420 protocol [NT LM 0.12]
422 Win2K:
423 protocol [PC NETWORK PROGRAM 1.0]
424 protocol [LANMAN1.0]
425 protocol [Windows for Workgroups 3.1a]
426 protocol [LM1.2X002]
427 protocol [LANMAN2.1]
428 protocol [NT LM 0.12]
430 Vista:
431 protocol [PC NETWORK PROGRAM 1.0]
432 protocol [LANMAN1.0]
433 protocol [Windows for Workgroups 3.1a]
434 protocol [LM1.2X002]
435 protocol [LANMAN2.1]
436 protocol [NT LM 0.12]
437 protocol [SMB 2.001]
439 OS/2:
440 protocol [PC NETWORK PROGRAM 1.0]
441 protocol [XENIX CORE]
442 protocol [LANMAN1.0]
443 protocol [LM1.2X002]
444 protocol [LANMAN2.1]
446 OSX:
447 protocol [NT LM 0.12]
448 protocol [SMB 2.002]
449 protocol [SMB 2.???]
453 * Modified to recognize the architecture of the remote machine better.
455 * This appears to be the matrix of which protocol is used by which
456 * product.
457 Protocol WfWg Win95 WinNT Win2K OS/2 Vista OSX
458 PC NETWORK PROGRAM 1.0 1 1 1 1 1 1
459 XENIX CORE 2 2
460 MICROSOFT NETWORKS 3.0 2 2
461 DOS LM1.2X002 3 3
462 MICROSOFT NETWORKS 1.03 3
463 DOS LANMAN2.1 4 4
464 LANMAN1.0 4 2 3 2
465 Windows for Workgroups 3.1a 5 5 5 3 3
466 LM1.2X002 6 4 4 4
467 LANMAN2.1 7 5 5 5
468 NT LM 0.12 6 8 6 6 6 1
469 SMB 2.001 7
470 SMB 2.002 2
471 SMB 2.??? 3
473 * tim@fsg.com 09/29/95
474 * Win2K added by matty 17/7/99
477 #define PROT_PC_NETWORK_PROGRAM_1_0 0x0001
478 #define PROT_XENIX_CORE 0x0002
479 #define PROT_MICROSOFT_NETWORKS_3_0 0x0004
480 #define PROT_DOS_LM1_2X002 0x0008
481 #define PROT_MICROSOFT_NETWORKS_1_03 0x0010
482 #define PROT_DOS_LANMAN2_1 0x0020
483 #define PROT_LANMAN1_0 0x0040
484 #define PROT_WFWG 0x0080
485 #define PROT_LM1_2X002 0x0100
486 #define PROT_LANMAN2_1 0x0200
487 #define PROT_NT_LM_0_12 0x0400
488 #define PROT_SMB_2_001 0x0800
489 #define PROT_SMB_2_002 0x1000
490 #define PROT_SMB_2_FF 0x2000
491 #define PROT_SAMBA 0x4000
492 #define PROT_POSIX_2 0x8000
494 #define ARCH_WFWG ( PROT_PC_NETWORK_PROGRAM_1_0 | PROT_MICROSOFT_NETWORKS_3_0 | \
495 PROT_DOS_LM1_2X002 | PROT_DOS_LANMAN2_1 | PROT_WFWG )
496 #define ARCH_WIN95 ( ARCH_WFWG | PROT_NT_LM_0_12 )
497 #define ARCH_WINNT ( PROT_PC_NETWORK_PROGRAM_1_0 | PROT_XENIX_CORE | \
498 PROT_MICROSOFT_NETWORKS_1_03 | PROT_LANMAN1_0 | PROT_WFWG | \
499 PROT_LM1_2X002 | PROT_LANMAN2_1 | PROT_NT_LM_0_12 )
500 #define ARCH_WIN2K ( ARCH_WINNT & ~(PROT_XENIX_CORE | PROT_MICROSOFT_NETWORKS_1_03) )
501 #define ARCH_OS2 ( ARCH_WINNT & ~(PROT_MICROSOFT_NETWORKS_1_03 | PROT_WFWG) )
502 #define ARCH_VISTA ( ARCH_WIN2K | PROT_SMB_2_001 )
503 #define ARCH_SAMBA ( PROT_SAMBA )
504 #define ARCH_CIFSFS ( PROT_POSIX_2 )
505 #define ARCH_OSX ( PROT_NT_LM_0_12 | PROT_SMB_2_002 | PROT_SMB_2_FF )
507 /* List of supported protocols, most desired first */
508 static const struct {
509 const char *proto_name;
510 const char *short_name;
511 void (*proto_reply_fn)(struct smb_request *req, uint16_t choice);
512 int protocol_level;
513 } supported_protocols[] = {
514 {"SMB 2.???", "SMB2_FF", reply_smb20ff, PROTOCOL_SMB2_10},
515 {"SMB 2.002", "SMB2_02", reply_smb2002, PROTOCOL_SMB2_02},
516 {"NT LANMAN 1.0", "NT1", reply_nt1, PROTOCOL_NT1},
517 {"NT LM 0.12", "NT1", reply_nt1, PROTOCOL_NT1},
518 {"POSIX 2", "NT1", reply_nt1, PROTOCOL_NT1},
519 {"LANMAN2.1", "LANMAN2", reply_lanman2, PROTOCOL_LANMAN2},
520 {"LM1.2X002", "LANMAN2", reply_lanman2, PROTOCOL_LANMAN2},
521 {"Samba", "LANMAN2", reply_lanman2, PROTOCOL_LANMAN2},
522 {"DOS LM1.2X002", "LANMAN2", reply_lanman2, PROTOCOL_LANMAN2},
523 {"LANMAN1.0", "LANMAN1", reply_lanman1, PROTOCOL_LANMAN1},
524 {"MICROSOFT NETWORKS 3.0", "LANMAN1", reply_lanman1, PROTOCOL_LANMAN1},
525 {NULL,NULL,NULL,0},
528 /****************************************************************************
529 Reply to a negprot.
530 conn POINTER CAN BE NULL HERE !
531 ****************************************************************************/
533 void reply_negprot(struct smb_request *req)
535 int choice= -1;
536 int chosen_level = -1;
537 int protocol;
538 const char *p;
539 int protocols = 0;
540 int num_cliprotos;
541 char **cliprotos;
542 int i;
543 size_t converted_size;
544 struct smbXsrv_connection *xconn = req->xconn;
545 struct smbd_server_connection *sconn = req->sconn;
546 bool signing_required = true;
547 int max_proto;
548 int min_proto;
550 START_PROFILE(SMBnegprot);
552 if (xconn->smb1.negprot.done) {
553 END_PROFILE(SMBnegprot);
554 exit_server_cleanly("multiple negprot's are not permitted");
556 xconn->smb1.negprot.done = true;
558 if (req->buflen == 0) {
559 DEBUG(0, ("negprot got no protocols\n"));
560 reply_nterror(req, NT_STATUS_INVALID_PARAMETER);
561 END_PROFILE(SMBnegprot);
562 return;
565 if (req->buf[req->buflen-1] != '\0') {
566 DEBUG(0, ("negprot protocols not 0-terminated\n"));
567 reply_nterror(req, NT_STATUS_INVALID_PARAMETER);
568 END_PROFILE(SMBnegprot);
569 return;
572 p = (const char *)req->buf + 1;
574 num_cliprotos = 0;
575 cliprotos = NULL;
577 while (smbreq_bufrem(req, p) > 0) {
579 char **tmp;
581 tmp = talloc_realloc(talloc_tos(), cliprotos, char *,
582 num_cliprotos+1);
583 if (tmp == NULL) {
584 DEBUG(0, ("talloc failed\n"));
585 TALLOC_FREE(cliprotos);
586 reply_nterror(req, NT_STATUS_NO_MEMORY);
587 END_PROFILE(SMBnegprot);
588 return;
591 cliprotos = tmp;
593 if (!pull_ascii_talloc(cliprotos, &cliprotos[num_cliprotos], p,
594 &converted_size)) {
595 DEBUG(0, ("pull_ascii_talloc failed\n"));
596 TALLOC_FREE(cliprotos);
597 reply_nterror(req, NT_STATUS_NO_MEMORY);
598 END_PROFILE(SMBnegprot);
599 return;
602 DEBUG(3, ("Requested protocol [%s]\n",
603 cliprotos[num_cliprotos]));
605 num_cliprotos += 1;
606 p += strlen(p) + 2;
609 for (i=0; i<num_cliprotos; i++) {
610 if (strcsequal(cliprotos[i], "Windows for Workgroups 3.1a")) {
611 protocols |= PROT_WFWG;
612 } else if (strcsequal(cliprotos[i], "DOS LM1.2X002")) {
613 protocols |= PROT_DOS_LM1_2X002;
614 } else if (strcsequal(cliprotos[i], "DOS LANMAN2.1")) {
615 protocols |= PROT_DOS_LANMAN2_1;
616 } else if (strcsequal(cliprotos[i], "LANMAN1.0")) {
617 protocols |= PROT_LANMAN1_0;
618 } else if (strcsequal(cliprotos[i], "NT LM 0.12")) {
619 protocols |= PROT_NT_LM_0_12;
620 } else if (strcsequal(cliprotos[i], "SMB 2.001")) {
621 protocols |= PROT_SMB_2_001;
622 } else if (strcsequal(cliprotos[i], "SMB 2.002")) {
623 protocols |= PROT_SMB_2_002;
624 } else if (strcsequal(cliprotos[i], "SMB 2.???")) {
625 protocols |= PROT_SMB_2_FF;
626 } else if (strcsequal(cliprotos[i], "LANMAN2.1")) {
627 protocols |= PROT_LANMAN2_1;
628 } else if (strcsequal(cliprotos[i], "LM1.2X002")) {
629 protocols |= PROT_LM1_2X002;
630 } else if (strcsequal(cliprotos[i], "MICROSOFT NETWORKS 1.03")) {
631 protocols |= PROT_MICROSOFT_NETWORKS_1_03;
632 } else if (strcsequal(cliprotos[i], "MICROSOFT NETWORKS 3.0")) {
633 protocols |= PROT_MICROSOFT_NETWORKS_3_0;
634 } else if (strcsequal(cliprotos[i], "PC NETWORK PROGRAM 1.0")) {
635 protocols |= PROT_PC_NETWORK_PROGRAM_1_0;
636 } else if (strcsequal(cliprotos[i], "XENIX CORE")) {
637 protocols |= PROT_XENIX_CORE;
638 } else if (strcsequal(cliprotos[i], "Samba")) {
639 protocols = PROT_SAMBA;
640 break;
641 } else if (strcsequal(cliprotos[i], "POSIX 2")) {
642 protocols = PROT_POSIX_2;
643 break;
647 switch ( protocols ) {
648 /* Old CIFSFS can send one arch only, NT LM 0.12. */
649 case PROT_NT_LM_0_12:
650 case ARCH_CIFSFS:
651 set_remote_arch(RA_CIFSFS);
652 break;
653 case ARCH_SAMBA:
654 set_remote_arch(RA_SAMBA);
655 break;
656 case ARCH_WFWG:
657 set_remote_arch(RA_WFWG);
658 break;
659 case ARCH_WIN95:
660 set_remote_arch(RA_WIN95);
661 break;
662 case ARCH_WINNT:
663 set_remote_arch(RA_WINNT);
664 break;
665 case ARCH_WIN2K:
666 set_remote_arch(RA_WIN2K);
667 break;
668 case ARCH_VISTA:
669 set_remote_arch(RA_VISTA);
670 break;
671 case ARCH_OS2:
672 set_remote_arch(RA_OS2);
673 break;
674 case ARCH_OSX:
675 set_remote_arch(RA_OSX);
676 break;
677 default:
678 set_remote_arch(RA_UNKNOWN);
679 break;
682 /* possibly reload - change of architecture */
683 reload_services(sconn, conn_snum_used, true);
685 /* moved from the netbios session setup code since we don't have that
686 when the client connects to port 445. Of course there is a small
687 window where we are listening to messages -- jerry */
689 serverid_register(messaging_server_id(sconn->msg_ctx),
690 FLAG_MSG_GENERAL|FLAG_MSG_SMBD
691 |FLAG_MSG_PRINT_GENERAL);
694 * Anything higher than PROTOCOL_SMB2_10 still
695 * needs to go via "SMB 2.???", which is marked
696 * as PROTOCOL_SMB2_10.
698 * The real negotiation happens via reply_smb20ff()
699 * using SMB2 Negotiation.
701 max_proto = lp_server_max_protocol();
702 if (max_proto > PROTOCOL_SMB2_10) {
703 max_proto = PROTOCOL_SMB2_10;
705 min_proto = lp_server_min_protocol();
706 if (min_proto > PROTOCOL_SMB2_10) {
707 min_proto = PROTOCOL_SMB2_10;
710 /* Check for protocols, most desirable first */
711 for (protocol = 0; supported_protocols[protocol].proto_name; protocol++) {
712 i = 0;
713 if ((supported_protocols[protocol].protocol_level <= max_proto) &&
714 (supported_protocols[protocol].protocol_level >= min_proto))
715 while (i < num_cliprotos) {
716 if (strequal(cliprotos[i],supported_protocols[protocol].proto_name)) {
717 choice = i;
718 chosen_level = supported_protocols[protocol].protocol_level;
720 i++;
722 if(choice != -1)
723 break;
726 if(choice != -1) {
727 fstrcpy(remote_proto,supported_protocols[protocol].short_name);
728 reload_services(sconn, conn_snum_used, true);
729 supported_protocols[protocol].proto_reply_fn(req, choice);
730 DEBUG(3,("Selected protocol %s\n",supported_protocols[protocol].proto_name));
731 } else {
732 DBG_NOTICE("No protocol supported !\n");
733 reply_outbuf(req, 1, 0);
734 SSVAL(req->outbuf, smb_vwv0, choice);
737 DEBUG( 5, ( "negprot index=%d\n", choice ) );
739 /* We always have xconn->smb1.signing_state also for >= SMB2_02 */
740 signing_required = smb_signing_is_mandatory(xconn->smb1.signing_state);
741 if (signing_required && (chosen_level < PROTOCOL_NT1)) {
742 exit_server_cleanly("SMB signing is required and "
743 "client negotiated a downlevel protocol");
746 TALLOC_FREE(cliprotos);
748 if (lp_async_smb_echo_handler() && (chosen_level < PROTOCOL_SMB2_02) &&
749 !fork_echo_handler(xconn)) {
750 exit_server("Failed to fork echo handler");
753 END_PROFILE(SMBnegprot);
754 return;