diff --git a/docs-xml/smbdotconf/locking/smb3directoryleases.xml b/docs-xml/smbdotconf/locking/smb3directoryleases.xml
new file mode 100644
index 00000000000..2d36d3c5b8f
--- /dev/null
+++ b/docs-xml/smbdotconf/locking/smb3directoryleases.xml
@@ -0,0 +1,40 @@
+
+
+
+ This is an enumerated type that controls smbd whether SMB3 directory leases are
+ enabled. Directory Leasing is an SMB3-only feature which allows
+ clients to cache directories.
+
+
+ Possible values for
+ are yes, no and
+ auto, auto being the
+ default.
+
+
+ When set to auto, the effective value depends on the
+ option . If is enabled, are disabled and the other way around.
+
+
+ are only available
+ with yes,
+ yes and
+ no.
+
+
+ Enabling implicitly enables
+ .
+
+
+
+smb2 leases
+auto
+
diff --git a/docs-xml/smbdotconf/tuning/strictrename.xml b/docs-xml/smbdotconf/tuning/strictrename.xml
index 8da94c012cc..446f83378bb 100644
--- a/docs-xml/smbdotconf/tuning/strictrename.xml
+++ b/docs-xml/smbdotconf/tuning/strictrename.xml
@@ -1,6 +1,7 @@
By default a Windows SMB server prevents directory
@@ -28,6 +29,9 @@
pathnames) then renames are always allowed and this parameter
has no effect.
+ Enabling implicitly
+ enables .
+
no
diff --git a/lib/param/loadparm.c b/lib/param/loadparm.c
index db434e66262..c867527f255 100644
--- a/lib/param/loadparm.c
+++ b/lib/param/loadparm.c
@@ -3077,6 +3077,8 @@ struct loadparm_context *loadparm_init(TALLOC_CTX *mem_ctx)
lpcfg_do_global_parameter(lp_ctx, "smb2 leases", "yes");
+ lpcfg_do_global_parameter(lp_ctx, "smb3 directory leases", "Auto");
+
lpcfg_do_global_parameter(lp_ctx, "server multi channel support", "yes");
lpcfg_do_global_parameter(lp_ctx, "kerberos encryption types", "all");
diff --git a/source3/param/loadparm.c b/source3/param/loadparm.c
index 0596573176d..03506fd912e 100644
--- a/source3/param/loadparm.c
+++ b/source3/param/loadparm.c
@@ -215,7 +215,7 @@ static const struct loadparm_service _sDefault =
.follow_symlinks = true,
.sync_always = false,
.strict_allocate = false,
- .strict_rename = false,
+ ._strict_rename = false,
.strict_sync = true,
.mangling_char = '~',
.copymap = NULL,
@@ -879,6 +879,7 @@ void loadparm_s3_init_globals(struct loadparm_context *lp_ctx,
Globals.smb2_max_trans = DEFAULT_SMB2_MAX_TRANSACT;
Globals.smb2_max_credits = DEFAULT_SMB2_MAX_CREDITS;
Globals.smb2_leases = true;
+ Globals._smb3_directory_leases = Auto;
Globals.server_multi_channel_support = true;
lpcfg_string_set(Globals.ctx, &Globals.ncalrpc_dir,
@@ -4921,3 +4922,25 @@ uint32_t lp_get_async_dns_timeout(void)
*/
return MAX(Globals.async_dns_timeout, 1);
}
+
+bool lp_strict_rename(int snum)
+{
+ if (lp_smb3_directory_leases()){
+ return true;
+ }
+ return lp__strict_rename(snum);
+}
+
+int lp_smb3_directory_leases(void)
+{
+ bool dirleases = lp__smb3_directory_leases();
+
+ if (lp__smb3_directory_leases() == Auto) {
+ dirleases &= !lp_clustering();
+ }
+
+ dirleases &= lp_smb2_leases();
+ dirleases &= lp_oplocks(GLOBAL_SECTION_SNUM);
+ dirleases &= !lp_kernel_oplocks(GLOBAL_SECTION_SNUM);
+ return dirleases;
+}
diff --git a/source3/param/loadparm.h b/source3/param/loadparm.h
index e8f06ddbc2c..a33f1ae9a3b 100644
--- a/source3/param/loadparm.h
+++ b/source3/param/loadparm.h
@@ -69,6 +69,8 @@ int lp_rpc_high_port(void);
const char *lp_dns_hostname(void);
bool lp_lanman_auth(void);
enum samba_weak_crypto lp_weak_crypto(void);
+bool lp_strict_rename(int snum);
+int lp_smb3_directory_leases(void);
int lp_wi_scan_global_parametrics(
const char *regex, size_t max_matches,
diff --git a/source3/smbd/smb2_negprot.c b/source3/smbd/smb2_negprot.c
index b656865a2c8..d44ce7c7863 100644
--- a/source3/smbd/smb2_negprot.c
+++ b/source3/smbd/smb2_negprot.c
@@ -414,6 +414,13 @@ NTSTATUS smbd_smb2_request_process_negprot(struct smbd_smb2_request *req)
capabilities |= SMB2_CAP_ENCRYPTION;
}
+ if (protocol >= PROTOCOL_SMB3_00 &&
+ in_capabilities & SMB2_CAP_DIRECTORY_LEASING &&
+ lp_smb3_directory_leases())
+ {
+ capabilities |= SMB2_CAP_DIRECTORY_LEASING;
+ }
+
/*
* 0x10000 (65536) is the maximum allowed message size
* for SMB 2.0