2005-03-29 00:42:51 +00:00
/*
Unix SMB / Netbios implementation .
Version 2.0
SMB wrapper functions
Copyright ( C ) Andrew Tridgell 1998
Copyright ( C ) Derrell Lipman 2003 - 2005
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
2007-07-09 19:25:36 +00:00
the Free Software Foundation ; either version 3 of the License , or
2005-03-29 00:42:51 +00:00
( 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
2007-07-10 00:57:11 +00:00
along with this program . If not , see < http : //www.gnu.org/licenses/>.
2005-03-29 00:42:51 +00:00
*/
# include <stdio.h>
# include <stdlib.h>
# include <unistd.h>
# include <stdarg.h>
# include <assert.h>
# include "smbw.h"
2006-01-07 20:43:36 +00:00
# include "bsd-strlfunc.h"
typedef enum StartupType
{
StartupType_Fake ,
StartupType_Real
} StartupType ;
2005-03-29 00:42:51 +00:00
int smbw_fd_map [ __FD_SETSIZE ] ;
int smbw_ref_count [ __FD_SETSIZE ] ;
char smbw_cwd [ PATH_MAX ] ;
char smbw_prefix [ ] = SMBW_PREFIX ;
/* needs to be here because of dumb include files on some systems */
int creat_bits = O_WRONLY | O_CREAT | O_TRUNC ;
int smbw_initialized = 0 ;
static int debug_level = 0 ;
static SMBCCTX * smbw_ctx ;
extern int smbw_debug ;
2006-01-07 20:43:36 +00:00
/*****************************************************
smbw_ref - - manipulate reference counts
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
2005-03-29 00:42:51 +00:00
int smbw_ref ( int client_fd , Ref_Count_Type type , . . . )
{
/* client id values begin at SMBC_BASE_FC. */
client_fd - = SMBC_BASE_FD ;
switch ( type )
{
case SMBW_RCT_Increment :
return + + smbw_ref_count [ client_fd ] ;
case SMBW_RCT_Decrement :
return - - smbw_ref_count [ client_fd ] ;
case SMBW_RCT_Get :
return smbw_ref_count [ client_fd ] ;
case SMBW_RCT_Set :
2009-06-12 13:01:41 +02:00
{
va_list ap ;
int ret ;
va_start ( ap , type ) ;
ret = ( smbw_ref_count [ client_fd ] = va_arg ( ap , int ) ) ;
va_end ( ap ) ;
return ret ;
}
2005-03-29 00:42:51 +00:00
}
/* never gets here */
return - 1 ;
}
/*
* Return a username and password given a server and share name
*
* Returns 0 upon success ;
* non - zero otherwise , and errno is set to indicate the error .
*/
static void get_envvar_auth_data ( const char * srv ,
const char * shr ,
char * wg , int wglen ,
char * un , int unlen ,
char * pw , int pwlen )
{
char * u ;
char * p ;
char * w ;
/* Fall back to environment variables */
w = getenv ( " WORKGROUP " ) ;
if ( w = = NULL ) w = " " ;
u = getenv ( " USER " ) ;
if ( u = = NULL ) u = " " ;
p = getenv ( " PASSWORD " ) ;
if ( p = = NULL ) p = " " ;
2006-01-07 20:43:36 +00:00
smbw_strlcpy ( wg , w , wglen ) ;
smbw_strlcpy ( un , u , unlen ) ;
smbw_strlcpy ( pw , p , pwlen ) ;
2005-03-29 00:42:51 +00:00
}
static smbc_get_auth_data_fn get_auth_data_fn = get_envvar_auth_data ;
/*****************************************************
set the get auth data function
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
void smbw_set_auth_data_fn ( smbc_get_auth_data_fn fn )
{
get_auth_data_fn = fn ;
}
/*****************************************************
ensure that all connections are terminated upon exit
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
static void do_shutdown ( void )
{
if ( smbw_ctx ! = NULL ) {
smbc_free_context ( smbw_ctx , 1 ) ;
}
}
/*****************************************************
initialise structures
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
2006-01-07 20:43:36 +00:00
static void do_init ( StartupType startupType )
2005-03-29 00:42:51 +00:00
{
int i ;
char * p ;
smbw_initialized = 1 ; /* this must be first to avoid recursion! */
smbw_ctx = NULL ; /* don't free context until it's established */
/* initially, no file descriptors are mapped */
for ( i = 0 ; i < __FD_SETSIZE ; i + + ) {
smbw_fd_map [ i ] = - 1 ;
smbw_ref_count [ i ] = 0 ;
}
/* See if we've been told to start in a particular directory */
if ( ( p = getenv ( " SMBW_DIR " ) ) ! = NULL ) {
2006-01-07 20:43:36 +00:00
smbw_strlcpy ( smbw_cwd , p , PATH_MAX ) ;
2005-03-29 00:42:51 +00:00
/* we don't want the old directory to be busy */
( * smbw_libc . chdir ) ( " / " ) ;
} else {
* smbw_cwd = ' \0 ' ;
}
if ( ( p = getenv ( " DEBUG " ) ) ) {
debug_level = atoi ( p ) ;
}
if ( ( smbw_ctx = smbc_new_context ( ) ) = = NULL ) {
2006-01-07 20:43:36 +00:00
fprintf ( stderr , " Could not create a context. \n " ) ;
2005-03-29 00:42:51 +00:00
exit ( 1 ) ;
}
2008-02-28 11:23:20 -05:00
smbc_setDebug ( smbw_ctx , debug_level ) ;
smbc_setFunctionAuthData ( smbw_ctx , get_auth_data_fn ) ;
2008-03-02 16:21:48 -05:00
smbc_setOptionBrowseMaxLmbCount ( smbw_ctx , 0 ) ;
smbc_setOptionUrlEncodeReaddirEntries ( smbw_ctx , 1 ) ;
smbc_setOptionOneSharePerServer ( smbw_ctx , 1 ) ;
2005-03-29 00:42:51 +00:00
if ( smbc_init_context ( smbw_ctx ) = = NULL ) {
2006-01-07 20:43:36 +00:00
fprintf ( stderr , " Could not initialize context. \n " ) ;
2005-03-29 00:42:51 +00:00
exit ( 1 ) ;
}
smbc_set_context ( smbw_ctx ) ;
/* if not real startup, exit handler has already been established */
2006-01-07 20:43:36 +00:00
if ( startupType = = StartupType_Real ) {
2005-03-29 00:42:51 +00:00
atexit ( do_shutdown ) ;
}
}
/*****************************************************
initialise structures , real start up vs a fork ( )
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
void smbw_init ( void )
{
2006-01-07 20:43:36 +00:00
do_init ( StartupType_Real ) ;
2005-03-29 00:42:51 +00:00
}
/*****************************************************
determine if a file descriptor is a smb one
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_fd ( int smbw_fd )
{
SMBW_INIT ( ) ;
return ( smbw_fd > = 0 & &
smbw_fd < __FD_SETSIZE & &
smbw_fd_map [ smbw_fd ] > = SMBC_BASE_FD ) ; /* minimum smbc_ fd */
}
/*****************************************************
determine if a path is a smb one
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_path ( const char * name )
{
int len ;
int ret ;
int saved_errno ;
saved_errno = errno ;
SMBW_INIT ( ) ;
len = strlen ( smbw_prefix ) ;
ret = ( ( strncmp ( name , smbw_prefix , len ) = = 0 & &
( name [ len ] = = ' \0 ' | | name [ len ] = = ' / ' ) ) | |
( * name ! = ' / ' & & * smbw_cwd ! = ' \0 ' ) ) ;
errno = saved_errno ;
return ret ;
}
/*****************************************************
remove redundent stuff from a filename
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
void smbw_clean_fname ( char * name )
{
char * p , * p2 ;
int l ;
int modified = 1 ;
if ( ! name ) return ;
DEBUG ( 10 , ( " Clean [%s]... \n " , name ) ) ;
while ( modified ) {
modified = 0 ;
if ( ( p = strstr ( name , " /./ " ) ) ) {
modified = 1 ;
while ( * p ) {
p [ 0 ] = p [ 2 ] ;
p + + ;
}
DEBUG ( 10 , ( " \t clean 1 (/./) produced [%s] \n " , name ) ) ;
}
if ( ( p = strstr ( name , " // " ) ) ) {
modified = 1 ;
while ( * p ) {
p [ 0 ] = p [ 1 ] ;
p + + ;
}
DEBUG ( 10 , ( " \t clean 2 (//) produced [%s] \n " , name ) ) ;
}
if ( strcmp ( name , " /../ " ) = = 0 ) {
modified = 1 ;
name [ 1 ] = 0 ;
DEBUG ( 10 , ( " \t clean 3 (^/../$) produced [%s] \n " , name ) ) ;
}
if ( ( p = strstr ( name , " /../ " ) ) ) {
modified = 1 ;
for ( p2 = ( p > name ? p - 1 : p ) ; p2 > name ; p2 - - ) {
if ( p2 [ 0 ] = = ' / ' ) break ;
}
if ( p2 > name ) p2 + + ;
while ( * p2 ) {
p2 [ 0 ] = p [ 3 ] ;
p2 + + ;
p + + ;
}
DEBUG ( 10 , ( " \t clean 4 (/../) produced [%s] \n " , name ) ) ;
}
if ( strcmp ( name , " /.. " ) = = 0 ) {
modified = 1 ;
name [ 1 ] = 0 ;
DEBUG ( 10 , ( " \t clean 5 (^/..$) produced [%s] \n " , name ) ) ;
}
l = strlen ( name ) ;
p = l > = 3 ? ( name + l - 3 ) : name ;
if ( strcmp ( p , " /.. " ) = = 0 ) {
modified = 1 ;
for ( p2 = p - 1 ; p2 > name ; p2 - - ) {
if ( p2 [ 0 ] = = ' / ' ) break ;
}
if ( p2 = = name ) {
p [ 0 ] = ' / ' ;
p [ 1 ] = 0 ;
} else {
p2 [ 0 ] = 0 ;
}
DEBUG ( 10 , ( " \t clean 6 (/..) produced [%s] \n " , name ) ) ;
}
l = strlen ( name ) ;
p = l > = 2 ? ( name + l - 2 ) : name ;
if ( strcmp ( p , " /. " ) = = 0 ) {
modified = 1 ;
if ( p = = name ) {
p [ 1 ] = 0 ;
} else {
p [ 0 ] = 0 ;
}
DEBUG ( 10 , ( " \t clean 7 (/.) produced [%s] \n " , name ) ) ;
}
if ( strncmp ( p = name , " ./ " , 2 ) = = 0 ) {
modified = 1 ;
do {
p [ 0 ] = p [ 2 ] ;
} while ( * p + + ) ;
DEBUG ( 10 , ( " \t clean 8 (^./) produced [%s] \n " , name ) ) ;
}
l = strlen ( p = name ) ;
if ( l > 1 & & p [ l - 1 ] = = ' / ' ) {
modified = 1 ;
p [ l - 1 ] = 0 ;
DEBUG ( 10 , ( " \t clean 9 (/) produced [%s] \n " , name ) ) ;
}
}
}
void smbw_fix_path ( const char * src , char * dest )
{
const char * p ;
int len = strlen ( smbw_prefix ) ;
if ( * src = = ' / ' ) {
for ( p = src + len ; * p = = ' / ' ; p + + )
;
snprintf ( dest , PATH_MAX , " smb://%s " , p ) ;
} else {
snprintf ( dest , PATH_MAX , " %s/%s " , smbw_cwd , src ) ;
}
smbw_clean_fname ( dest + 5 ) ;
DEBUG ( 10 , ( " smbw_fix_path(%s) returning [%s] \n " , src , dest ) ) ;
}
/*****************************************************
a wrapper for open ( )
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_open ( const char * fname , int flags , mode_t mode )
{
int client_fd ;
int smbw_fd ;
char path [ PATH_MAX ] ;
SMBW_INIT ( ) ;
if ( ! fname ) {
errno = EINVAL ;
return - 1 ;
}
smbw_fd = ( smbw_libc . open ) ( SMBW_DUMMY , O_WRONLY , 0200 ) ;
if ( smbw_fd = = - 1 ) {
errno = EMFILE ;
return - 1 ;
}
smbw_fix_path ( fname , path ) ;
if ( flags = = creat_bits ) {
client_fd = smbc_creat ( path , mode ) ;
} else {
client_fd = smbc_open ( path , flags , mode ) ;
}
if ( client_fd < 0 ) {
( * smbw_libc . close ) ( smbw_fd ) ;
return - 1 ;
}
smbw_fd_map [ smbw_fd ] = client_fd ;
smbw_ref ( client_fd , SMBW_RCT_Increment ) ;
return smbw_fd ;
}
/*****************************************************
a wrapper for pread ( )
there should really be an smbc_pread ( ) to avoid the two
lseek ( ) s required in this kludge .
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
ssize_t smbw_pread ( int smbw_fd , void * buf , size_t count , SMBW_OFF_T ofs )
{
int client_fd ;
ssize_t ret ;
int saved_errno ;
SMBW_OFF_T old_ofs ;
2006-01-07 20:43:36 +00:00
if ( count = = 0 ) {
return 0 ;
}
2005-03-29 00:42:51 +00:00
client_fd = smbw_fd_map [ smbw_fd ] ;
if ( ( old_ofs = smbc_lseek ( client_fd , 0 , SEEK_CUR ) ) < 0 | |
smbc_lseek ( client_fd , ofs , SEEK_SET ) < 0 ) {
return - 1 ;
}
if ( ( ret = smbc_read ( client_fd , buf , count ) ) < 0 ) {
saved_errno = errno ;
( void ) smbc_lseek ( client_fd , old_ofs , SEEK_SET ) ;
errno = saved_errno ;
return - 1 ;
}
return ret ;
}
/*****************************************************
a wrapper for read ( )
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
ssize_t smbw_read ( int smbw_fd , void * buf , size_t count )
{
int client_fd ;
client_fd = smbw_fd_map [ smbw_fd ] ;
return smbc_read ( client_fd , buf , count ) ;
}
/*****************************************************
a wrapper for write ( )
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
ssize_t smbw_write ( int smbw_fd , void * buf , size_t count )
{
int client_fd ;
client_fd = smbw_fd_map [ smbw_fd ] ;
return smbc_write ( client_fd , buf , count ) ;
}
/*****************************************************
a wrapper for pwrite ( )
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
ssize_t smbw_pwrite ( int smbw_fd , void * buf , size_t count , SMBW_OFF_T ofs )
{
int saved_errno ;
int client_fd ;
ssize_t ret ;
SMBW_OFF_T old_ofs ;
2006-01-07 20:43:36 +00:00
if ( count = = 0 ) {
return 0 ;
}
2005-03-29 00:42:51 +00:00
client_fd = smbw_fd_map [ smbw_fd ] ;
if ( ( old_ofs = smbc_lseek ( client_fd , 0 , SEEK_CUR ) ) < 0 | |
smbc_lseek ( client_fd , ofs , SEEK_SET ) < 0 ) {
return - 1 ;
}
if ( ( ret = smbc_write ( client_fd , buf , count ) ) < 0 ) {
saved_errno = errno ;
( void ) smbc_lseek ( client_fd , old_ofs , SEEK_SET ) ;
errno = saved_errno ;
return - 1 ;
}
return ret ;
}
/*****************************************************
a wrapper for close ( )
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_close ( int smbw_fd )
{
int client_fd ;
client_fd = smbw_fd_map [ smbw_fd ] ;
if ( smbw_ref ( client_fd , SMBW_RCT_Decrement ) > 0 ) {
return 0 ;
}
( * smbw_libc . close ) ( smbw_fd ) ;
smbw_fd_map [ smbw_fd ] = - 1 ;
return smbc_close ( client_fd ) ;
}
/*****************************************************
a wrapper for fcntl ( )
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_fcntl ( int smbw_fd , int cmd , long arg )
{
return 0 ;
}
/*****************************************************
a wrapper for access ( )
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_access ( const char * name , int mode )
{
struct SMBW_stat st ;
SMBW_INIT ( ) ;
if ( smbw_stat ( name , & st ) ) return - 1 ;
if ( ( ( mode & R_OK ) & & ! ( st . s_mode & S_IRUSR ) ) | |
( ( mode & W_OK ) & & ! ( st . s_mode & S_IWUSR ) ) | |
( ( mode & X_OK ) & & ! ( st . s_mode & S_IXUSR ) ) ) {
errno = EACCES ;
return - 1 ;
}
return 0 ;
}
/*****************************************************
a wrapper for readlink ( ) - needed for correct errno setting
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_readlink ( const char * fname , char * buf , size_t bufsize )
{
struct SMBW_stat st ;
int ret ;
SMBW_INIT ( ) ;
ret = smbw_stat ( fname , & st ) ;
if ( ret ! = 0 ) {
return - 1 ;
}
/* it exists - say it isn't a link */
errno = EINVAL ;
return - 1 ;
}
/*****************************************************
a wrapper for unlink ( )
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_unlink ( const char * fname )
{
char path [ PATH_MAX ] ;
SMBW_INIT ( ) ;
smbw_fix_path ( fname , path ) ;
return smbc_unlink ( path ) ;
}
/*****************************************************
a wrapper for rename ( )
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_rename ( const char * oldname , const char * newname )
{
char path_old [ PATH_MAX ] ;
char path_new [ PATH_MAX ] ;
SMBW_INIT ( ) ;
smbw_fix_path ( oldname , path_old ) ;
smbw_fix_path ( newname , path_new ) ;
return smbc_rename ( path_old , path_new ) ;
}
/*****************************************************
a wrapper for utimes
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_utimes ( const char * fname , void * buf )
{
char path [ PATH_MAX ] ;
smbw_fix_path ( fname , path ) ;
return smbc_utimes ( path , buf ) ;
}
/*****************************************************
a wrapper for utime
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_utime ( const char * fname , void * buf )
{
char path [ PATH_MAX ] ;
smbw_fix_path ( fname , path ) ;
return smbc_utime ( path , buf ) ;
}
/*****************************************************
a wrapper for chown ( )
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_chown ( const char * fname , uid_t owner , gid_t group )
{
/* always indiciate that this is not supported. */
errno = ENOTSUP ;
return - 1 ;
}
/*****************************************************
a wrapper for chmod ( )
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_chmod ( const char * fname , mode_t newmode )
{
char path [ PATH_MAX ] ;
smbw_fix_path ( fname , path ) ;
return smbc_chmod ( path , newmode ) ;
}
/*****************************************************
a wrapper for lseek ( )
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
SMBW_OFF_T smbw_lseek ( int smbw_fd ,
SMBW_OFF_T offset ,
int whence )
{
int client_fd ;
SMBW_OFF_T ret ;
client_fd = smbw_fd_map [ smbw_fd ] ;
ret = smbc_lseek ( client_fd , offset , whence ) ;
if ( smbw_debug )
{
printf ( " smbw_lseek(%d/%d, 0x%llx) returned 0x%llx \n " ,
smbw_fd , client_fd ,
( unsigned long long ) offset ,
( unsigned long long ) ret ) ;
}
return ret ;
}
/*****************************************************
a wrapper for dup ( )
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_dup ( int smbw_fd )
{
int fd2 ;
fd2 = ( smbw_libc . dup ) ( smbw_fd ) ;
if ( fd2 = = - 1 ) {
return - 1 ;
}
smbw_fd_map [ fd2 ] = smbw_fd_map [ smbw_fd ] ;
smbw_ref ( smbw_fd_map [ smbw_fd ] , SMBW_RCT_Increment ) ;
return fd2 ;
}
/*****************************************************
a wrapper for dup2 ( )
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_dup2 ( int smbw_fd , int fd2 )
{
if ( ( * smbw_libc . dup2 ) ( smbw_fd , fd2 ) ! = fd2 ) {
return - 1 ;
}
smbw_fd_map [ fd2 ] = smbw_fd_map [ smbw_fd ] ;
smbw_ref ( smbw_fd_map [ smbw_fd ] , SMBW_RCT_Increment ) ;
return fd2 ;
}
/*****************************************************
when we fork we have to close all connections and files
in the child
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
int smbw_fork ( void )
{
int i ;
pid_t child_pid ;
int p [ 2 ] ;
char c = 0 ;
SMBW_INIT ( ) ;
if ( pipe ( p ) ) return ( * smbw_libc . fork ) ( ) ;
child_pid = ( * smbw_libc . fork ) ( ) ;
if ( child_pid ) {
/* block the parent for a moment until the sockets are
closed */
( * smbw_libc . close ) ( p [ 1 ] ) ;
( * smbw_libc . read ) ( p [ 0 ] , & c , 1 ) ;
( * smbw_libc . close ) ( p [ 0 ] ) ;
return child_pid ;
}
( * smbw_libc . close ) ( p [ 0 ] ) ;
/* close all server connections and locally-opened files */
for ( i = 0 ; i < __FD_SETSIZE ; i + + ) {
if ( smbw_fd_map [ i ] > 0 & &
smbw_ref ( smbw_fd_map [ i ] , SMBW_RCT_Get ) > 0 ) {
smbc_close ( smbw_fd_map [ i ] ) ;
smbw_ref ( smbw_fd_map [ i ] , SMBW_RCT_Set , 0 ) ;
( * smbw_libc . close ) ( i ) ;
}
smbw_fd_map [ i ] = - 1 ;
}
/* unblock the parent */
write ( p [ 1 ] , & c , 1 ) ;
( * smbw_libc . close ) ( p [ 1 ] ) ;
/* specify directory to start in, if it's simulated smb */
if ( * smbw_cwd ! = ' \0 ' ) {
setenv ( " SMBW_DIR " , smbw_cwd , 1 ) ;
} else {
unsetenv ( " SMBW_DIR " ) ;
}
/* Re-initialize this library for the child */
2006-01-07 20:43:36 +00:00
do_init ( StartupType_Fake ) ;
2005-03-29 00:42:51 +00:00
/* and continue in the child */
return 0 ;
}
int smbw_setxattr ( const char * fname ,
const char * name ,
const void * value ,
size_t size ,
int flags )
{
char path [ PATH_MAX ] ;
if ( strcmp ( name , " system.posix_acl_access " ) = = 0 )
{
name = " system.* " ;
}
smbw_fix_path ( fname , path ) ;
return smbc_setxattr ( path , name , value , size , flags ) ;
}
int smbw_lsetxattr ( const char * fname ,
const char * name ,
const void * value ,
size_t size ,
int flags )
{
char path [ PATH_MAX ] ;
if ( strcmp ( name , " system.posix_acl_access " ) = = 0 )
{
name = " system.* " ;
}
smbw_fix_path ( fname , path ) ;
return smbc_lsetxattr ( path , name , value , size , flags ) ;
}
int smbw_fsetxattr ( int smbw_fd ,
const char * name ,
const void * value ,
size_t size ,
int flags )
{
int client_fd ;
if ( strcmp ( name , " system.posix_acl_access " ) = = 0 )
{
name = " system.* " ;
}
client_fd = smbw_fd_map [ smbw_fd ] ;
return smbc_fsetxattr ( client_fd , name , value , size , flags ) ;
}
int smbw_getxattr ( const char * fname ,
const char * name ,
const void * value ,
size_t size )
{
char path [ PATH_MAX ] ;
if ( strcmp ( name , " system.posix_acl_access " ) = = 0 )
{
name = " system.* " ;
}
smbw_fix_path ( fname , path ) ;
return smbc_getxattr ( path , name , value , size ) ;
}
int smbw_lgetxattr ( const char * fname ,
const char * name ,
const void * value ,
size_t size )
{
char path [ PATH_MAX ] ;
if ( strcmp ( name , " system.posix_acl_access " ) = = 0 )
{
name = " system.* " ;
}
smbw_fix_path ( fname , path ) ;
return smbc_lgetxattr ( path , name , value , size ) ;
}
int smbw_fgetxattr ( int smbw_fd ,
const char * name ,
const void * value ,
size_t size )
{
int client_fd ;
if ( strcmp ( name , " system.posix_acl_access " ) = = 0 )
{
name = " system.* " ;
}
client_fd = smbw_fd_map [ smbw_fd ] ;
return smbc_fgetxattr ( client_fd , name , value , size ) ;
}
int smbw_removexattr ( const char * fname ,
const char * name )
{
char path [ PATH_MAX ] ;
if ( strcmp ( name , " system.posix_acl_access " ) = = 0 )
{
name = " system.* " ;
}
smbw_fix_path ( fname , path ) ;
return smbc_removexattr ( path , name ) ;
}
int smbw_lremovexattr ( const char * fname ,
const char * name )
{
char path [ PATH_MAX ] ;
if ( strcmp ( name , " system.posix_acl_access " ) = = 0 )
{
name = " system.* " ;
}
smbw_fix_path ( fname , path ) ;
return smbc_lremovexattr ( path , name ) ;
}
int smbw_fremovexattr ( int smbw_fd ,
const char * name )
{
int client_fd ;
if ( strcmp ( name , " system.posix_acl_access " ) = = 0 )
{
name = " system.* " ;
}
client_fd = smbw_fd_map [ smbw_fd ] ;
return smbc_fremovexattr ( client_fd , name ) ;
}
int smbw_listxattr ( const char * fname ,
char * list ,
size_t size )
{
char path [ PATH_MAX ] ;
smbw_fix_path ( fname , path ) ;
return smbc_listxattr ( path , list , size ) ;
}
int smbw_llistxattr ( const char * fname ,
char * list ,
size_t size )
{
char path [ PATH_MAX ] ;
smbw_fix_path ( fname , path ) ;
return smbc_llistxattr ( path , list , size ) ;
}
int smbw_flistxattr ( int smbw_fd ,
char * list ,
size_t size )
{
int client_fd ;
client_fd = smbw_fd_map [ smbw_fd ] ;
return smbc_flistxattr ( client_fd , list , size ) ;
}