source: TI05-delivery/trunk/src/bbftp-server-3.2.0/bbftpd/bbftpd_cd.c @ 983

Subversion URL: http://proj.badc.rl.ac.uk/svn/ndg/TI05-delivery/trunk/src/bbftp-server-3.2.0/bbftpd/bbftpd_cd.c@983
Revision 983, 5.3 KB checked in by spascoe, 13 years ago (diff)

Added the autorisation hook bbftpd_private_authz. It appears to be called
correctly for a dir command.

Line 
1/*
2 * bbftpd/bbftpd_cd.c
3 * Copyright (C) 1999, 2000, 2001, 2002 IN2P3, CNRS
4 * bbftp@in2p3.fr
5 * http://doc.in2p3.fr/bbftp
6 *
7 * This program is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU General Public License
9 * as published by the Free Software Foundation; either version 2
10 * of the License, or any later version.
11 *
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
20 */ 
21
22/****************************************************************************
23
24 
25 RETURN:
26        0  Keep the connection open (does not mean that the directory has been
27           successfully created)
28        -1 Tell the calling program to close the connection
29 
30 bbftpd_cd.c    v 2.0.0 2001/02/12  - Creation of the routine.
31                v 2.0.1 2001/04/23  - Correct indentation
32                v 2.1.0 2001/06/01  - Change routine name
33                                     
34 *****************************************************************************/
35#include <bbftpd.h>
36
37#include <errno.h>
38#include <fcntl.h>
39#include <netinet/in.h>
40#include <stdio.h>
41#include <syslog.h>
42#include <sys/stat.h>
43#include <sys/types.h>
44#include <unistd.h>
45#include <utime.h>
46#if HAVE_STRING_H
47# include <string.h>
48#endif
49
50#include <common.h>
51#include <daemon.h>
52#include <daemon_proto.h>
53#include <structures.h>
54
55extern int transferoption ;
56extern int recvcontrolto ;
57int bbftpd_cd(int sock,int msglen) 
58{
59
60    char    *buffer ;
61    int        savederrno ;
62    char    *logmessage ;
63    struct  mess_dir *msg_dir ;
64    char    *dirname ;
65
66    if ( (buffer = (char *) malloc (msglen+1) ) == NULL ) {
67         syslog(BBFTPD_ERR,"Unable to malloc space for directory name (%d)",msglen) ;
68         reply(MSG_BAD,"Unable to malloc space for directory name") ;
69        return 0 ;
70    }
71    if ( (logmessage = (char *) malloc (msglen+1024) ) == NULL ) {
72         syslog(BBFTPD_ERR,"Unable to malloc space for logmessage ") ;
73         reply(MSG_BAD,"Unable to malloc space for logmessage") ;
74        FREE(buffer) ;
75        return 0 ;
76    }
77    /*
78    ** Read the characteristics of the directory
79    */
80    if ( readmessage(sock,buffer,msglen,recvcontrolto) < 0 ) {
81        /*
82        ** Error ...
83        */
84        syslog(BBFTPD_ERR,"Error reading directory name") ;
85        FREE(buffer) ;
86        FREE(logmessage) ;
87        return -1 ;
88    }
89    /*
90    ** buffer contains the directory to create
91    */
92    buffer[msglen] = '\0' ;
93    msg_dir = (struct mess_dir *) buffer ;
94     transferoption  = msg_dir->transferoption ;
95    dirname = msg_dir->dirname ;
96
97#ifdef NDG_AUTH
98    if (bbftpd_private_authz(MSG_CHDIR_V2, (void *)msg_dir, logmessage) != 0) {
99      syslog(BBFTPD_ERR, logmessage);
100      reply(MSG_BAD, logmessage);
101      FREE(logmessage);
102      FREE(buffer);
103      return 0;
104    }
105#endif // NDG_AUTH
106   
107    if ( (transferoption & TROPT_RFIO) == TROPT_RFIO ) {
108        syslog(BBFTPD_ERR,"Changing directory is not allowed under RFIO") ;
109        sprintf(logmessage,"Changing directory is not allowed under RFIO") ;
110        reply(MSG_BAD_NO_RETRY,logmessage) ;
111        FREE(logmessage) ;
112        FREE(buffer) ;
113        return 0 ;
114    }
115    syslog(BBFTPD_DEBUG,"Changing directory to %s",dirname) ;
116    /*
117    ** We change the directory
118    */
119    if ( chdir(dirname) < 0 ) {
120        /*
121        ** Depending on errno we are going to tell the client to
122        ** retry or not
123        */
124        savederrno = errno ;
125        sprintf(logmessage,"Error changing directory %s : %s ",dirname,strerror(errno)) ;
126        syslog(BBFTPD_ERR,"Error changing directory %s : %s",dirname,strerror(errno)) ;
127        /*
128        ** We tell the client not to retry in the following case (even in waiting
129        ** WAITRETRYTIME the problem will not be solved) :
130        **        EACCES        : Search permission denied
131        **        ELOOP        : To many symbolic links on path
132        **        ENAMETOOLONG: Path argument too long
133        **        ENOTDIR        : A component in path is not a directory
134        **        ENOENT      : A component of the path prefix does not exist or is a null pathname.
135        */
136        if ( savederrno == EACCES ||
137                savederrno == ELOOP ||
138                savederrno == ENAMETOOLONG ||
139                savederrno == ENOTDIR ||
140                savederrno == ENOENT ) {
141            reply(MSG_BAD_NO_RETRY,logmessage) ;
142            FREE(buffer) ;
143            FREE(logmessage) ;
144        } else {
145            reply(MSG_BAD,logmessage) ;
146            FREE(logmessage) ;
147            FREE(buffer) ;
148        }
149        return 0 ;
150    } else {
151        if ( getcwd(logmessage,msglen+1024)  == NULL ) {
152            /*
153            ** Unable to get current directory
154            */
155            sprintf(logmessage,"Unable to get current directory") ;
156            reply(MSG_BAD,logmessage) ;
157            FREE(logmessage) ;
158            FREE(buffer) ;
159            return 0 ;
160        } 
161    }
162    reply(MSG_OK,logmessage) ;
163    FREE(logmessage) ;
164    FREE(buffer) ;
165    return 0 ;
166}
Note: See TracBrowser for help on using the repository browser.