diff options
Diffstat (limited to 'source3/smbwrapper')
-rw-r--r-- | source3/smbwrapper/lseek.c | 35 | ||||
-rw-r--r-- | source3/smbwrapper/realcalls.h | 1 | ||||
-rw-r--r-- | source3/smbwrapper/smbw.c | 49 |
3 files changed, 82 insertions, 3 deletions
diff --git a/source3/smbwrapper/lseek.c b/source3/smbwrapper/lseek.c new file mode 100644 index 0000000000..3507dab690 --- /dev/null +++ b/source3/smbwrapper/lseek.c @@ -0,0 +1,35 @@ +/* + Unix SMB/Netbios implementation. + Version 2.0 + SMB wrapper functions + Copyright (C) Andrew Tridgell 1998 + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. +*/ + +#include "wrapper.h" + +#ifdef linux +__asm__(".globl __lseek; __lseek = lseek"); +#endif + + ssize_t lseek(int fd, off_t offset, int whence) +{ + if (smbw_fd(fd)) { + return smbw_lseek(fd, offset, whence); + } + + return real_lseek(fd, offset, whence); +} diff --git a/source3/smbwrapper/realcalls.h b/source3/smbwrapper/realcalls.h index ef173c8964..898a94eeb4 100644 --- a/source3/smbwrapper/realcalls.h +++ b/source3/smbwrapper/realcalls.h @@ -32,6 +32,7 @@ struct dirent *__libc_readdir(DIR * dir); #define real_stat(fn, buf ) (syscall(SYS_stat, (fn), (buf))) #define real_fstat(fd, buf ) (syscall(SYS_fstat, (fd), (buf))) #define real_read(fd, buf, count ) (syscall(SYS_read, (fd), (buf), (count))) +#define real_lseek(fd, offset, whence) (syscall(SYS_lseek, (fd), (offset), (whence))) #define real_write(fd, buf, count ) (syscall(SYS_write, (fd), (buf), (count))) #define real_close(fd) (syscall(SYS_close, (fd))) #define real_fcntl(fd,cmd,arg) (syscall(SYS_fcntl, (fd), (cmd), (arg))) diff --git a/source3/smbwrapper/smbw.c b/source3/smbwrapper/smbw.c index 5392cf1abc..d77f33c97e 100644 --- a/source3/smbwrapper/smbw.c +++ b/source3/smbwrapper/smbw.c @@ -654,6 +654,8 @@ int smbw_dir_open(const char *fname, int flags) dir->fd = fd + SMBW_FD_OFFSET; + DEBUG(4,(" -> %d\n", dir->count)); + return dir->fd; failed: @@ -1053,6 +1055,9 @@ int smbw_getdents(unsigned int fd, struct dirent *dirp, int count) sizeof(dirp->d_name)-1); dir->offset++; count -= dirp->d_reclen; + if (dir->offset == dir->count) { + dirp->d_off = -1; + } dirp++; n++; } @@ -1410,10 +1415,48 @@ int smbw_chmod(const char *fname, mode_t newmode) return -1; } + +/***************************************************** +a wrapper for lseek() on directories +*******************************************************/ +off_t smbw_dir_lseek(int fd, off_t offset, int whence) +{ + struct smbw_dir *dir; + off_t ret; + + DEBUG(4,("%s offset=%d whence=%d\n", __FUNCTION__, + (int)offset, whence)); + + dir = smbw_dir(fd); + if (!dir) { + errno = EBADF; + return -1; + } + + switch (whence) { + case SEEK_SET: + dir->offset = offset/sizeof(struct dirent); + break; + case SEEK_CUR: + dir->offset += offset/sizeof(struct dirent); + break; + case SEEK_END: + dir->offset = (dir->count * sizeof(struct dirent)) + offset; + dir->offset /= sizeof(struct dirent); + break; + } + + ret = dir->offset * sizeof(struct dirent); + + DEBUG(4,(" -> %d\n", (int)ret)); + + return ret; +} + /***************************************************** a wrapper for lseek() *******************************************************/ -ssize_t smbw_lseek(int fd, off_t offset, int whence) +off_t smbw_lseek(int fd, off_t offset, int whence) { struct smbw_file *file; uint32 size; @@ -1424,9 +1467,9 @@ ssize_t smbw_lseek(int fd, off_t offset, int whence) file = smbw_file(fd); if (!file) { - errno = EBADF; + off_t ret = smbw_dir_lseek(fd, offset, whence); smbw_busy--; - return -1; + return ret; } switch (whence) { |