[SCM] Samba Shared Repository - branch master updated

Andreas Schneider asn at samba.org
Thu Dec 19 15:45:05 UTC 2019


The branch, master has been updated
       via  8b04590e4d8 libsmbclient: If over SMB1 first try to do a posix stat on the file.
       via  b3e3cb3bbd8 s3:libsmb: Add a setup_stat_from_stat_ex() function
       via  0fe9dc5219b s3:libsmb: Return a 'struct stat' buffer for SMBC_getatr()
       via  bf9a3a7aa19 s3:libsmb: Add try_posixinfo to SMBSRV struct. Only enable for SMB1 with UNIX for now.
       via  ea51a426e50 s3:libsmb: Generate the inode only based on the path component
       via  dd694bdc643 s3:script: Try to fix a Perl warning
      from  1bfb384018d source4/utils/oLschema2ldif: include stdint.h before cmocka.h

https://git.samba.org/?p=samba.git;a=shortlog;h=master


- Log -----------------------------------------------------------------
commit 8b04590e4d8f817ad6d194bb9d622c18734e3011
Author: Andreas Schneider <asn at samba.org>
Date:   Mon Nov 25 11:11:13 2019 +0100

    libsmbclient: If over SMB1 first try to do a posix stat on the file.
    
    Disable in future, if server doesn't support this.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=14101
    
    Signed-off-by: Andreas Schneider <asn at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>
    
    Autobuild-User(master): Andreas Schneider <asn at cryptomilk.org>
    Autobuild-Date(master): Thu Dec 19 15:44:25 UTC 2019 on sn-devel-184

commit b3e3cb3bbd86a53b48ee009adf811d48dd50dc8b
Author: Andreas Schneider <asn at samba.org>
Date:   Mon Nov 25 11:10:49 2019 +0100

    s3:libsmb: Add a setup_stat_from_stat_ex() function
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=14101
    
    Signed-off-by: Andreas Schneider <asn at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit 0fe9dc5219beaf605da9c7922053f7324507b50e
Author: Andreas Schneider <asn at samba.org>
Date:   Mon Nov 25 11:09:52 2019 +0100

    s3:libsmb: Return a 'struct stat' buffer for SMBC_getatr()
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=14101
    
    Signed-off-by: Andreas Schneider <asn at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit bf9a3a7aa1913238ae2c997ce00369d0dbae3a08
Author: Andreas Schneider <asn at samba.org>
Date:   Mon Nov 25 11:06:57 2019 +0100

    s3:libsmb: Add try_posixinfo to SMBSRV struct. Only enable for SMB1 with UNIX for now.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=14101
    
    Signed-off-by: Andreas Schneider <asn at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit ea51a426e506bd6456814ecddcb63441859f9d89
Author: Andreas Schneider <asn at samba.org>
Date:   Wed Dec 18 13:27:26 2019 +0100

    s3:libsmb: Generate the inode only based on the path component
    
    Currently we use the full smb url which includes also username and
    password.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=14101
    
    Signed-off-by: Andreas Schneider <asn at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit dd694bdc643ad294475ddf2dd42b537ffeb7e8dc
Author: Andreas Schneider <asn at samba.org>
Date:   Tue Nov 26 08:21:27 2019 +0100

    s3:script: Try to fix a Perl warning
    
    Scalar value @ENV{"BASH_ENV"} better written as $ENV{"BASH_ENV"} at
    /tmp/samba-testbase/b23/samba-ad-dc-1/source3/script/tests/printing/modprinter.pl
    line 134.
    
    Signed-off-by: Andreas Schneider <asn at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

-----------------------------------------------------------------------

Summary of changes:
 source3/include/libsmb_internal.h           |  12 ++-
 source3/libsmb/libsmb_dir.c                 |  59 +++++++++-----
 source3/libsmb/libsmb_file.c                | 122 +++++++++++++++++-----------
 source3/libsmb/libsmb_server.c              |   9 ++
 source3/libsmb/libsmb_stat.c                |  62 ++++++++------
 source3/libsmb/libsmb_xattr.c               |  69 ++++++----------
 source3/script/tests/printing/modprinter.pl |   2 +-
 7 files changed, 194 insertions(+), 141 deletions(-)


Changeset truncated at 500 lines:

diff --git a/source3/include/libsmb_internal.h b/source3/include/libsmb_internal.h
index bfb3e064297..21a11c1a024 100644
--- a/source3/include/libsmb_internal.h
+++ b/source3/include/libsmb_internal.h
@@ -76,6 +76,7 @@ typedef struct DOS_ATTR_DESC {
 struct _SMBCSRV {
 	struct cli_state *cli;
 	dev_t dev;
+	bool try_posixinfo;
 	bool no_pathinfo;
 	bool no_pathinfo2;
 	bool no_pathinfo3;
@@ -407,13 +408,7 @@ bool
 SMBC_getatr(SMBCCTX * context,
             SMBCSRV *srv,
             const char *path,
-            uint16_t *mode,
-            off_t *size,
-            struct timespec *create_time_ts,
-            struct timespec *access_time_ts,
-            struct timespec *write_time_ts,
-            struct timespec *change_time_ts,
-            SMB_INO_T *ino);
+	    struct stat *sbuf);
 
 bool
 SMBC_setatr(SMBCCTX * context, SMBCSRV *srv, char *path,
@@ -537,6 +532,9 @@ void setup_stat(struct stat *st,
 		struct timespec access_time_ts,
 		struct timespec change_time_ts,
 		struct timespec write_time_ts);
+void setup_stat_from_stat_ex(const struct stat_ex *stex,
+			     const char *fname,
+			     struct stat *st);
 
 int
 SMBC_stat_ctx(SMBCCTX *context,
diff --git a/source3/libsmb/libsmb_dir.c b/source3/libsmb/libsmb_dir.c
index 8eecde0668e..00d2a878e84 100644
--- a/source3/libsmb/libsmb_dir.c
+++ b/source3/libsmb/libsmb_dir.c
@@ -475,7 +475,6 @@ SMBC_opendir_ctx(SMBCCTX *context,
 	char *workgroup = NULL;
 	char *path = NULL;
 	size_t path_len = 0;
-        uint16_t mode;
 	uint16_t port = 0;
 	SMBCSRV *srv  = NULL;
 	SMBCFILE *dir = NULL;
@@ -962,6 +961,7 @@ SMBC_opendir_ctx(SMBCCTX *context,
 				saved_errno = SMBC_errno(context, targetcli);
 
                                 if (saved_errno == EINVAL) {
+					struct stat sb = {0};
                                         /*
                                          * See if they asked to opendir
                                          * something other than a directory.
@@ -971,11 +971,11 @@ SMBC_opendir_ctx(SMBCCTX *context,
                                          */
                                         path[path_len] = '\0'; /* restore original path */
 
-                                        if (SMBC_getatr(context, srv, path,
-                                                        &mode, NULL,
-                                                        NULL, NULL, NULL, NULL,
-                                                        NULL) &&
-                                            ! IS_DOS_DIR(mode)) {
+                                        if (SMBC_getatr(context,
+							srv,
+							path,
+							&sb) &&
+                                            !S_ISDIR(sb.st_mode)) {
 
                                                 /* It is.  Correct the error value */
                                                 saved_errno = ENOTDIR;
@@ -1276,6 +1276,15 @@ const struct libsmb_file_info *SMBC_readdirplus2_ctx(SMBCCTX *context,
 	struct smbc_dirplus_list *dp_list = NULL;
 	ino_t ino;
 	char *full_pathname = NULL;
+	char *workgroup = NULL;
+	char *server = NULL;
+	uint16_t port = 0;
+	char *share = NULL;
+	char *path = NULL;
+	char *user = NULL;
+	char *password = NULL;
+	char *options = NULL;
+	int rc;
 	TALLOC_CTX *frame = NULL;
 
 	/*
@@ -1333,8 +1342,25 @@ const struct libsmb_file_info *SMBC_readdirplus2_ctx(SMBCCTX *context,
 		return NULL;
 	}
 
+	rc = SMBC_parse_path(frame,
+			     context,
+			     full_pathname,
+			     &workgroup,
+			     &server,
+			     &port,
+			     &share,
+			     &path,
+			     &user,
+			     &password,
+			     &options);
+	if (rc != 0) {
+		TALLOC_FREE(frame);
+		errno = ENOENT;
+		return NULL;
+	}
+
 	setup_stat(st,
-		full_pathname,
+		path,
 		smb_finfo->size,
 		smb_finfo->attrs,
 		ino,
@@ -2198,20 +2224,11 @@ SMBC_unlink_ctx(SMBCCTX *context,
 		if (errno == EACCES) { /* Check if the file is a directory */
 
 			int saverr = errno;
-			off_t size = 0;
-			uint16_t mode = 0;
-			struct timespec write_time_ts;
-                        struct timespec access_time_ts;
-                        struct timespec change_time_ts;
-			SMB_INO_T ino = 0;
-
-			if (!SMBC_getatr(context, srv, path, &mode, &size,
-					 NULL,
-                                         &access_time_ts,
-                                         &write_time_ts,
-                                         &change_time_ts,
-                                         &ino)) {
+			struct stat sb = {0};
+			bool ok;
 
+			ok = SMBC_getatr(context, srv, path, &sb);
+			if (!ok) {
 				/* Hmmm, bad error ... What? */
 
 				errno = SMBC_errno(context, targetcli);
@@ -2221,7 +2238,7 @@ SMBC_unlink_ctx(SMBCCTX *context,
 			}
 			else {
 
-				if (IS_DOS_DIR(mode))
+				if (S_ISDIR(sb.st_mode))
 					errno = EISDIR;
 				else
 					errno = saverr;  /* Restore this */
diff --git a/source3/libsmb/libsmb_file.c b/source3/libsmb/libsmb_file.c
index be9bcd936b2..1577010e490 100644
--- a/source3/libsmb/libsmb_file.c
+++ b/source3/libsmb/libsmb_file.c
@@ -452,18 +452,19 @@ bool
 SMBC_getatr(SMBCCTX * context,
             SMBCSRV *srv,
             const char *path,
-            uint16_t *mode,
-            off_t *size,
-            struct timespec *create_time_ts,
-            struct timespec *access_time_ts,
-            struct timespec *write_time_ts,
-            struct timespec *change_time_ts,
-            SMB_INO_T *ino)
+	    struct stat *sb)
 {
 	char *fixedpath = NULL;
 	char *targetpath = NULL;
 	struct cli_state *targetcli = NULL;
-	time_t write_time;
+	uint16_t mode = 0;
+	off_t size = 0;
+	struct timespec create_time_ts = {0};
+	struct timespec access_time_ts = {0};
+	struct timespec write_time_ts = {0};
+	struct timespec change_time_ts = {0};
+	time_t write_time = 0;
+	SMB_INO_T ino = 0;
 	TALLOC_CTX *frame = talloc_stackframe();
 	NTSTATUS status;
 
@@ -503,28 +504,56 @@ SMBC_getatr(SMBCCTX * context,
 		return False;
 	}
 
-	if (!srv->no_pathinfo2 &&
-            NT_STATUS_IS_OK(cli_qpathinfo2(targetcli, targetpath,
-                           create_time_ts,
-                           access_time_ts,
-                           write_time_ts,
-                           change_time_ts,
-			   size, mode, ino))) {
-		TALLOC_FREE(frame);
-		return True;
+	if (srv->try_posixinfo) {
+		SMB_STRUCT_STAT sbuf;
+
+		status = cli_posix_stat(targetcli, frame, &sbuf);
+		if (NT_STATUS_IS_OK(status)) {
+			setup_stat_from_stat_ex(&sbuf, path, sb);
+
+			TALLOC_FREE(frame);
+			return true;
+		}
+		if (NT_STATUS_EQUAL(status, NT_STATUS_NOT_IMPLEMENTED) ||
+		    NT_STATUS_EQUAL(status, NT_STATUS_INVALID_LEVEL)) {
+			/*
+			 * Turn this off if the server doesn't
+			 * support it.
+			 */
+			srv->try_posixinfo = false;
+		}
+	}
+
+	if (!srv->no_pathinfo2) {
+		status = cli_qpathinfo2(targetcli,
+					targetpath,
+					&create_time_ts,
+					&access_time_ts,
+					&write_time_ts,
+					&change_time_ts,
+					&size,
+					&mode,
+					&ino);
+		if (NT_STATUS_IS_OK(status)) {
+			goto setup_stat;
+		}
         }
 
 	srv->no_pathinfo2 = True;
 
-	if (!srv->no_pathinfo3 &&
-            NT_STATUS_IS_OK(cli_qpathinfo3(targetcli, targetpath,
-                           create_time_ts,
-                           access_time_ts,
-                           write_time_ts,
-                           change_time_ts,
-			   size, mode, ino))) {
-		TALLOC_FREE(frame);
-		return True;
+	if (!srv->no_pathinfo3) {
+		status = cli_qpathinfo3(targetcli,
+					targetpath,
+					&create_time_ts,
+					&access_time_ts,
+					&write_time_ts,
+					&change_time_ts,
+					&size,
+					&mode,
+					&ino);
+		if (NT_STATUS_IS_OK(status)) {
+			goto setup_stat;
+		}
         }
 
 	srv->no_pathinfo3 = True;
@@ -534,29 +563,30 @@ SMBC_getatr(SMBCCTX * context,
 		goto all_failed;
         }
 
-	if (NT_STATUS_IS_OK(cli_getatr(targetcli, targetpath, mode, size, &write_time))) {
-                struct timespec w_time_ts;
+	status = cli_getatr(targetcli, targetpath, &mode, &size, &write_time);
+	if (NT_STATUS_IS_OK(status)) {
+		struct timespec w_time_ts =
+			convert_time_t_to_timespec(write_time);
 
-                w_time_ts = convert_time_t_to_timespec(write_time);
-                if (write_time_ts != NULL) {
-			*write_time_ts = w_time_ts;
-                }
-                if (create_time_ts != NULL) {
-                        *create_time_ts = w_time_ts;
-                }
-                if (access_time_ts != NULL) {
-                        *access_time_ts = w_time_ts;
-                }
-                if (change_time_ts != NULL) {
-                        *change_time_ts = w_time_ts;
-                }
-		if (ino) {
-			*ino = 0;
-		}
-		TALLOC_FREE(frame);
-		return True;
+		access_time_ts = change_time_ts = write_time_ts = w_time_ts;
+
+		goto setup_stat;
 	}
 
+setup_stat:
+	setup_stat(sb,
+		   path,
+		   size,
+		   mode,
+		   ino,
+		   srv->dev,
+		   access_time_ts,
+		   change_time_ts,
+		   write_time_ts);
+
+	TALLOC_FREE(frame);
+	return true;
+
 all_failed:
 	srv->no_pathinfo2 = False;
 	srv->no_pathinfo3 = False;
diff --git a/source3/libsmb/libsmb_server.c b/source3/libsmb/libsmb_server.c
index 0067df48cac..d4f71d8c8b7 100644
--- a/source3/libsmb/libsmb_server.c
+++ b/source3/libsmb/libsmb_server.c
@@ -657,6 +657,15 @@ SMBC_server_internal(TALLOC_CTX *ctx,
 	ZERO_STRUCTP(srv);
 	DLIST_ADD(srv->cli, c);
 	srv->dev = (dev_t)(str_checksum(server) ^ str_checksum(share));
+	srv->try_posixinfo = false;
+	/*
+	 * Until SMB2 POSIX is done, only
+	 * try POSIX stat on SMB1 with POSIX capabilities.
+	 */
+	if ((smbXcli_conn_protocol(c->conn) < PROTOCOL_SMB2_02) &&
+	    (smb1cli_conn_capabilities(c->conn) & CAP_UNIX)) {
+		srv->try_posixinfo = true;
+	}
         srv->no_pathinfo = False;
         srv->no_pathinfo2 = False;
 	srv->no_pathinfo3 = False;
diff --git a/source3/libsmb/libsmb_stat.c b/source3/libsmb/libsmb_stat.c
index 0db9be3677b..f20f79579e2 100644
--- a/source3/libsmb/libsmb_stat.c
+++ b/source3/libsmb/libsmb_stat.c
@@ -107,6 +107,43 @@ void setup_stat(struct stat *st,
 	st->st_mtime = convert_timespec_to_time_t(write_time_ts);
 }
 
+void setup_stat_from_stat_ex(const struct stat_ex *stex,
+			     const char *fname,
+			     struct stat *st)
+{
+	st->st_atime = convert_timespec_to_time_t(stex->st_ex_atime);
+	st->st_ctime = convert_timespec_to_time_t(stex->st_ex_ctime);
+	st->st_mtime = convert_timespec_to_time_t(stex->st_ex_mtime);
+
+	st->st_mode = stex->st_ex_mode;
+	st->st_size = stex->st_ex_size;
+#ifdef HAVE_STAT_ST_BLKSIZE
+	st->st_blksize = 512;
+#endif
+#ifdef HAVE_STAT_ST_BLOCKS
+	st->st_blocks = (st->st_size + 511) / 512;
+#endif
+#ifdef HAVE_STRUCT_STAT_ST_RDEV
+	st->st_rdev = 0;
+#endif
+	st->st_uid = stex->st_ex_uid;
+	st->st_gid = stex->st_ex_gid;
+
+	st->st_nlink = stex->st_ex_nlink;
+
+	if (stex->st_ex_ino == 0) {
+		st->st_ino = 0;
+		if (fname != NULL) {
+			st->st_ino = generate_inode(fname);
+		}
+	} else {
+		st->st_ino = stex->st_ex_ino;
+	}
+
+	st->st_dev = stex->st_ex_dev;
+
+}
+
 /*
  * Routine to stat a file given a name
  */
@@ -123,13 +160,7 @@ SMBC_stat_ctx(SMBCCTX *context,
 	char *password = NULL;
 	char *workgroup = NULL;
 	char *path = NULL;
-	struct timespec write_time_ts;
-        struct timespec access_time_ts;
-        struct timespec change_time_ts;
-	off_t size = 0;
-	uint16_t mode = 0;
 	uint16_t port = 0;
-	SMB_INO_T ino = 0;
 	TALLOC_CTX *frame = talloc_stackframe();
 
 	if (!context || !context->internal->initialized) {
@@ -178,27 +209,12 @@ SMBC_stat_ctx(SMBCCTX *context,
 		return -1;  /* errno set by SMBC_server */
 	}
 
-	if (!SMBC_getatr(context, srv, path, &mode, &size,
-			 NULL,
-                         &access_time_ts,
-                         &write_time_ts,
-                         &change_time_ts,
-                         &ino)) {
+	if (!SMBC_getatr(context, srv, path, st)) {
 		errno = SMBC_errno(context, srv->cli);
 		TALLOC_FREE(frame);
 		return -1;
 	}
 
-	setup_stat(st,
-		fname,
-		size,
-		mode,
-		ino,
-		srv->dev,
-		access_time_ts,
-		change_time_ts,
-		write_time_ts);
-
 	TALLOC_FREE(frame);
 	return 0;
 }
@@ -296,7 +312,7 @@ SMBC_fstat_ctx(SMBCCTX *context,
 	}
 
 	setup_stat(st,
-		file->fname,
+		path,
 		size,
 		mode,
 		ino,
diff --git a/source3/libsmb/libsmb_xattr.c b/source3/libsmb/libsmb_xattr.c
index 442b45f2435..06a1d0c601d 100644
--- a/source3/libsmb/libsmb_xattr.c
+++ b/source3/libsmb/libsmb_xattr.c
@@ -552,13 +552,7 @@ dos_attr_query(SMBCCTX *context,
                const char *filename,
                SMBCSRV *srv)
 {
-        struct timespec create_time_ts;
-        struct timespec write_time_ts;
-        struct timespec access_time_ts;
-        struct timespec change_time_ts;
-        off_t size = 0;
-        uint16_t mode = 0;
-	SMB_INO_T inode = 0;
+	struct stat sb = {0};
         DOS_ATTR_DESC *ret;
 
         ret = talloc(ctx, DOS_ATTR_DESC);
@@ -568,26 +562,20 @@ dos_attr_query(SMBCCTX *context,
         }
 
         /* Obtain the DOS attributes */
-        if (!SMBC_getatr(context, srv, filename,
-                         &mode, &size,
-                         &create_time_ts,
-                         &access_time_ts,
-                         &write_time_ts,
-                         &change_time_ts,
-                         &inode)) {
+        if (!SMBC_getatr(context, srv, filename, &sb)) {
                 errno = SMBC_errno(context, srv->cli);
                 DEBUG(5, ("dos_attr_query Failed to query old attributes\n"));
 		TALLOC_FREE(ret);
                 return NULL;
         }
 
-        ret->mode = mode;
-        ret->size = size;
-        ret->create_time = convert_timespec_to_time_t(create_time_ts);
-        ret->access_time = convert_timespec_to_time_t(access_time_ts);
-        ret->write_time = convert_timespec_to_time_t(write_time_ts);
-        ret->change_time = convert_timespec_to_time_t(change_time_ts);
-        ret->inode = inode;
+        ret->mode = sb.st_mode;
+        ret->size = sb.st_size;
+        ret->create_time = sb.st_ctime;
+        ret->access_time = sb.st_atime;
+        ret->write_time = sb.st_mtime;
+        ret->change_time = sb.st_mtime;
+        ret->inode = sb.st_ino;
 
         return ret;
 }
@@ -736,17 +724,6 @@ cacl_get(SMBCCTX *context,
         char *name;
         char *pExclude;
         char *p;
-        struct timespec create_time_ts;
-	struct timespec write_time_ts;
-        struct timespec access_time_ts;
-        struct timespec change_time_ts;
-	time_t create_time = (time_t)0;
-	time_t write_time = (time_t)0;
-        time_t access_time = (time_t)0;
-        time_t change_time = (time_t)0;
-	off_t size = 0;
-	uint16_t mode = 0;
-	SMB_INO_T ino = 0;
 	struct cli_state *cli = srv->cli;
         struct {


-- 
Samba Shared Repository



More information about the samba-cvs mailing list