1998-10-04 03:28:43 +00:00
/*
2002-01-30 06:08:46 +00:00
Unix SMB / CIFS implementation .
1998-10-04 03:28:43 +00:00
SMB wrapper directory 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 0213 9 , USA .
*/
# include "includes.h"
1998-10-07 07:55:14 +00:00
# include "realcalls.h"
1998-10-04 03:28:43 +00:00
1998-10-06 10:24:22 +00:00
extern pstring smbw_cwd ;
extern fstring smbw_prefix ;
1998-10-04 03:28:43 +00:00
static struct smbw_dir * smbw_dirs ;
extern struct bitmap * smbw_file_bmap ;
extern int smbw_busy ;
/*****************************************************
map a fd to a smbw_dir structure
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
struct smbw_dir * smbw_dir ( int fd )
{
struct smbw_dir * dir ;
for ( dir = smbw_dirs ; dir ; dir = dir - > next ) {
if ( dir - > fd = = fd ) return dir ;
}
return NULL ;
}
/*****************************************************
check if a DIR * is one of ours
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_dirp ( DIR * dirp )
{
struct smbw_dir * d = ( struct smbw_dir * ) dirp ;
struct smbw_dir * dir ;
for ( dir = smbw_dirs ; dir ; dir = dir - > next ) {
if ( dir = = d ) return 1 ;
}
return 0 ;
}
/*****************************************************
free a smbw_dir structure and all entries
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
static void free_dir ( struct smbw_dir * dir )
{
2001-09-17 11:25:41 +00:00
if ( ! dir ) return ;
SAFE_FREE ( dir - > list ) ;
SAFE_FREE ( dir - > path ) ;
1998-10-04 03:28:43 +00:00
ZERO_STRUCTP ( dir ) ;
2001-09-17 11:25:41 +00:00
SAFE_FREE ( dir ) ;
1998-10-04 03:28:43 +00:00
}
static struct smbw_dir * cur_dir ;
/*****************************************************
add a entry to a directory listing
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
2001-01-15 17:46:02 +00:00
static void smbw_dir_add ( struct file_info * finfo , const char * mask ,
void * state )
1998-10-04 03:28:43 +00:00
{
2001-08-12 17:30:01 +00:00
struct file_info * cdl ;
1998-10-04 03:28:43 +00:00
DEBUG ( 5 , ( " %s \n " , finfo - > name ) ) ;
if ( cur_dir - > malloced = = cur_dir - > count ) {
2001-08-12 17:30:01 +00:00
cdl = ( struct file_info * ) Realloc ( cur_dir - > list ,
1998-10-04 03:28:43 +00:00
sizeof ( cur_dir - > list [ 0 ] ) *
( cur_dir - > count + 100 ) ) ;
2001-10-11 12:33:26 +00:00
if ( ! cdl ) {
1998-10-04 03:28:43 +00:00
/* oops */
return ;
}
2001-08-12 17:30:01 +00:00
cur_dir - > list = cdl ;
1998-10-04 03:28:43 +00:00
cur_dir - > malloced + = 100 ;
}
cur_dir - > list [ cur_dir - > count ] = * finfo ;
cur_dir - > count + + ;
}
/*****************************************************
add a entry to a directory listing
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
2001-01-04 11:35:55 +00:00
static void smbw_share_add ( const char * share , uint32 type ,
2001-04-12 05:53:07 +00:00
const char * comment , void * state )
1998-10-04 03:28:43 +00:00
{
struct file_info finfo ;
1998-10-04 14:07:18 +00:00
if ( strcmp ( share , " IPC$ " ) = = 0 ) return ;
1998-10-04 03:28:43 +00:00
ZERO_STRUCT ( finfo ) ;
pstrcpy ( finfo . name , share ) ;
finfo . mode = aRONLY | aDIR ;
2001-01-15 17:46:02 +00:00
smbw_dir_add ( & finfo , NULL , NULL ) ;
1998-10-04 03:28:43 +00:00
}
1998-10-04 11:25:06 +00:00
/*****************************************************
add a server to a directory listing
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
static void smbw_server_add ( const char * name , uint32 type ,
2001-01-04 11:35:55 +00:00
const char * comment , void * state )
1998-10-04 11:25:06 +00:00
{
struct file_info finfo ;
ZERO_STRUCT ( finfo ) ;
pstrcpy ( finfo . name , name ) ;
finfo . mode = aRONLY | aDIR ;
2001-01-15 17:46:02 +00:00
smbw_dir_add ( & finfo , NULL , NULL ) ;
1998-10-04 11:25:06 +00:00
}
1998-10-04 09:42:51 +00:00
/*****************************************************
add a entry to a directory listing
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
static void smbw_printjob_add ( struct print_job_info * job )
{
struct file_info finfo ;
ZERO_STRUCT ( finfo ) ;
pstrcpy ( finfo . name , job - > name ) ;
finfo . mode = aRONLY | aDIR ;
finfo . mtime = job - > t ;
finfo . atime = job - > t ;
finfo . ctime = job - > t ;
1999-12-13 13:27:58 +00:00
finfo . uid = nametouid ( job - > user ) ;
1998-10-04 09:42:51 +00:00
finfo . mode = aRONLY ;
finfo . size = job - > size ;
2001-01-15 17:46:02 +00:00
smbw_dir_add ( & finfo , NULL , NULL ) ;
1998-10-04 09:42:51 +00:00
}
1998-10-04 03:28:43 +00:00
/*****************************************************
open a directory on the server
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_dir_open ( const char * fname )
{
fstring server , share ;
pstring path ;
struct smbw_server * srv = NULL ;
struct smbw_dir * dir = NULL ;
pstring mask ;
int fd ;
1998-10-04 11:25:06 +00:00
char * s , * p ;
1998-10-04 03:28:43 +00:00
if ( ! fname ) {
errno = EINVAL ;
return - 1 ;
}
smbw_init ( ) ;
/* work out what server they are after */
s = smbw_parse_path ( fname , server , share , path ) ;
DEBUG ( 4 , ( " dir_open share=%s \n " , share ) ) ;
/* get a connection to the server */
srv = smbw_server ( server , share ) ;
if ( ! srv ) {
/* smbw_server sets errno */
goto failed ;
}
dir = ( struct smbw_dir * ) malloc ( sizeof ( * dir ) ) ;
if ( ! dir ) {
errno = ENOMEM ;
goto failed ;
}
ZERO_STRUCTP ( dir ) ;
cur_dir = dir ;
slprintf ( mask , sizeof ( mask ) - 1 , " %s \\ * " , path ) ;
1999-12-13 13:27:58 +00:00
all_string_sub ( mask , " \\ \\ " , " \\ " , 0 ) ;
1998-10-04 03:28:43 +00:00
2000-12-11 00:09:06 +00:00
if ( ( p = strstr ( srv - > server_name , " #01 " ) ) ) {
* p = 0 ;
2001-01-05 00:17:36 +00:00
smbw_server_add ( " . " , 0 , " " , NULL ) ;
smbw_server_add ( " .. " , 0 , " " , NULL ) ;
2001-04-12 05:53:07 +00:00
smbw_NetServerEnum ( & srv - > cli , srv - > server_name ,
SV_TYPE_DOMAIN_ENUM , smbw_server_add , NULL ) ;
2000-12-11 00:09:06 +00:00
* p = ' # ' ;
} else if ( ( p = strstr ( srv - > server_name , " #1D " ) ) ) {
1998-10-04 11:25:06 +00:00
DEBUG ( 4 , ( " doing NetServerEnum \n " ) ) ;
* p = 0 ;
2001-01-05 00:17:36 +00:00
smbw_server_add ( " . " , 0 , " " , NULL ) ;
smbw_server_add ( " .. " , 0 , " " , NULL ) ;
2001-04-12 05:53:07 +00:00
smbw_NetServerEnum ( & srv - > cli , srv - > server_name , SV_TYPE_ALL ,
smbw_server_add , NULL ) ;
1998-10-04 11:25:06 +00:00
* p = ' # ' ;
2003-04-23 10:07:25 +00:00
} else if ( ( strcmp ( srv - > cli . dev , " IPC " ) = = 0 ) | | ( strcasecmp ( share , " IPC$ " ) = = 0 ) ) {
1998-10-04 03:28:43 +00:00
DEBUG ( 4 , ( " doing NetShareEnum \n " ) ) ;
2001-01-05 00:17:36 +00:00
smbw_share_add ( " . " , 0 , " " , NULL ) ;
smbw_share_add ( " .. " , 0 , " " , NULL ) ;
2001-04-12 05:53:07 +00:00
if ( smbw_RNetShareEnum ( & srv - > cli , smbw_share_add , NULL ) < 0 ) {
1998-10-04 09:42:51 +00:00
errno = smbw_errno ( & srv - > cli ) ;
goto failed ;
}
} else if ( strncmp ( srv - > cli . dev , " LPT " , 3 ) = = 0 ) {
2001-01-05 00:17:36 +00:00
smbw_share_add ( " . " , 0 , " " , NULL ) ;
smbw_share_add ( " .. " , 0 , " " , NULL ) ;
1998-10-04 09:42:51 +00:00
if ( cli_print_queue ( & srv - > cli , smbw_printjob_add ) < 0 ) {
1998-10-04 03:28:43 +00:00
errno = smbw_errno ( & srv - > cli ) ;
goto failed ;
}
} else {
2000-12-11 00:09:06 +00:00
#if 0
1998-10-24 08:08:05 +00:00
if ( strcmp ( path , " \\ " ) = = 0 ) {
smbw_share_add ( " . " , 0 , " " ) ;
smbw_share_add ( " .. " , 0 , " " ) ;
}
2000-12-11 00:09:06 +00:00
# endif
1998-10-04 03:28:43 +00:00
if ( cli_list ( & srv - > cli , mask , aHIDDEN | aSYSTEM | aDIR ,
2001-01-05 13:11:29 +00:00
smbw_dir_add , NULL ) < 0 ) {
1998-10-04 03:28:43 +00:00
errno = smbw_errno ( & srv - > cli ) ;
goto failed ;
}
}
cur_dir = NULL ;
1998-10-04 06:22:08 +00:00
fd = open ( SMBW_DUMMY , O_WRONLY ) ;
1998-10-04 03:28:43 +00:00
if ( fd = = - 1 ) {
errno = EMFILE ;
goto failed ;
}
1998-10-04 04:48:17 +00:00
if ( bitmap_query ( smbw_file_bmap , fd ) ) {
DEBUG ( 0 , ( " ERROR: fd used in smbw_dir_open \n " ) ) ;
errno = EIO ;
goto failed ;
}
1998-10-04 03:28:43 +00:00
DLIST_ADD ( smbw_dirs , dir ) ;
bitmap_set ( smbw_file_bmap , fd ) ;
1998-10-04 04:48:17 +00:00
dir - > fd = fd ;
1998-10-04 03:28:43 +00:00
dir - > srv = srv ;
dir - > path = strdup ( s ) ;
DEBUG ( 4 , ( " -> %d \n " , dir - > count ) ) ;
return dir - > fd ;
failed :
2001-09-17 11:25:41 +00:00
free_dir ( dir ) ;
1998-10-04 03:28:43 +00:00
return - 1 ;
}
/*****************************************************
a wrapper for fstat ( ) on a directory
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_dir_fstat ( int fd , struct stat * st )
{
struct smbw_dir * dir ;
dir = smbw_dir ( fd ) ;
if ( ! dir ) {
errno = EBADF ;
return - 1 ;
}
ZERO_STRUCTP ( st ) ;
1998-10-04 14:02:50 +00:00
smbw_setup_stat ( st , " " , dir - > count * DIRP_SIZE , aDIR ) ;
1998-10-04 03:28:43 +00:00
st - > st_dev = dir - > srv - > dev ;
return 0 ;
}
/*****************************************************
close a directory handle
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_dir_close ( int fd )
{
struct smbw_dir * dir ;
dir = smbw_dir ( fd ) ;
if ( ! dir ) {
errno = EBADF ;
return - 1 ;
}
1998-10-04 04:48:17 +00:00
bitmap_clear ( smbw_file_bmap , dir - > fd ) ;
close ( dir - > fd ) ;
1998-10-04 03:28:43 +00:00
DLIST_REMOVE ( smbw_dirs , dir ) ;
free_dir ( dir ) ;
return 0 ;
}
/*****************************************************
a wrapper for getdents ( )
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_getdents ( unsigned int fd , struct dirent * dirp , int count )
{
struct smbw_dir * dir ;
int n = 0 ;
smbw_busy + + ;
dir = smbw_dir ( fd ) ;
if ( ! dir ) {
errno = EBADF ;
smbw_busy - - ;
return - 1 ;
}
1998-10-04 14:02:50 +00:00
while ( count > = DIRP_SIZE & & ( dir - > offset < dir - > count ) ) {
1998-10-07 07:55:14 +00:00
# if HAVE_DIRENT_D_OFF
1998-10-04 14:02:50 +00:00
dirp - > d_off = ( dir - > offset + 1 ) * DIRP_SIZE ;
1998-10-07 07:55:14 +00:00
# endif
1998-10-04 14:02:50 +00:00
dirp - > d_reclen = DIRP_SIZE ;
fstrcpy ( & dirp - > d_name [ 0 ] , dir - > list [ dir - > offset ] . name ) ;
1998-10-04 03:28:43 +00:00
dirp - > d_ino = smbw_inode ( dir - > list [ dir - > offset ] . name ) ;
dir - > offset + + ;
count - = dirp - > d_reclen ;
1998-10-07 07:55:14 +00:00
# if HAVE_DIRENT_D_OFF
1998-10-04 03:28:43 +00:00
if ( dir - > offset = = dir - > count ) {
dirp - > d_off = - 1 ;
}
1998-10-07 07:55:14 +00:00
# endif
1998-10-04 14:02:50 +00:00
dirp = ( struct dirent * ) ( ( ( char * ) dirp ) + DIRP_SIZE ) ;
1998-10-04 03:28:43 +00:00
n + + ;
}
smbw_busy - - ;
1998-10-04 14:02:50 +00:00
return n * DIRP_SIZE ;
1998-10-04 03:28:43 +00:00
}
/*****************************************************
a wrapper for chdir ( )
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_chdir ( const char * name )
{
struct smbw_server * srv ;
fstring server , share ;
pstring path ;
1998-11-09 20:33:37 +00:00
uint16 mode = aDIR ;
1998-10-04 03:28:43 +00:00
char * cwd ;
1998-10-06 10:24:22 +00:00
int len ;
1998-10-04 03:28:43 +00:00
smbw_init ( ) ;
1998-10-06 10:24:22 +00:00
len = strlen ( smbw_prefix ) ;
1998-10-05 12:43:05 +00:00
if ( smbw_busy ) return real_chdir ( name ) ;
1998-10-04 03:28:43 +00:00
smbw_busy + + ;
if ( ! name ) {
errno = EINVAL ;
goto failed ;
}
1998-10-06 10:24:22 +00:00
DEBUG ( 4 , ( " smbw_chdir(%s) \n " , name ) ) ;
1998-10-04 03:28:43 +00:00
/* work out what server they are after */
cwd = smbw_parse_path ( name , server , share , path ) ;
1998-10-06 10:24:22 +00:00
/* a special case - accept cd to /smb */
if ( strncmp ( cwd , smbw_prefix , len - 1 ) = = 0 & &
cwd [ len - 1 ] = = 0 ) {
1998-10-06 11:56:44 +00:00
goto success1 ;
1998-10-06 10:24:22 +00:00
}
if ( strncmp ( cwd , smbw_prefix , strlen ( smbw_prefix ) ) ) {
1998-10-04 03:28:43 +00:00
if ( real_chdir ( cwd ) = = 0 ) {
1998-10-06 11:56:44 +00:00
goto success2 ;
1998-10-04 03:28:43 +00:00
}
goto failed ;
}
/* get a connection to the server */
srv = smbw_server ( server , share ) ;
if ( ! srv ) {
/* smbw_server sets errno */
goto failed ;
}
2003-04-23 10:07:25 +00:00
if ( strncmp ( srv - > cli . dev , " IPC " , 3 ) & &
strcasecmp ( share , " IPC$ " ) & &
1998-10-04 09:42:51 +00:00
strncmp ( srv - > cli . dev , " LPT " , 3 ) & &
1998-10-04 03:28:43 +00:00
! smbw_getatr ( srv , path ,
1998-10-24 08:08:05 +00:00
& mode , NULL , NULL , NULL , NULL , NULL ) ) {
1998-10-04 03:28:43 +00:00
errno = smbw_errno ( & srv - > cli ) ;
goto failed ;
}
if ( ! ( mode & aDIR ) ) {
errno = ENOTDIR ;
goto failed ;
}
1998-10-06 11:56:44 +00:00
success1 :
/* we don't want the old directory to be busy */
real_chdir ( " / " ) ;
success2 :
1998-10-06 10:24:22 +00:00
DEBUG ( 4 , ( " set SMBW_CWD to %s \n " , cwd ) ) ;
pstrcpy ( smbw_cwd , cwd ) ;
1998-10-04 03:28:43 +00:00
smbw_busy - - ;
return 0 ;
failed :
smbw_busy - - ;
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 ;
dir = smbw_dir ( fd ) ;
if ( ! dir ) {
errno = EBADF ;
return - 1 ;
}
switch ( whence ) {
case SEEK_SET :
1998-10-04 14:02:50 +00:00
dir - > offset = offset / DIRP_SIZE ;
1998-10-04 03:28:43 +00:00
break ;
case SEEK_CUR :
1998-10-04 14:02:50 +00:00
dir - > offset + = offset / DIRP_SIZE ;
1998-10-04 03:28:43 +00:00
break ;
case SEEK_END :
1998-10-04 14:02:50 +00:00
dir - > offset = ( dir - > count * DIRP_SIZE ) + offset ;
dir - > offset / = DIRP_SIZE ;
1998-10-04 03:28:43 +00:00
break ;
}
1998-10-04 14:02:50 +00:00
ret = dir - > offset * DIRP_SIZE ;
1998-10-04 03:28:43 +00:00
DEBUG ( 4 , ( " -> %d \n " , ( int ) ret ) ) ;
return ret ;
}
/*****************************************************
a wrapper for mkdir ( )
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_mkdir ( const char * fname , mode_t mode )
{
struct smbw_server * srv ;
fstring server , share ;
pstring path ;
if ( ! fname ) {
errno = EINVAL ;
return - 1 ;
}
smbw_init ( ) ;
smbw_busy + + ;
/* work out what server they are after */
smbw_parse_path ( fname , server , share , path ) ;
/* get a connection to the server */
srv = smbw_server ( server , share ) ;
if ( ! srv ) {
/* smbw_server sets errno */
goto failed ;
}
if ( ! cli_mkdir ( & srv - > cli , path ) ) {
errno = smbw_errno ( & srv - > cli ) ;
goto failed ;
}
smbw_busy - - ;
return 0 ;
failed :
smbw_busy - - ;
return - 1 ;
}
/*****************************************************
a wrapper for rmdir ( )
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_rmdir ( const char * fname )
{
struct smbw_server * srv ;
fstring server , share ;
pstring path ;
if ( ! fname ) {
errno = EINVAL ;
return - 1 ;
}
smbw_init ( ) ;
smbw_busy + + ;
/* work out what server they are after */
smbw_parse_path ( fname , server , share , path ) ;
/* get a connection to the server */
srv = smbw_server ( server , share ) ;
if ( ! srv ) {
/* smbw_server sets errno */
goto failed ;
}
if ( ! cli_rmdir ( & srv - > cli , path ) ) {
errno = smbw_errno ( & srv - > cli ) ;
goto failed ;
}
smbw_busy - - ;
return 0 ;
failed :
smbw_busy - - ;
return - 1 ;
}
/*****************************************************
a wrapper for getcwd ( )
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
char * smbw_getcwd ( char * buf , size_t size )
{
smbw_init ( ) ;
if ( smbw_busy ) {
1998-10-07 10:49:27 +00:00
return ( char * ) real_getcwd ( buf , size ) ;
1998-10-04 03:28:43 +00:00
}
smbw_busy + + ;
if ( ! buf ) {
1998-10-06 10:24:22 +00:00
if ( size < = 0 ) size = strlen ( smbw_cwd ) + 1 ;
1998-10-04 03:28:43 +00:00
buf = ( char * ) malloc ( size ) ;
if ( ! buf ) {
errno = ENOMEM ;
smbw_busy - - ;
return NULL ;
}
}
1998-10-06 10:24:22 +00:00
if ( strlen ( smbw_cwd ) > size - 1 ) {
1998-10-04 03:28:43 +00:00
errno = ERANGE ;
smbw_busy - - ;
return NULL ;
}
1998-10-06 10:24:22 +00:00
safe_strcpy ( buf , smbw_cwd , size ) ;
1998-10-04 03:28:43 +00:00
smbw_busy - - ;
return buf ;
}
/*****************************************************
a wrapper for fchdir ( )
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_fchdir ( unsigned int fd )
{
struct smbw_dir * dir ;
1998-10-08 01:23:33 +00:00
int ret ;
1998-10-04 03:28:43 +00:00
smbw_busy + + ;
dir = smbw_dir ( fd ) ;
1998-10-08 01:23:33 +00:00
if ( dir ) {
1998-10-04 03:28:43 +00:00
smbw_busy - - ;
1998-10-08 01:23:33 +00:00
return chdir ( dir - > path ) ;
1998-10-04 03:28:43 +00:00
}
1998-10-08 01:23:33 +00:00
ret = real_fchdir ( fd ) ;
if ( ret = = 0 ) {
sys_getwd ( smbw_cwd ) ;
}
1998-10-04 03:28:43 +00:00
smbw_busy - - ;
1998-10-08 01:23:33 +00:00
return ret ;
1998-10-04 03:28:43 +00:00
}
/*****************************************************
open a directory on the server
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
DIR * smbw_opendir ( const char * fname )
{
int fd ;
smbw_busy + + ;
fd = smbw_dir_open ( fname ) ;
if ( fd = = - 1 ) {
smbw_busy - - ;
return NULL ;
}
smbw_busy - - ;
return ( DIR * ) smbw_dir ( fd ) ;
}
/*****************************************************
read one entry from a directory
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
1998-10-04 04:33:56 +00:00
struct dirent * smbw_readdir ( DIR * dirp )
1998-10-04 03:28:43 +00:00
{
1998-10-04 04:33:56 +00:00
struct smbw_dir * d = ( struct smbw_dir * ) dirp ;
1998-10-05 01:42:46 +00:00
static union {
char buf [ DIRP_SIZE ] ;
struct dirent de ;
} dbuf ;
1998-10-04 03:28:43 +00:00
1998-10-05 01:42:46 +00:00
if ( smbw_getdents ( d - > fd , & dbuf . de , DIRP_SIZE ) > 0 )
return & dbuf . de ;
1998-10-04 03:28:43 +00:00
return NULL ;
}
/*****************************************************
close a DIR *
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
1998-10-04 04:33:56 +00:00
int smbw_closedir ( DIR * dirp )
1998-10-04 03:28:43 +00:00
{
1998-10-04 04:33:56 +00:00
struct smbw_dir * d = ( struct smbw_dir * ) dirp ;
1998-10-04 03:28:43 +00:00
return smbw_close ( d - > fd ) ;
}
/*****************************************************
seek in a directory
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
1998-10-04 04:33:56 +00:00
void smbw_seekdir ( DIR * dirp , off_t offset )
1998-10-04 03:28:43 +00:00
{
1998-10-04 04:33:56 +00:00
struct smbw_dir * d = ( struct smbw_dir * ) dirp ;
1998-10-04 03:28:43 +00:00
smbw_dir_lseek ( d - > fd , offset , SEEK_SET ) ;
}
/*****************************************************
current loc in a directory
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
1998-10-04 04:33:56 +00:00
off_t smbw_telldir ( DIR * dirp )
1998-10-04 03:28:43 +00:00
{
1998-10-04 04:33:56 +00:00
struct smbw_dir * d = ( struct smbw_dir * ) dirp ;
1998-10-04 03:28:43 +00:00
return smbw_dir_lseek ( d - > fd , 0 , SEEK_CUR ) ;
}