summaryrefslogtreecommitdiff
path: root/source4/ntvfs
diff options
context:
space:
mode:
authorAndrew Tridgell <tridge@samba.org>2004-09-21 08:46:47 +0000
committerGerald (Jerry) Carter <jerry@samba.org>2007-10-10 12:58:56 -0500
commit23ba434b017d61f397befe9808fa3214c3964355 (patch)
tree6b44688395804faba93febbcd0411c221481b98f /source4/ntvfs
parentd9e43bc8834d797a2f5a7d39342f4083a3bc8239 (diff)
downloadsamba-23ba434b017d61f397befe9808fa3214c3964355.tar.gz
samba-23ba434b017d61f397befe9808fa3214c3964355.tar.bz2
samba-23ba434b017d61f397befe9808fa3214c3964355.zip
r2469: complete overhaul of the old-style RAW_SEARCH_ calls (the OS/2 and
original core level calls). The old code was completely wrong in many respects. also fixed the EA_SIZE level in the server extended the RAW-SEARCH test suite to test the new code properly (This used to be commit 71480271ad84b57fcdde264a54bb2408cf783255)
Diffstat (limited to 'source4/ntvfs')
-rw-r--r--source4/ntvfs/posix/pvfs_search.c110
-rw-r--r--source4/ntvfs/posix/vfs_posix.h2
2 files changed, 91 insertions, 21 deletions
diff --git a/source4/ntvfs/posix/pvfs_search.c b/source4/ntvfs/posix/pvfs_search.c
index 548d7ad77e..3004e92d51 100644
--- a/source4/ntvfs/posix/pvfs_search.c
+++ b/source4/ntvfs/posix/pvfs_search.c
@@ -102,31 +102,14 @@ NTSTATUS pvfs_search_first(struct smbsrv_request *req, union smb_search_first *i
NTSTATUS status;
struct pvfs_filename *name;
- switch (io->generic.level) {
- case RAW_SEARCH_SEARCH:
+ if (io->generic.level == RAW_SEARCH_SEARCH) {
max_count = io->search_first.in.max_count;
search_attrib = io->search_first.in.search_attrib;
pattern = io->search_first.in.pattern;
- break;
-
- case RAW_SEARCH_STANDARD:
- case RAW_SEARCH_EA_SIZE:
- case RAW_SEARCH_DIRECTORY_INFO:
- case RAW_SEARCH_FULL_DIRECTORY_INFO:
- case RAW_SEARCH_NAME_INFO:
- case RAW_SEARCH_BOTH_DIRECTORY_INFO:
- case RAW_SEARCH_ID_FULL_DIRECTORY_INFO:
- case RAW_SEARCH_ID_BOTH_DIRECTORY_INFO:
- case RAW_SEARCH_UNIX_INFO:
+ } else {
max_count = io->t2ffirst.in.max_count;
search_attrib = io->t2ffirst.in.search_attrib;
pattern = io->t2ffirst.in.pattern;
- break;
-
- case RAW_SEARCH_FCLOSE:
- case RAW_SEARCH_GENERIC:
- DEBUG(0,("WARNING: Invalid search class %d in pvfs_search_first\n", io->generic.level));
- return NT_STATUS_INVALID_INFO_CLASS;
}
/* resolve the cifs name to a posix name */
@@ -232,7 +215,94 @@ NTSTATUS pvfs_search_next(struct smbsrv_request *req, union smb_search_next *io,
void *search_private,
BOOL (*callback)(void *, union smb_search_data *))
{
- return NT_STATUS_NOT_IMPLEMENTED;
+#if 0
+ struct pvfs_state *pvfs = req->tcon->ntvfs_private;
+ struct search_state *search;
+ union smb_search_data file;
+ uint_t max_count;
+ uint16_t handle;
+ int i;
+
+ if (io->generic.level == RAW_SEARCH_SEARCH) {
+ max_count = io->search_next.in.max_count;
+ search_attrib = io->search_next.in.search_attrib;
+ } else {
+ handle = io->t2fnext.in.handle;
+ }
+
+ if (io->generic.level != RAW_SEARCH_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 = pvfs_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);
+ }
+#endif
+ return NT_STATUS_OK;
}
/* close a search */
diff --git a/source4/ntvfs/posix/vfs_posix.h b/source4/ntvfs/posix/vfs_posix.h
index 12955ced5c..8b7ddfad88 100644
--- a/source4/ntvfs/posix/vfs_posix.h
+++ b/source4/ntvfs/posix/vfs_posix.h
@@ -92,9 +92,9 @@ struct pvfs_dir {
/* the state of a search started with pvfs_search_first() */
struct pvfs_search_state {
struct pvfs_search_state *next, *prev;
- uint16_t search_attrib;
uint16_t handle;
uint_t current_index;
+ uint16_t search_attrib;
struct pvfs_dir *dir;
};