summaryrefslogtreecommitdiff
path: root/source4/ntvfs
diff options
context:
space:
mode:
Diffstat (limited to 'source4/ntvfs')
-rw-r--r--source4/ntvfs/cifs/vfs_cifs.c20
-rw-r--r--source4/ntvfs/config.mk8
-rw-r--r--source4/ntvfs/ipc/vfs_ipc.c4
-rw-r--r--source4/ntvfs/ntvfs.h8
-rw-r--r--source4/ntvfs/ntvfs_generic.c12
-rw-r--r--source4/ntvfs/posix/config.mk2
-rw-r--r--source4/ntvfs/posix/pvfs_setfileinfo.c44
7 files changed, 64 insertions, 34 deletions
diff --git a/source4/ntvfs/cifs/vfs_cifs.c b/source4/ntvfs/cifs/vfs_cifs.c
index 910401f157..901dd2cf7c 100644
--- a/source4/ntvfs/cifs/vfs_cifs.c
+++ b/source4/ntvfs/cifs/vfs_cifs.c
@@ -64,12 +64,16 @@ struct async_info {
#define SETUP_PID private->tree->session->pid = req->smbpid
-#define SETUP_FILE do { \
- struct cvfs_file *f; \
+#define SETUP_FILE_HERE(f) do { \
f = ntvfs_handle_get_backend_data(io->generic.in.file.ntvfs, ntvfs); \
if (!f) return NT_STATUS_INVALID_HANDLE; \
io->generic.in.file.fnum = f->fnum; \
-} while (0)
+} while (0)
+
+#define SETUP_FILE do { \
+ struct cvfs_file *f; \
+ SETUP_FILE_HERE(f); \
+} while (0)
#define SETUP_PID_AND_FILE do { \
SETUP_PID; \
@@ -484,6 +488,7 @@ static void async_open(struct smbcli_request *c_req)
req->async_states->status = ntvfs_handle_set_backend_data(f->h, cvfs->ntvfs, f);
if (!NT_STATUS_IS_OK(req->async_states->status)) goto failed;
file->ntvfs = f->h;
+ DLIST_ADD(cvfs->files, f);
failed:
req->async_states->send_fn(req);
}
@@ -526,6 +531,7 @@ static NTSTATUS cvfs_open(struct ntvfs_module_context *ntvfs,
status = ntvfs_handle_set_backend_data(f->h, private->ntvfs, f);
NT_STATUS_NOT_OK_RETURN(status);
file->ntvfs = f->h;
+ DLIST_ADD(private->files, f);
return NT_STATUS_OK;
}
@@ -752,6 +758,7 @@ static NTSTATUS cvfs_close(struct ntvfs_module_context *ntvfs,
{
struct cvfs_private *private = ntvfs->private_data;
struct smbcli_request *c_req;
+ struct cvfs_file *f;
SETUP_PID;
@@ -759,7 +766,12 @@ static NTSTATUS cvfs_close(struct ntvfs_module_context *ntvfs,
private->map_generic) {
return ntvfs_map_close(ntvfs, req, io);
}
- SETUP_FILE;
+ SETUP_FILE_HERE(f);
+ /* Note, we aren't free-ing f, or it's h here. Should we?
+ even if file-close fails, we'll remove it from the list,
+ what else would we do? Maybe we should not remove until
+ after the proxied call completes? */
+ DLIST_REMOVE(private->files, f);
if (!(req->async_states->state & NTVFS_ASYNC_STATE_MAY_ASYNC)) {
return smb_raw_close(private->tree, io);
diff --git a/source4/ntvfs/config.mk b/source4/ntvfs/config.mk
index 017614b7be..dbc1a4c277 100644
--- a/source4/ntvfs/config.mk
+++ b/source4/ntvfs/config.mk
@@ -1,8 +1,8 @@
# NTVFS Server subsystem
-include posix/config.mk
-include common/config.mk
-include unixuid/config.mk
-include sysdep/config.mk
+mkinclude posix/config.mk
+mkinclude common/config.mk
+mkinclude unixuid/config.mk
+mkinclude sysdep/config.mk
################################################
# Start MODULE ntvfs_cifs
diff --git a/source4/ntvfs/ipc/vfs_ipc.c b/source4/ntvfs/ipc/vfs_ipc.c
index 81cd984f0b..92f0eadae1 100644
--- a/source4/ntvfs/ipc/vfs_ipc.c
+++ b/source4/ntvfs/ipc/vfs_ipc.c
@@ -322,7 +322,7 @@ static NTSTATUS ipc_open_smb2(struct ntvfs_module_context *ntvfs,
NT_STATUS_NOT_OK_RETURN(status);
oi->smb2.out.file.ntvfs = p->handle;
- oi->smb2.out.oplock_flags = oi->smb2.in.oplock_flags;
+ oi->smb2.out.oplock_level = oi->smb2.in.oplock_level;
oi->smb2.out.create_action = NTCREATEX_ACTION_EXISTED;
oi->smb2.out.create_time = 0;
oi->smb2.out.access_time = 0;
@@ -331,7 +331,7 @@ static NTSTATUS ipc_open_smb2(struct ntvfs_module_context *ntvfs,
oi->smb2.out.alloc_size = 4096;
oi->smb2.out.size = 0;
oi->smb2.out.file_attr = FILE_ATTRIBUTE_NORMAL;
- oi->smb2.out._pad = 0;
+ oi->smb2.out.reserved2 = 0;
oi->smb2.out.blob = data_blob(NULL, 0);
return status;
diff --git a/source4/ntvfs/ntvfs.h b/source4/ntvfs/ntvfs.h
index fe5f956426..a708dbff51 100644
--- a/source4/ntvfs/ntvfs.h
+++ b/source4/ntvfs/ntvfs.h
@@ -32,9 +32,11 @@ struct ntvfs_module_context;
struct ntvfs_request;
/* each backend has to be one one of the following 3 basic types. In
- * earlier versions of Samba backends needed to handle all types, now
- * we implement them separately. */
-enum ntvfs_type {NTVFS_DISK, NTVFS_PRINT, NTVFS_IPC};
+ earlier versions of Samba backends needed to handle all types, now
+ we implement them separately.
+ The values 1..3 match the SMB2 SMB2_SHARE_TYPE_* values
+ */
+enum ntvfs_type {NTVFS_DISK=1, NTVFS_IPC=2, NTVFS_PRINT=3};
/* the ntvfs operations structure - contains function pointers to
the backend implementations of each operation */
diff --git a/source4/ntvfs/ntvfs_generic.c b/source4/ntvfs/ntvfs_generic.c
index 7708f4fc80..5092e732b4 100644
--- a/source4/ntvfs/ntvfs_generic.c
+++ b/source4/ntvfs/ntvfs_generic.c
@@ -208,7 +208,7 @@ static NTSTATUS ntvfs_map_open_finish(struct ntvfs_module_context *ntvfs,
case RAW_OPEN_SMB2:
io->smb2.out.file.ntvfs = io2->generic.out.file.ntvfs;
- io->smb2.out.oplock_flags = 0;
+ io->smb2.out.oplock_level = 0;
io->smb2.out.create_action = io2->generic.out.create_action;
io->smb2.out.create_time = io2->generic.out.create_time;
io->smb2.out.access_time = io2->generic.out.access_time;
@@ -217,7 +217,7 @@ static NTSTATUS ntvfs_map_open_finish(struct ntvfs_module_context *ntvfs,
io->smb2.out.alloc_size = io2->generic.out.alloc_size;
io->smb2.out.size = io2->generic.out.size;
io->smb2.out.file_attr = io2->generic.out.attrib;
- io->smb2.out._pad = 0;
+ io->smb2.out.reserved2 = 0;
io->smb2.out.blob = data_blob(NULL, 0);
break;
@@ -486,13 +486,13 @@ _PUBLIC_ NTSTATUS ntvfs_map_open(struct ntvfs_module_context *ntvfs,
case RAW_OPEN_SMB2:
io2->generic.in.flags = 0;
io2->generic.in.root_fid = 0;
- io2->generic.in.access_mask = io->smb2.in.access_mask;
+ io2->generic.in.access_mask = io->smb2.in.desired_access;
io2->generic.in.alloc_size = 0;
- io2->generic.in.file_attr = io->smb2.in.file_attr;
+ io2->generic.in.file_attr = io->smb2.in.file_attributes;
io2->generic.in.share_access = io->smb2.in.share_access;
- io2->generic.in.open_disposition= io->smb2.in.open_disposition;
+ io2->generic.in.open_disposition= io->smb2.in.create_disposition;
io2->generic.in.create_options = io->smb2.in.create_options;
- io2->generic.in.impersonation = io->smb2.in.impersonation;
+ io2->generic.in.impersonation = io->smb2.in.impersonation_level;
io2->generic.in.security_flags = 0;
io2->generic.in.fname = io->smb2.in.fname;
io2->generic.in.sec_desc = NULL;
diff --git a/source4/ntvfs/posix/config.mk b/source4/ntvfs/posix/config.mk
index 6588be11ae..6879940337 100644
--- a/source4/ntvfs/posix/config.mk
+++ b/source4/ntvfs/posix/config.mk
@@ -31,7 +31,7 @@ PRIVATE_DEPENDENCIES = LIBAIO_LINUX
# Start MODULE ntvfs_posix
[MODULE::ntvfs_posix]
SUBSYSTEM = ntvfs
-OUTPUT_TYPE = INTEGRATED
+OUTPUT_TYPE = MERGED_OBJ
INIT_FUNCTION = ntvfs_posix_init
PRIVATE_PROTO_HEADER = vfs_posix_proto.h
OBJ_FILES = \
diff --git a/source4/ntvfs/posix/pvfs_setfileinfo.c b/source4/ntvfs/posix/pvfs_setfileinfo.c
index 340913cd4d..9c78699edb 100644
--- a/source4/ntvfs/posix/pvfs_setfileinfo.c
+++ b/source4/ntvfs/posix/pvfs_setfileinfo.c
@@ -63,6 +63,11 @@ static uint32_t pvfs_setfileinfo_access(union smb_setfileinfo *info)
}
break;
+ case RAW_SFILEINFO_RENAME_INFORMATION:
+ case RAW_SFILEINFO_RENAME_INFORMATION_SMB2:
+ needed = SEC_STD_DELETE;
+ break;
+
default:
needed = SEC_FILE_WRITE_ATTRIBUTE;
break;
@@ -84,7 +89,8 @@ static NTSTATUS pvfs_setfileinfo_rename(struct pvfs_state *pvfs,
char *new_name, *p;
/* renames are only allowed within a directory */
- if (strchr_m(info->rename_information.in.new_name, '\\')) {
+ if (strchr_m(info->rename_information.in.new_name, '\\') &&
+ (req->ctx->protocol != PROTOCOL_SMB2)) {
return NT_STATUS_NOT_SUPPORTED;
}
@@ -98,24 +104,32 @@ static NTSTATUS pvfs_setfileinfo_rename(struct pvfs_state *pvfs,
return NT_STATUS_INVALID_PARAMETER;
}
- /* w2k3 does not appear to allow relative rename */
- if (info->rename_information.in.root_fid != 0) {
+ /* w2k3 does not appear to allow relative rename. On SMB2, vista sends it sometimes,
+ but I suspect it is just uninitialised memory */
+ if (info->rename_information.in.root_fid != 0 &&
+ (req->ctx->protocol != PROTOCOL_SMB2)) {
return NT_STATUS_INVALID_PARAMETER;
}
/* construct the fully qualified windows name for the new file name */
- new_name = talloc_strdup(req, name->original_name);
- if (new_name == NULL) {
- return NT_STATUS_NO_MEMORY;
- }
- p = strrchr_m(new_name, '\\');
- if (p == NULL) {
- return NT_STATUS_OBJECT_NAME_INVALID;
- }
- *p = 0;
+ if (req->ctx->protocol == PROTOCOL_SMB2) {
+ /* SMB2 sends the full path of the new name */
+ new_name = talloc_asprintf(req, "\\%s", info->rename_information.in.new_name);
+ } else {
+ new_name = talloc_strdup(req, name->original_name);
+ if (new_name == NULL) {
+ return NT_STATUS_NO_MEMORY;
+ }
+ p = strrchr_m(new_name, '\\');
+ if (p == NULL) {
+ return NT_STATUS_OBJECT_NAME_INVALID;
+ } else {
+ *p = 0;
+ }
- new_name = talloc_asprintf(req, "%s\\%s", new_name,
- info->rename_information.in.new_name);
+ new_name = talloc_asprintf(req, "%s\\%s", new_name,
+ info->rename_information.in.new_name);
+ }
if (new_name == NULL) {
return NT_STATUS_NO_MEMORY;
}
@@ -369,6 +383,7 @@ NTSTATUS pvfs_setfileinfo(struct ntvfs_module_context *ntvfs,
break;
case RAW_SFILEINFO_RENAME_INFORMATION:
+ case RAW_SFILEINFO_RENAME_INFORMATION_SMB2:
return pvfs_setfileinfo_rename(pvfs, req, h->name,
info);
@@ -566,6 +581,7 @@ NTSTATUS pvfs_setpathinfo(struct ntvfs_module_context *ntvfs,
return NT_STATUS_OK;
case RAW_SFILEINFO_RENAME_INFORMATION:
+ case RAW_SFILEINFO_RENAME_INFORMATION_SMB2:
return pvfs_setfileinfo_rename(pvfs, req, name,
info);