mirror of
https://github.com/samba-team/samba.git
synced 2025-01-11 05:18:09 +03:00
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@samba.org> Reviewed-by: Jeremy Allison <jra@samba.org>
This commit is contained in:
parent
bf9a3a7aa1
commit
0fe9dc5219
@ -408,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,
|
||||
|
@ -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;
|
||||
@ -2224,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);
|
||||
@ -2247,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 */
|
||||
|
@ -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,36 @@ 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->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,28 +543,29 @@ 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;
|
||||
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;
|
||||
}
|
||||
return true;
|
||||
|
||||
all_failed:
|
||||
srv->no_pathinfo2 = False;
|
||||
|
@ -123,13 +123,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 +172,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,
|
||||
path,
|
||||
size,
|
||||
mode,
|
||||
ino,
|
||||
srv->dev,
|
||||
access_time_ts,
|
||||
change_time_ts,
|
||||
write_time_ts);
|
||||
|
||||
TALLOC_FREE(frame);
|
||||
return 0;
|
||||
}
|
||||
|
@ -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 {
|
||||
const char * create_time_attr;
|
||||
@ -1155,25 +1132,31 @@ cacl_get(SMBCCTX *context,
|
||||
}
|
||||
|
||||
if (all || some_dos) {
|
||||
struct stat sb = {0};
|
||||
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;
|
||||
|
||||
/* Point to the portion after "system.dos_attr." */
|
||||
name += 16; /* if (all) this will be invalid but unused */
|
||||
|
||||
/* Obtain the DOS attributes */
|
||||
if (!SMBC_getatr(context, srv, filename, &mode, &size,
|
||||
&create_time_ts,
|
||||
&access_time_ts,
|
||||
&write_time_ts,
|
||||
&change_time_ts,
|
||||
&ino)) {
|
||||
|
||||
if (!SMBC_getatr(context, srv, filename, &sb)) {
|
||||
errno = SMBC_errno(context, srv->cli);
|
||||
return -1;
|
||||
}
|
||||
|
||||
create_time = convert_timespec_to_time_t(create_time_ts);
|
||||
access_time = convert_timespec_to_time_t(access_time_ts);
|
||||
write_time = convert_timespec_to_time_t(write_time_ts);
|
||||
change_time = convert_timespec_to_time_t(change_time_ts);
|
||||
create_time = sb.st_ctime;
|
||||
access_time = sb.st_atime;
|
||||
write_time = sb.st_mtime;
|
||||
change_time = sb.st_mtime;
|
||||
size = sb.st_size;
|
||||
mode = sb.st_mode;
|
||||
ino = sb.st_ino;
|
||||
|
||||
if (! exclude_dos_mode) {
|
||||
if (all || all_dos) {
|
||||
|
Loading…
Reference in New Issue
Block a user