Пример #1
0
static int onefs_open(vfs_handle_struct *handle, const char *fname,
		      files_struct *fsp, int flags, mode_t mode)
{
	/* SMB_VFS_OPEN should never be called in vfs_onefs */
	SMB_ASSERT(false);
	return SMB_VFS_NEXT_OPEN(handle, fname, fsp, flags, mode);
}
Пример #2
0
static int greyhole_open(vfs_handle_struct *handle, const char *fname, files_struct *fsp, int flags, mode_t mode)
{
	int result;
	FILE *spoolf;
	char filename[38];
	struct timeval tp;

	result = SMB_VFS_NEXT_OPEN(handle, fname, fsp, flags, mode);

	if (result >= 0) {
		if ((flags & O_WRONLY) || (flags & O_RDWR)) {
			gettimeofday(&tp, (struct timezone *) NULL);
			snprintf(filename, 37, "/var/spool/greyhole/%.0f", ((double) (tp.tv_sec)*1000000.0) + (((double) tp.tv_usec)));
			spoolf = fopen(filename, "wt");
			fprintf(spoolf, "open\n%s\n%s\n%d\n%s\n",
				lp_servicename(handle->conn->params->service),
				fname,
				result,
				"for writing ");
			fclose(spoolf);
		}
	}

	return result;
}
Пример #3
0
static int cap_open(vfs_handle_struct *handle, connection_struct *conn, const char *fname, int flags, mode_t mode)
{
        pstring capname;
	DEBUG(3,("cap: cap_open for %s\n", fname));
	capencode(capname, fname);
	return SMB_VFS_NEXT_OPEN(handle, conn, capname, flags, mode);
}
Пример #4
0
static int vfsx_open(vfs_handle_struct *handle, const char *fname, files_struct *fsp, int flags, mode_t mode)
{
	int result = -1;
	int count;
	char buf[VFSX_MSG_OUT_SIZE];

	count = snprintf(buf, VFSX_MSG_OUT_SIZE, "open:%s:%s:%s,%d,%d", handle->conn->user, handle->conn->origpath, fname, flags, mode);
	if (vfsx_execute(buf, count) == VFSX_SUCCESS_TRANSPARENT) {
		result = SMB_VFS_NEXT_OPEN(handle, fname, fsp, flags, mode);
	}
	return result;
}
Пример #5
0
static int audit_open(vfs_handle_struct *handle, const char *fname, files_struct *fsp, int flags, mode_t mode)
{
	int result;

	result = SMB_VFS_NEXT_OPEN(handle, fname, fsp, flags, mode);

	syslog(audit_syslog_priority(handle), "open %s (fd %d) %s%s%s\n", 
	       fname, result,
	       ((flags & O_WRONLY) || (flags & O_RDWR)) ? "for writing " : "", 
	       (result < 0) ? "failed: " : "",
	       (result < 0) ? strerror(errno) : "");

	return result;
}
Пример #6
0
static int open_acl_xattr(vfs_handle_struct *handle,
					const char *fname,
					files_struct *fsp,
					int flags,
					mode_t mode)
{
	uint32_t access_granted = 0;
	struct security_descriptor *pdesc = NULL;
	bool file_existed = true;
	NTSTATUS status = get_nt_acl_xattr_internal(handle,
					NULL,
					fname,
					(OWNER_SECURITY_INFORMATION |
					 GROUP_SECURITY_INFORMATION |
					 DACL_SECURITY_INFORMATION),
					&pdesc);
        if (NT_STATUS_IS_OK(status)) {
		/* See if we can access it. */
		status = smb1_file_se_access_check(pdesc,
					handle->conn->server_info->ptok,
					fsp->access_mask,
					&access_granted);
		if (!NT_STATUS_IS_OK(status)) {
			DEBUG(10,("open_acl_xattr: file %s open "
				"refused with error %s\n",
				fname,
				nt_errstr(status) ));
			errno = map_errno_from_nt_status(status);
			return -1;
		}
        } else if (NT_STATUS_EQUAL(status,NT_STATUS_OBJECT_NAME_NOT_FOUND)) {
		file_existed = false;
	}

	DEBUG(10,("open_acl_xattr: get_nt_acl_attr_internal for "
		"file %s returned %s\n",
		fname,
		nt_errstr(status) ));

	fsp->fh->fd = SMB_VFS_NEXT_OPEN(handle, fname, fsp, flags, mode);

	if (!file_existed && fsp->fh->fd != -1) {
		/* File was created. Inherit from parent directory. */
		string_set(&fsp->fsp_name, fname);
		inherit_new_acl(handle, fname, fsp, false);
	}

	return fsp->fh->fd;
}
static int greyhole_open(vfs_handle_struct *handle, struct smb_filename *fname, files_struct *fsp, int flags, mode_t mode)
{
	int result;

	result = SMB_VFS_NEXT_OPEN(handle, fname, fsp, flags, mode);

	if (result >= 0) {
		if ((flags & O_WRONLY) || (flags & O_RDWR)) {
			gh_spoolf("open\n%s\n%s\n%d\n%s\n",
				lp_servicename(talloc_tos(), handle->conn->params->service),
				fname->base_name,
				result,
				"for writing ");
		}
	}

	return result;
}
Пример #8
0
static int audit_open(vfs_handle_struct *handle,
		      struct smb_filename *smb_fname, files_struct *fsp,
		      int flags, mode_t mode)
{
	int result;

	result = SMB_VFS_NEXT_OPEN(handle, smb_fname, fsp, flags, mode);

	if (lp_syslog() > 0) {
		syslog(audit_syslog_priority(handle), "open %s (fd %d) %s%s%s\n",
		       smb_fname->base_name, result,
		       ((flags & O_WRONLY) || (flags & O_RDWR)) ? "for writing " : "",
		       (result < 0) ? "failed: " : "",
		       (result < 0) ? strerror(errno) : "");
	}
	DEBUG(2, ("vfs_extd_audit: open %s %s %s\n",
	       smb_fname_str_dbg(smb_fname),
	       (result < 0) ? "failed: " : "",
	       (result < 0) ? strerror(errno) : ""));

	return result;
}
Пример #9
0
static int skel_open(vfs_handle_struct *handle, struct smb_filename *smb_fname,
		     files_struct *fsp, int flags, mode_t mode)
{
	return SMB_VFS_NEXT_OPEN(handle, smb_fname, fsp, flags, mode);
}
Пример #10
0
static int streams_xattr_open(vfs_handle_struct *handle,
			      struct smb_filename *smb_fname,
			      files_struct *fsp, int flags, mode_t mode)
{
	NTSTATUS status;
	struct streams_xattr_config *config = NULL;
	struct stream_io *sio = NULL;
	struct ea_struct ea;
	char *xattr_name = NULL;
	int pipe_fds[2];
	int fakefd = -1;
	int ret;

	SMB_VFS_HANDLE_GET_DATA(handle, config, struct streams_xattr_config,
				return -1);

	DEBUG(10, ("streams_xattr_open called for %s with flags 0x%x\n",
		   smb_fname_str_dbg(smb_fname), flags));

	if (!is_ntfs_stream_smb_fname(smb_fname)) {
		return SMB_VFS_NEXT_OPEN(handle, smb_fname, fsp, flags, mode);
	}

	/* If the default stream is requested, just open the base file. */
	if (is_ntfs_default_stream_smb_fname(smb_fname)) {
		char *tmp_stream_name;

		tmp_stream_name = smb_fname->stream_name;
		smb_fname->stream_name = NULL;

		ret = SMB_VFS_NEXT_OPEN(handle, smb_fname, fsp, flags, mode);

		smb_fname->stream_name = tmp_stream_name;

		return ret;
	}

	status = streams_xattr_get_name(handle, talloc_tos(),
					smb_fname->stream_name, &xattr_name);
	if (!NT_STATUS_IS_OK(status)) {
		errno = map_errno_from_nt_status(status);
		goto fail;
	}

	/*
	 * Return a valid fd, but ensure any attempt to use it returns an error
	 * (EPIPE).
	 */
	ret = pipe(pipe_fds);
	if (ret != 0) {
		goto fail;
	}

	close(pipe_fds[1]);
	pipe_fds[1] = -1;
	fakefd = pipe_fds[0];

	status = get_ea_value(talloc_tos(), handle->conn, NULL,
			      smb_fname, xattr_name, &ea);

	DEBUG(10, ("get_ea_value returned %s\n", nt_errstr(status)));

	if (!NT_STATUS_IS_OK(status)
	    && !NT_STATUS_EQUAL(status, NT_STATUS_NOT_FOUND)) {
		/*
		 * The base file is not there. This is an error even if we got
		 * O_CREAT, the higher levels should have created the base
		 * file for us.
		 */
		DEBUG(10, ("streams_xattr_open: base file %s not around, "
			   "returning ENOENT\n", smb_fname->base_name));
		errno = ENOENT;
		goto fail;
	}

	if ((!NT_STATUS_IS_OK(status) && (flags & O_CREAT)) ||
	    (flags & O_TRUNC)) {
		/*
		 * The attribute does not exist or needs to be truncated
		 */

		/*
		 * Darn, xattrs need at least 1 byte
		 */
		char null = '\0';

		DEBUG(10, ("creating or truncating attribute %s on file %s\n",
			   xattr_name, smb_fname->base_name));

		ret = SMB_VFS_SETXATTR(fsp->conn,
				       smb_fname,
				       xattr_name,
				       &null, sizeof(null),
				       flags & O_EXCL ? XATTR_CREATE : 0);
		if (ret != 0) {
			goto fail;
		}
	}

        sio = VFS_ADD_FSP_EXTENSION(handle, fsp, struct stream_io, NULL);
        if (sio == NULL) {
                errno = ENOMEM;
                goto fail;
        }

        sio->xattr_name = talloc_strdup(VFS_MEMCTX_FSP_EXTENSION(handle, fsp),
					xattr_name);
	/*
	 * so->base needs to be a copy of fsp->fsp_name->base_name,
	 * making it identical to streams_xattr_recheck(). If the
	 * open is changing directories, fsp->fsp_name->base_name
	 * will be the full path from the share root, whilst
	 * smb_fname will be relative to the $cwd.
	 */
        sio->base = talloc_strdup(VFS_MEMCTX_FSP_EXTENSION(handle, fsp),
				  fsp->fsp_name->base_name);
	sio->fsp_name_ptr = fsp->fsp_name;
	sio->handle = handle;
	sio->fsp = fsp;

	if ((sio->xattr_name == NULL) || (sio->base == NULL)) {
		errno = ENOMEM;
		goto fail;
	}

	return fakefd;

 fail:
	if (fakefd >= 0) {
		close(fakefd);
		fakefd = -1;
	}

	return -1;
}
Пример #11
0
static int prealloc_open(vfs_handle_struct* handle,
			const char *	    fname,
			files_struct *	    fsp,
			int		    flags,
			mode_t		    mode)
{
	int fd;
	SMB_OFF_T size = 0;

	const char * dot;
	char fext[10];

	if (!(flags & (O_CREAT|O_TRUNC))) {
		/* Caller is not intending to rewrite the file. Let's not mess
		 * with the allocation in this case.
		 */
		goto normal_open;
	}

	*fext = '\0';
	dot = strrchr(fname, '.');
	if (dot && *++dot) {
		if (strlen(dot) < sizeof(fext)) {
			strncpy(fext, dot, sizeof(fext));
			strnorm(fext, CASE_LOWER);
		}
	}

	if (*fext == '\0') {
		goto normal_open;
	}

	/* Syntax for specifying preallocation size is:
	 *	MODULE: <extension> = <size>
	 * where
	 *	<extension> is the file extension in lower case
	 *	<size> is a size like 10, 10K, 10M
	 */
	size = conv_str_size(lp_parm_const_string(SNUM(handle->conn), MODULE,
						    fext, NULL));
	if (size <= 0) {
		/* No need to preallocate this file. */
		goto normal_open;
	}

	fd = SMB_VFS_NEXT_OPEN(handle, fname, fsp, flags, mode);
	if (fd < 0) {
		return fd;
	}

	/* Prellocate only if the file is being created or replaced. Note that
	 * Samba won't ever pass down O_TRUNC, which is why we have to handle
	 * truncate calls specially.
	 */
	if ((flags & O_CREAT) || (flags & O_TRUNC)) {
		SMB_OFF_T * psize;

		psize = VFS_ADD_FSP_EXTENSION(handle, fsp, SMB_OFF_T);
		if (psize == NULL || *psize == -1) {
			return fd;
		}

		DEBUG(module_debug,
			("%s: preallocating %s (fd=%d) to %lld bytes\n",
			MODULE, fname, fd, (long long)size));

		*psize = size;
		if (preallocate_space(fd, 0, *psize) < 0) {
			VFS_REMOVE_FSP_EXTENSION(handle, fsp);
		}
	}

	return fd;

normal_open:
	/* We are not creating or replacing a file. Skip the
	 * preallocation.
	 */
	DEBUG(module_debug, ("%s: skipping preallocation for %s\n",
		    MODULE, fname));
	return SMB_VFS_NEXT_OPEN(handle, fname, fsp, flags, mode);
}
Пример #12
0
static int skel_open(vfs_handle_struct *handle,  const char *fname, files_struct *fsp, int flags, mode_t mode)
{
	return SMB_VFS_NEXT_OPEN(handle, fname, fsp, flags, mode);
}
Пример #13
0
static int skel_open(vfs_handle_struct *handle, connection_struct *conn, const char *fname, int flags, mode_t mode)
{
	return SMB_VFS_NEXT_OPEN(handle, conn, fname, flags, mode);
}
Пример #14
0
static int open_acl_common(vfs_handle_struct *handle,
			struct smb_filename *smb_fname,
			files_struct *fsp,
			int flags,
			mode_t mode)
{
	uint32_t access_granted = 0;
	struct security_descriptor *pdesc = NULL;
	struct security_descriptor *parent_desc = NULL;
	bool file_existed = true;
	char *fname = NULL;
	NTSTATUS status;

	if (fsp->base_fsp) {
		/* Stream open. Base filename open already did the ACL check. */
		DEBUG(10,("open_acl_common: stream open on %s\n",
			fsp_str_dbg(fsp) ));
		return SMB_VFS_NEXT_OPEN(handle, smb_fname, fsp, flags, mode);
	}

	status = get_full_smb_filename(talloc_tos(), smb_fname,
				       &fname);
	if (!NT_STATUS_IS_OK(status)) {
		goto err;
	}

	status = get_nt_acl_internal(handle,
				NULL,
				fname,
				(OWNER_SECURITY_INFORMATION |
				 GROUP_SECURITY_INFORMATION |
				 DACL_SECURITY_INFORMATION),
				&pdesc);
        if (NT_STATUS_IS_OK(status)) {
		/* See if we can access it. */
		status = smb1_file_se_access_check(handle->conn,
					pdesc,
					handle->conn->server_info->ptok,
					fsp->access_mask,
					&access_granted);
		if (!NT_STATUS_IS_OK(status)) {
			DEBUG(10,("open_acl_xattr: %s open "
				"refused with error %s\n",
				fsp_str_dbg(fsp),
				nt_errstr(status) ));
			goto err;
		}
        } else if (NT_STATUS_EQUAL(status,NT_STATUS_OBJECT_NAME_NOT_FOUND)) {
		file_existed = false;
		/*
		 * If O_CREAT is true then we're trying to create a file.
		 * Check the parent directory ACL will allow this.
		 */
		if (flags & O_CREAT) {
			struct security_descriptor *psd = NULL;

			status = check_parent_acl_common(handle, fname,
					SEC_DIR_ADD_FILE, &parent_desc);
			if (!NT_STATUS_IS_OK(status)) {
				goto err;
			}
			/* Cache the parent security descriptor for
			 * later use. We do have an fsp here, but to
			 * keep the code consistent with the directory
			 * case which doesn't, use the handle. */

			/* Attach this to the conn, move from talloc_tos(). */
			psd = (struct security_descriptor *)talloc_move(handle->conn,
				&parent_desc);

			if (!psd) {
				status = NT_STATUS_NO_MEMORY;
				goto err;
			}
			status = NT_STATUS_NO_MEMORY;
			SMB_VFS_HANDLE_SET_DATA(handle, psd, free_sd_common,
				struct security_descriptor *, goto err);
			status = NT_STATUS_OK;
		}
	}

	DEBUG(10,("open_acl_xattr: get_nt_acl_attr_internal for "
		"%s returned %s\n",
		fsp_str_dbg(fsp),
		nt_errstr(status) ));

	fsp->fh->fd = SMB_VFS_NEXT_OPEN(handle, smb_fname, fsp, flags, mode);
	return fsp->fh->fd;

  err:

	errno = map_errno_from_nt_status(status);
	return -1;
}