⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 vfs_simple.c

📁 samba最新软件
💻 C
📖 第 1 页 / 共 2 页
字号:
		return NT_STATUS_INVALID_HANDLE;	}	ret = pwrite(f->fd, 		     wr->writex.in.data, 		     wr->writex.in.count,		     wr->writex.in.offset);	if (ret == -1) {		return map_nt_error_from_unix(errno);	}			wr->writex.out.nwritten = ret;	wr->writex.out.remaining = 0; /* should fill this in? */		return NT_STATUS_OK;}/*  seek in a file*/static NTSTATUS svfs_seek(struct ntvfs_module_context *ntvfs,			  struct ntvfs_request *req,			  union smb_seek *io){	return NT_STATUS_NOT_SUPPORTED;}/*  flush a file*/static NTSTATUS svfs_flush(struct ntvfs_module_context *ntvfs,			   struct ntvfs_request *req,			   union smb_flush *io){	struct svfs_private *private = ntvfs->private_data;	struct svfs_file *f;	switch (io->generic.level) {	case RAW_FLUSH_FLUSH:	case RAW_FLUSH_SMB2:		/* ignore the additional unknown option in SMB2 */		f = find_fd(private, io->generic.in.file.ntvfs);		if (!f) {			return NT_STATUS_INVALID_HANDLE;		}		fsync(f->fd);		return NT_STATUS_OK;	case RAW_FLUSH_ALL:		for (f=private->open_files;f;f=f->next) {			fsync(f->fd);		}		return NT_STATUS_OK;	}	return NT_STATUS_INVALID_LEVEL;}/*  close a file*/static NTSTATUS svfs_close(struct ntvfs_module_context *ntvfs,			   struct ntvfs_request *req,			   union smb_close *io){	struct svfs_private *private = ntvfs->private_data;	struct svfs_file *f;	if (io->generic.level != RAW_CLOSE_CLOSE) {		/* we need a mapping function */		return NT_STATUS_INVALID_LEVEL;	}	f = find_fd(private, io->close.in.file.ntvfs);	if (!f) {		return NT_STATUS_INVALID_HANDLE;	}	if (close(f->fd) == -1) {		return map_nt_error_from_unix(errno);	}	DLIST_REMOVE(private->open_files, f);	talloc_free(f->name);	talloc_free(f);	return NT_STATUS_OK;}/*  exit - closing files*/static NTSTATUS svfs_exit(struct ntvfs_module_context *ntvfs,			  struct ntvfs_request *req){	return NT_STATUS_NOT_SUPPORTED;}/*  logoff - closing files*/static NTSTATUS svfs_logoff(struct ntvfs_module_context *ntvfs,			    struct ntvfs_request *req){	return NT_STATUS_NOT_SUPPORTED;}/*  setup for an async call*/static NTSTATUS svfs_async_setup(struct ntvfs_module_context *ntvfs,				 struct ntvfs_request *req, 				 void *private){	return NT_STATUS_OK;}/*  cancel an async call*/static NTSTATUS svfs_cancel(struct ntvfs_module_context *ntvfs, struct ntvfs_request *req){	return NT_STATUS_UNSUCCESSFUL;}/*  lock a byte range*/static NTSTATUS svfs_lock(struct ntvfs_module_context *ntvfs,			  struct ntvfs_request *req, union smb_lock *lck){	DEBUG(0,("REWRITE: not doing byte range locking!\n"));	return NT_STATUS_OK;}/*  set info on a pathname*/static NTSTATUS svfs_setpathinfo(struct ntvfs_module_context *ntvfs,				 struct ntvfs_request *req, union smb_setfileinfo *st){	CHECK_READ_ONLY(req);	return NT_STATUS_NOT_SUPPORTED;}/*  set info on a open file*/static NTSTATUS svfs_setfileinfo(struct ntvfs_module_context *ntvfs,				 struct ntvfs_request *req, 				 union smb_setfileinfo *info){	struct svfs_private *private = ntvfs->private_data;	struct svfs_file *f;	struct utimbuf unix_times;	CHECK_READ_ONLY(req);	f = find_fd(private, info->generic.in.file.ntvfs);	if (!f) {		return NT_STATUS_INVALID_HANDLE;	}		switch (info->generic.level) {	case RAW_SFILEINFO_END_OF_FILE_INFO:	case RAW_SFILEINFO_END_OF_FILE_INFORMATION:		if (ftruncate(f->fd, 			      info->end_of_file_info.in.size) == -1) {			return map_nt_error_from_unix(errno);		}		break;	case RAW_SFILEINFO_SETATTRE:		unix_times.actime = info->setattre.in.access_time;		unix_times.modtime = info->setattre.in.write_time;		if (unix_times.actime == 0 && unix_times.modtime == 0) {			break;		} 		/* set modify time = to access time if modify time was 0 */		if (unix_times.actime != 0 && unix_times.modtime == 0) {			unix_times.modtime = unix_times.actime;		}		/* Set the date on this file */		if (svfs_file_utime(f->fd, &unix_times) != 0) {			return NT_STATUS_ACCESS_DENIED;		}  		break;	default:		DEBUG(2,("svfs_setfileinfo: level %d not implemented\n", 			 info->generic.level));		return NT_STATUS_NOT_IMPLEMENTED;	}	return NT_STATUS_OK;}/*  return filesystem space info*/static NTSTATUS svfs_fsinfo(struct ntvfs_module_context *ntvfs,			    struct ntvfs_request *req, union smb_fsinfo *fs){	struct svfs_private *private = ntvfs->private_data;	struct stat st;	if (fs->generic.level != RAW_QFS_GENERIC) {		return ntvfs_map_fsinfo(ntvfs, req, fs);	}	if (sys_fsusage(private->connectpath, 			&fs->generic.out.blocks_free, 			&fs->generic.out.blocks_total) == -1) {		return map_nt_error_from_unix(errno);	}	fs->generic.out.block_size = 512;	if (stat(private->connectpath, &st) != 0) {		return NT_STATUS_DISK_CORRUPT_ERROR;	}		fs->generic.out.fs_id = st.st_ino;	unix_to_nt_time(&fs->generic.out.create_time, st.st_ctime);	fs->generic.out.serial_number = st.st_ino;	fs->generic.out.fs_attr = 0;	fs->generic.out.max_file_component_length = 255;	fs->generic.out.device_type = 0;	fs->generic.out.device_characteristics = 0;	fs->generic.out.quota_soft = 0;	fs->generic.out.quota_hard = 0;	fs->generic.out.quota_flags = 0;	fs->generic.out.volume_name = talloc_strdup(req, ntvfs->ctx->config->name);	fs->generic.out.fs_type = ntvfs->ctx->fs_type;	return NT_STATUS_OK;}#if 0/*  return filesystem attribute info*/static NTSTATUS svfs_fsattr(struct ntvfs_module_context *ntvfs,			    struct ntvfs_request *req, union smb_fsattr *fs){	struct stat st;	struct svfs_private *private = ntvfs->private_data;	if (fs->generic.level != RAW_FSATTR_GENERIC) {		return ntvfs_map_fsattr(ntvfs, req, fs);	}	if (stat(private->connectpath, &st) == -1) {		return map_nt_error_from_unix(errno);	}	unix_to_nt_time(&fs->generic.out.create_time, st.st_ctime);	fs->generic.out.fs_attr = 		FILE_CASE_PRESERVED_NAMES | 		FILE_CASE_SENSITIVE_SEARCH | 		FILE_PERSISTENT_ACLS;	fs->generic.out.max_file_component_length = 255;	fs->generic.out.serial_number = 1;	fs->generic.out.fs_type = talloc_strdup(req, "NTFS");	fs->generic.out.volume_name = talloc_strdup(req, 						    lp_servicename(req->tcon->service));	return NT_STATUS_OK;}#endif/*  return print queue info*/static NTSTATUS svfs_lpq(struct ntvfs_module_context *ntvfs,			 struct ntvfs_request *req, union smb_lpq *lpq){	return NT_STATUS_NOT_SUPPORTED;}/*    list files in a directory matching a wildcard pattern*/static NTSTATUS svfs_search_first(struct ntvfs_module_context *ntvfs,				  struct ntvfs_request *req, union smb_search_first *io, 				  void *search_private, 				  bool (*callback)(void *, const union smb_search_data *)){	struct svfs_dir *dir;	int i;	struct svfs_private *private = ntvfs->private_data;	struct search_state *search;	union smb_search_data file;	uint_t max_count;	if (io->generic.level != RAW_SEARCH_TRANS2) {		return NT_STATUS_NOT_SUPPORTED;	}	if (io->generic.data_level != RAW_SEARCH_DATA_BOTH_DIRECTORY_INFO) {		return NT_STATUS_NOT_SUPPORTED;	}	search = talloc_zero(private, struct search_state);	if (!search) {		return NT_STATUS_NO_MEMORY;	}	max_count = io->t2ffirst.in.max_count;	dir = svfs_list(ntvfs, req, io->t2ffirst.in.pattern);	if (!dir) {		return NT_STATUS_FOOBAR;	}	search->handle = private->next_search_handle;	search->dir = dir;	if (dir->count < max_count) {		max_count = dir->count;	}	for (i=0; i < max_count;i++) {		ZERO_STRUCT(file);		unix_to_nt_time(&file.both_directory_info.create_time, dir->files[i].st.st_ctime);		unix_to_nt_time(&file.both_directory_info.access_time, dir->files[i].st.st_atime);		unix_to_nt_time(&file.both_directory_info.write_time,  dir->files[i].st.st_mtime);		unix_to_nt_time(&file.both_directory_info.change_time, dir->files[i].st.st_mtime);		file.both_directory_info.name.s = dir->files[i].name;		file.both_directory_info.short_name.s = dir->files[i].name;		file.both_directory_info.size = dir->files[i].st.st_size;		file.both_directory_info.attrib = svfs_unix_to_dos_attrib(dir->files[i].st.st_mode);		if (!callback(search_private, &file)) {			break;		}	}	search->current_index = i;	io->t2ffirst.out.count = i;	io->t2ffirst.out.handle = search->handle;	io->t2ffirst.out.end_of_search = (i == dir->count) ? 1 : 0;	/* work out if we are going to keep the search state */	if ((io->t2ffirst.in.flags & FLAG_TRANS2_FIND_CLOSE) ||	    ((io->t2ffirst.in.flags & FLAG_TRANS2_FIND_CLOSE_IF_END) && (i == dir->count))) {		talloc_free(search);	} else {		private->next_search_handle++;		DLIST_ADD(private->search, search);	}	return NT_STATUS_OK;}/* continue a search */static NTSTATUS svfs_search_next(struct ntvfs_module_context *ntvfs,				 struct ntvfs_request *req, union smb_search_next *io, 				 void *search_private, 				 bool (*callback)(void *, const union smb_search_data *)){	struct svfs_dir *dir;	int i;	struct svfs_private *private = ntvfs->private_data;	struct search_state *search;	union smb_search_data file;	uint_t max_count;	if (io->generic.level != RAW_SEARCH_TRANS2) {		return NT_STATUS_NOT_SUPPORTED;	}	if (io->generic.data_level != RAW_SEARCH_DATA_BOTH_DIRECTORY_INFO) {		return NT_STATUS_NOT_SUPPORTED;	}	for (search=private->search; search; search = search->next) {		if (search->handle == io->t2fnext.in.handle) break;	}		if (!search) {		/* we didn't find the search handle */		return NT_STATUS_FOOBAR;	}	dir = search->dir;	/* the client might be asking for something other than just continuing	   with the search */	if (!(io->t2fnext.in.flags & FLAG_TRANS2_FIND_CONTINUE) &&	    (io->t2fnext.in.flags & FLAG_TRANS2_FIND_REQUIRE_RESUME) &&	    io->t2fnext.in.last_name && *io->t2fnext.in.last_name) {		/* look backwards first */		for (i=search->current_index; i > 0; i--) {			if (strcmp(io->t2fnext.in.last_name, dir->files[i-1].name) == 0) {				search->current_index = i;				goto found;			}		}		/* then look forwards */		for (i=search->current_index+1; i <= dir->count; i++) {			if (strcmp(io->t2fnext.in.last_name, dir->files[i-1].name) == 0) {				search->current_index = i;				goto found;			}		}	}found:		max_count = search->current_index + io->t2fnext.in.max_count;	if (max_count > dir->count) {		max_count = dir->count;	}	for (i = search->current_index; i < max_count;i++) {		ZERO_STRUCT(file);		unix_to_nt_time(&file.both_directory_info.create_time, dir->files[i].st.st_ctime);		unix_to_nt_time(&file.both_directory_info.access_time, dir->files[i].st.st_atime);		unix_to_nt_time(&file.both_directory_info.write_time,  dir->files[i].st.st_mtime);		unix_to_nt_time(&file.both_directory_info.change_time, dir->files[i].st.st_mtime);		file.both_directory_info.name.s = dir->files[i].name;		file.both_directory_info.short_name.s = dir->files[i].name;		file.both_directory_info.size = dir->files[i].st.st_size;		file.both_directory_info.attrib = svfs_unix_to_dos_attrib(dir->files[i].st.st_mode);		if (!callback(search_private, &file)) {			break;		}	}	io->t2fnext.out.count = i - search->current_index;	io->t2fnext.out.end_of_search = (i == dir->count) ? 1 : 0;	search->current_index = i;	/* work out if we are going to keep the search state */	if ((io->t2fnext.in.flags & FLAG_TRANS2_FIND_CLOSE) ||	    ((io->t2fnext.in.flags & FLAG_TRANS2_FIND_CLOSE_IF_END) && (i == dir->count))) {		DLIST_REMOVE(private->search, search);		talloc_free(search);	}	return NT_STATUS_OK;}/* close a search */static NTSTATUS svfs_search_close(struct ntvfs_module_context *ntvfs,				  struct ntvfs_request *req, union smb_search_close *io){	struct svfs_private *private = ntvfs->private_data;	struct search_state *search;	for (search=private->search; search; search = search->next) {		if (search->handle == io->findclose.in.handle) break;	}		if (!search) {		/* we didn't find the search handle */		return NT_STATUS_FOOBAR;	}	DLIST_REMOVE(private->search, search);	talloc_free(search);	return NT_STATUS_OK;}/* SMBtrans - not used on file shares */static NTSTATUS svfs_trans(struct ntvfs_module_context *ntvfs,			   struct ntvfs_request *req, struct smb_trans2 *trans2){	return NT_STATUS_ACCESS_DENIED;}/*  initialialise the POSIX disk backend, registering ourselves with the ntvfs subsystem */NTSTATUS ntvfs_simple_init(void){	NTSTATUS ret;	struct ntvfs_ops ops;	NTVFS_CURRENT_CRITICAL_SIZES(vers);	ZERO_STRUCT(ops);	/* fill in all the operations */	ops.connect = svfs_connect;	ops.disconnect = svfs_disconnect;	ops.unlink = svfs_unlink;	ops.chkpath = svfs_chkpath;	ops.qpathinfo = svfs_qpathinfo;	ops.setpathinfo = svfs_setpathinfo;	ops.open = svfs_open;	ops.mkdir = svfs_mkdir;	ops.rmdir = svfs_rmdir;	ops.rename = svfs_rename;	ops.copy = svfs_copy;	ops.ioctl = svfs_ioctl;	ops.read = svfs_read;	ops.write = svfs_write;	ops.seek = svfs_seek;	ops.flush = svfs_flush;		ops.close = svfs_close;	ops.exit = svfs_exit;	ops.lock = svfs_lock;	ops.setfileinfo = svfs_setfileinfo;	ops.qfileinfo = svfs_qfileinfo;	ops.fsinfo = svfs_fsinfo;	ops.lpq = svfs_lpq;	ops.search_first = svfs_search_first;	ops.search_next = svfs_search_next;	ops.search_close = svfs_search_close;	ops.trans = svfs_trans;	ops.logoff = svfs_logoff;	ops.async_setup = svfs_async_setup;	ops.cancel = svfs_cancel;	/* register ourselves with the NTVFS subsystem. We register	   under names 'simple'	*/	ops.type = NTVFS_DISK;	ops.name = "simple";	ret = ntvfs_register(&ops, &vers);	if (!NT_STATUS_IS_OK(ret)) {		DEBUG(0,("Failed to register simple backend with name: %s!\n",			 ops.name));	}	return ret;}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -