Skip site navigation (1)Skip section navigation (2)
Date:      Sun, 10 Aug 1997 19:57:20 -0700 (PDT)
From:      Ulf Zimmermann <ulf@Alameda.net>
To:        wu-ftpd-bugs@academ.com
Cc:        hackers@freebsd.org, bsdnet@Melmac.org
Subject:   Diffs for further virtual settings
Message-ID:  <199708110257.TAA07795@Melmac.org>

next in thread | raw e-mail | index | archive | help
Hello.

Below the signarture is a diff file for "access.c", "extensions.c", "ftpcmd.y"
and "ftpd.c". The diffs allow further virtual settings like:

limit
upload
overwrite
rename
umask
noretrieve
deny
email
log commands
log transfers
chmod
delete

I used the FreeBSD port based version of wu-ftpd-2.4.2BETA13 and tried not
to include the patches, which the port system applies. The changes are also
not very throughoutly tested.

-- 
Regards, Ulf.

--------------------------------------------------------------------------
Ulf Zimmermann, 1525 Pacific Ave., Alameda, CA-94501, #: 510-769-2936
Alameda Networks, Inc. | http://www.Alameda.net  | Fax#: 510-521-5073


diff -c -r src.orig/access.c src/access.c
*** src.orig/access.c	Sun Aug 10 19:44:44 1997
--- src/access.c	Sun Aug 10 18:55:32 1997
***************
*** 43,48 ****
--- 43,55 ----
  #else
  #include <syslog.h>
  #endif
+ #ifdef VIRTUAL
+ #include <netinet/in.h>
+ #include <netinet/in_systm.h>
+ #include <netinet/ip.h>
+ #include <sys/socket.h>
+ #include <arpa/inet.h>
+ #endif
  #include <time.h>
  #include <ctype.h>
  #include <pwd.h>
***************
*** 335,340 ****
--- 342,352 ----
  #endif
  {
      char class[1024];
+ #ifdef VIRTUAL
+     int virtual_len;
+     struct sockaddr_in virtual_addr;
+     struct sockaddr_in *virtual_ptr;
+ #endif
  
      extern int log_incoming_xfers,
        log_outbound_xfers,
***************
*** 396,402 ****
      }
  
      /* plan on expanding command syntax to include classes for each of these */
- 
      entry = (struct aclmember *) NULL;
      while (getaclentry("log", &entry)) {
          if (!strcasecmp(ARG0, "commands")) {
--- 408,413 ----
***************
*** 425,430 ****
--- 436,481 ----
                  log_outbound_xfers = outbound;
          }
      }
+ #ifdef VIRTUAL
+     virtual_len = sizeof(virtual_addr);
+     if (getsockname(0, (struct sockaddr *) &virtual_addr, &virtual_len) == 0) {
+         virtual_ptr = (struct sockaddr_in *) &virtual_addr;
+         entry = (struct aclmember *) NULL;
+         while (getaclentry("virtual", &entry)) {
+             if (!ARG0 || !ARG1 || !ARG2 || !ARG3)
+                 continue;
+             if (!strcmp(ARG0, inet_ntoa(virtual_ptr->sin_addr))) {
+                 if(!strcmp(ARG1, "log")) {
+                     if (!strcasecmp(ARG2, "commands")) {
+                         if (anonymous && strcasestr(ARG3, "anonymous"))
+                             log_commands = 1;
+                         if (guest && strcasestr(ARG3, "guest"))
+                             log_commands = 1;
+                         if (!guest && !anonymous && strcasestr(ARG3, "real"))
+                             log_commands = 1;
+                     }
+                     if (!strcasecmp(ARG2, "transfers")) {
+                         set = 0;
+                         if (strcasestr(ARG1, "anonymous") && anonymous)
+                             set = 1;
+                         if (strcasestr(ARG1, "guest") && guest)
+                             set = 1;
+                         if (strcasestr(ARG1, "real") && !guest && !anonymous)
+                             set = 1;
+                         if (strcasestr(ARG2, "inbound"))
+                             inbound = 1;
+                         if (strcasestr(ARG2, "outbound"))
+                             outbound = 1;
+                         if (set)
+                             log_incoming_xfers = inbound;
+                         if (set)
+                             log_outbound_xfers = outbound;
+                     }
+                 }
+             }
+         }
+     }
+ #endif	/* VIRTUAL */
  }
  
  /*************************************************************************/
***************
*** 485,494 ****
--- 536,575 ----
  {
      int limit;
      struct aclmember *entry = NULL;
+ #ifdef VIRTUAL
+     int virtual_len;
+     struct sockaddr_in virtual_addr;
+     struct sockaddr_in *virtual_ptr;
+ #endif
  
      if (msgpathbuf)
          *msgpathbuf = '\0';
  
+ #ifdef VIRTUAL
+     /* virtual ip_addr limit <class> <n> <times> [<message_file>] */
+     virtual_len = sizeof(virtual_addr);
+     if (getsockname(0, (struct sockaddr *) &virtual_addr, &virtual_len) == 0) {
+         virtual_ptr = (struct sockaddr_in *) &virtual_addr;
+         entry = (struct aclmember *) NULL;
+         while (getaclentry("virtual", &entry)) {
+             if (!ARG0 || !ARG1 || !ARG2 || !ARG3 || !ARG4)
+                 continue;
+             if (!strcmp(ARG0, inet_ntoa(virtual_ptr->sin_addr))) {
+                 if(!strcmp(ARG1, "limit")) {
+                     if (!strcmp(class, ARG2)) {
+ 			limit = atoi(ARG3);
+                         if (validtime(ARG4)) {
+ 			    if (ARG5 && msgpathbuf)
+ 				strcpy(msgpathbuf, ARG5);
+                             return (limit);
+                         }
+                     }
+                 }
+             }
+         }
+     }
+ #endif		/* VIRTUAL */
+ 
      /* limit <class> <n> <times> [<message_file>] */
      while (getaclentry("limit", &entry)) {
          if (!ARG0 || !ARG1 || !ARG2)
***************
*** 520,528 ****
--- 601,641 ----
  #endif
  {
      struct aclmember *entry = NULL;
+ #ifdef VIRTUAL
+     int virtual_len;
+     struct sockaddr_in virtual_addr;
+     struct sockaddr_in *virtual_ptr;
+ #endif
  
      if (msgpathbuf)
          *msgpathbuf = (char) NULL;
+ 
+ #ifdef VIRTUAL
+     /* virtual ip_addr deny <addrglob> [<message_file>] */
+     virtual_len = sizeof(virtual_addr);
+     if (getsockname(0, (struct sockaddr *) &virtual_addr, &virtual_len) == 0) {
+         virtual_ptr = (struct sockaddr_in *) &virtual_addr;
+         entry = (struct aclmember *) NULL;
+         while (getaclentry("virtual", &entry)) {
+             if (!ARG0 || !ARG1 || !ARG2)
+                 continue;
+             if (!strcmp(ARG0, inet_ntoa(virtual_ptr->sin_addr))) {
+                 if(!strcmp(ARG1, "deny")) {
+                     if (!nameserved && !strcmp(ARG2, "!nameserved")) {
+                         if (ARG3)
+                            strcpy(msgpathbuf, entry->arg[3]);
+                         return(1);
+                     }
+                     if (hostmatch(ARG2)) {
+                         if (ARG3)
+                            strcpy(msgpathbuf, entry->arg[3]);
+                         return(1);
+                     }
+                 }
+             }
+         }
+     }
+ #endif	/* VIRTUAL */
  
      /* deny <addrglob> [<message_file>] */
      while (getaclentry("deny", &entry)) {
diff -c -r src.orig/extensions.c src/extensions.c
*** src.orig/extensions.c	Sun Aug 10 19:44:44 1997
--- src/extensions.c	Sun Aug 10 19:29:23 1997
***************
*** 42,47 ****
--- 42,54 ----
  #else
  #include <syslog.h>
  #endif
+ #ifdef VIRTUAL
+ #include <netinet/in.h>
+ #include <netinet/in_systm.h>
+ #include <netinet/ip.h>
+ #include <sys/socket.h>
+ #include <arpa/inet.h>
+ #endif
  #include <time.h>
  #include <pwd.h>
  #include <grp.h>
***************
*** 55,60 ****
--- 62,69 ----
  #include <sys/statvfs.h>
  #elif defined(HAVE_SYS_VFS)
  #include <sys/vfs.h>
+ #elif defined(__FreeBSD__)
+ #include <sys/mount.h>
  #endif
  
  #include <arpa/ftp.h>
***************
*** 157,163 ****
  
      return(buf.f_bavail * buf.f_frsize / 1024);
  }
! #elif defined(HAVE_SYS_VFS)
  int getSize(s)
  char *s;
  {
--- 166,172 ----
  
      return(buf.f_bavail * buf.f_frsize / 1024);
  }
! #elif defined(HAVE_SYS_VFS) || defined(__FreeBSD__)
  int getSize(s)
  char *s;
  {
***************
*** 194,199 ****
--- 203,213 ----
      int limit;
      extern struct passwd *pw;
      struct aclmember *entry = NULL;
+ #ifdef VIRTUAL
+     int virtual_len;
+     struct sockaddr_in virtual_addr;
+     struct sockaddr_in *virtual_ptr;
+ #endif
  
      (void) time(&curtime);
      (void) acl_getclass(buffer);
***************
*** 206,213 ****
--- 220,248 ----
          else {
              switch (*++inptr) {
              case 'E':
+ #ifdef VIRTUAL
+                 /* virtual ip_addr email <name> */
+                 virtual_len = sizeof(virtual_addr);
+                 if (getsockname(0, (struct sockaddr *) &virtual_addr, &virtual_len) == 0) {
+                     virtual_ptr = (struct sockaddr_in *) &virtual_addr;
+                     entry = (struct aclmember *) NULL;
+                     while (getaclentry("virtual", &entry)) {
+                         if (!ARG0 || !ARG1 || !ARG2)
+                             continue;
+                         if (!strcmp(ARG0, inet_ntoa(virtual_ptr->sin_addr))) {
+                             if(!strcmp(ARG1, "email")) {
+                                 sprintf(outptr, "%s", ARG2);
+                                 goto email_breakout;
+                             }
+                         }
+                     }
+                 }
+ #endif	/* VIRTUAL */
                  if ( (getaclentry("email", &entry)) && ARG0 )
                      sprintf(outptr, "%s", ARG0); 
+ #ifdef VIRTUAL
+ email_breakout:
+ #endif	/* VIRTUAL */
                  break;
              case 'N': 
                  sprintf(outptr, "%d", acl_countusers(buffer)); 
***************
*** 222,228 ****
                  break;
  
              case 'F':
! #if defined(HAVE_STATVFS) || defined(HAVE_SYS_VFS)
                  sprintf(outptr, "%lu", getSize("."));
  #endif
                  break;
--- 257,263 ----
                  break;
  
              case 'F':
! #if defined(HAVE_STATVFS) || defined(HAVE_SYS_VFS) || defined(__FreeBSD__)
                  sprintf(outptr, "%lu", getSize("."));
  #endif
                  break;
***************
*** 806,811 ****
--- 841,851 ----
      struct passwd *pwent;
      struct group *grent;
      char buf[BUFSIZ];
+ #ifdef VIRTUAL
+     int virtual_len;
+     struct sockaddr_in virtual_addr;
+     struct sockaddr_in *virtual_ptr;
+ #endif
  
      while (getaclentry("upload", &entry) && ARG0 && ARG1 && ARG2 != NULL) {
          if (ARG3 && ARG4) {
***************
*** 824,829 ****
--- 864,900 ----
  	    endgrent();
          }
      }
+ #ifdef VIRTUAL
+     virtual_len = sizeof(virtual_addr);
+     if (getsockname(0, (struct sockaddr *) &virtual_addr, &virtual_len) == 0) {
+         virtual_ptr = (struct sockaddr_in *) &virtual_addr;
+         entry = (struct aclmember *) NULL;
+         while (getaclentry("virtual", &entry)) {
+             if (!ARG0 || !ARG1 || !ARG2 || !ARG3 || !ARG4)
+                 continue;
+             if (!strcmp(ARG0, inet_ntoa(virtual_ptr->sin_addr))) {
+                 if(!strcmp(ARG1, "upload")) {
+                     if (ARG5 && ARG6) {
+                         pwent = getpwnam(ARG5);
+                         grent = getgrnam(ARG6);
+ 
+                         if (pwent)  sprintf(buf, "%d", pwent->pw_uid);
+                         else        sprintf(buf, "%d", 0);
+                         ARG5 = (char *) malloc(strlen(buf) + 1);
+                         strcpy(ARG5, buf);
+ 
+                         if (grent)  sprintf(buf, "%d", grent->gr_gid);
+                         else        sprintf(buf, "%d", 0);
+                         ARG6  = (char *) malloc(strlen(buf) + 1);
+                         strcpy(ARG6, buf);
+                         endgrent();
+                     }
+                 }
+             }
+         }
+     }
+ #endif	/* VIRTUAL */
+ 
  }
  
  int
***************
*** 956,961 ****
--- 1027,1037 ----
    char path[BUFSIZ];
    char *sp;
    extern struct passwd *pw;
+ #ifdef VIRTUAL
+     int virtual_len;
+     struct sockaddr_in virtual_addr;
+     struct sockaddr_in *virtual_ptr;
+ #endif
  
    *valid = 0;
    /* what's our current directory? */
***************
*** 981,986 ****
--- 1057,1088 ----
            else       ap6 = NULL;
        }
    }
+ #ifdef VIRTUAL
+     virtual_len = sizeof(virtual_addr);
+     if (getsockname(0, (struct sockaddr *) &virtual_addr, &virtual_len) == 0) {
+         virtual_ptr = (struct sockaddr_in *) &virtual_addr;
+         entry = (struct aclmember *) NULL;
+         while (getaclentry("virtual", &entry)) {
+             if (!ARG0 || !ARG1 || !ARG2 || !ARG3 || !ARG4)
+                 continue;
+             if (!strcmp(ARG0, inet_ntoa(virtual_ptr->sin_addr))) {
+                 if(!strcmp(ARG1, "upload")) {
+                     if ( (!strcmp(ARG2, pw->pw_dir)) &&
+                          ((i = path_compare(ARG3, cwdir)) >= match_value) ) {
+                         match_value = i;
+                         ap2 = ARG4;
+                         if (ARG5)  ap3 = ARG5;
+                         else       ap3 = NULL;
+                         if (ARG6)  ap4 = ARG6;
+                         else       ap4 = NULL;
+                         if (ARG8)  ap6 = ARG8;
+                         else       ap6 = NULL;
+                     }
+                 }
+             }
+         }
+     }
+ #endif	/* VIRTUAL */
    if ( ((ap2 && !strcasecmp(ap2, "no")) && (ap3 && strcasecmp(ap3, "dirs"))) || 
         (ap3 && !strcasecmp(ap3, "nodirs")) ||
         (ap6 && !strcasecmp(ap6, "nodirs")) ) {
***************
*** 1022,1027 ****
--- 1124,1134 ----
  
    struct aclmember *entry = NULL;
    extern struct passwd *pw;
+ #ifdef VIRTUAL
+     int virtual_len;
+     struct sockaddr_in virtual_addr;
+     struct sockaddr_in *virtual_ptr;
+ #endif
  
    *valid = 0;
  
***************
*** 1053,1058 ****
--- 1160,1192 ----
                else      ap5 = NULL;
            }
  	}
+ #ifdef VIRTUAL
+     virtual_len = sizeof(virtual_addr);
+     if (getsockname(0, (struct sockaddr *) &virtual_addr, &virtual_len) == 0) {
+         virtual_ptr = (struct sockaddr_in *) &virtual_addr;
+         entry = (struct aclmember *) NULL;
+         while (getaclentry("virtual", &entry)) {
+             if (!ARG0 || !ARG1 || !ARG2 || !ARG3 || !ARG4)
+                 continue;
+             if (!strcmp(ARG0, inet_ntoa(virtual_ptr->sin_addr))) {
+                 if(!strcmp(ARG1, "upload")) {
+                     if ( (!strcmp(ARG2, pw->pw_dir)) &&
+                          ((i = path_compare(ARG3, cwdir)) >= match_value) ) {
+                         match_value = i;
+                         ap1 = ARG3;
+                         ap2 = ARG4;
+                         if (ARG5)  ap3 = ARG5;
+                         else       ap3 = NULL;
+                         if (ARG6)  ap4 = ARG6;
+                         else       ap4 = NULL;
+                         if (ARG7)  ap5 = ARG7;
+                         else       ap5 = NULL;
+                     }
+                 }
+             }
+         }
+     }
+ #endif	/* VIRTUAL */
  
        if (ap3 && ( (!strcasecmp("dirs",ap3)) || (!strcasecmp("nodirs", ap3)) ))
          ap3 = NULL;
***************
*** 1092,1104 ****
  {
    int pdelete = 1;
    struct aclmember *entry = NULL;
  
    while (getaclentry("delete", &entry) && ARG0 && ARG1 != NULL) {
        if (type_match(ARG1))
            if (*ARG0 == 'n')
                pdelete = 0;
    }
!   
  /* H* fix: no deletion, period. You put a file here, I get to look at it. */
  #ifdef PARANOID
    pdelete = 0;
--- 1226,1264 ----
  {
    int pdelete = 1;
    struct aclmember *entry = NULL;
+ #ifdef VIRTUAL
+     int virtual_len;
+     struct sockaddr_in virtual_addr;
+     struct sockaddr_in *virtual_ptr;
+ #endif
  
    while (getaclentry("delete", &entry) && ARG0 && ARG1 != NULL) {
        if (type_match(ARG1))
            if (*ARG0 == 'n')
                pdelete = 0;
    }
! #ifdef VIRTUAL
!   virtual_len = sizeof(virtual_addr);
!   if (getsockname(0, (struct sockaddr *) &virtual_addr, &virtual_len) == 0) {
!       virtual_ptr = (struct sockaddr_in *) &virtual_addr;
!       entry = (struct aclmember *) NULL;
!       while (getaclentry("virtual", &entry)) {
!           if (!ARG0 || !ARG1 || !ARG2 || !ARG3)
!               continue;
!           if (!strcmp(ARG0, inet_ntoa(virtual_ptr->sin_addr))) {
!               if(!strcmp(ARG1, "delete")) {
!                   if (type_match(ARG3)) {
!                       if (*ARG2 == 'n')
!                           pdelete = 0;
!                       else
!                           pdelete = 1;
!                   }
!               }
!           }
!       }
!   }
! #endif	/* VIRTUAL */
! 
  /* H* fix: no deletion, period. You put a file here, I get to look at it. */
  #ifdef PARANOID
    pdelete = 0;
***************
*** 1127,1132 ****
--- 1287,1297 ----
    char cwd[MAXPATHLEN+1], realwd[MAXPATHLEN+1], realname[MAXPATHLEN+1];
    int i;
    struct aclmember *entry = NULL;
+ #ifdef VIRTUAL
+     int virtual_len;
+     struct sockaddr_in virtual_addr;
+     struct sockaddr_in *virtual_ptr;
+ #endif
  
    if (name == (char *)NULL || *name == '\0')
      return 0; 
***************
*** 1139,1144 ****
--- 1304,1334 ----
  
    realpath (cwd, realwd);
    realpath (name, realname);
+ 
+ #ifdef VIRTUAL
+    /* virtual ip_addr noretrieve <filename> <filename> */
+    virtual_len = sizeof(virtual_addr);
+    if (getsockname(0, (struct sockaddr *) &virtual_addr, &virtual_len) == 0) {
+        virtual_ptr = (struct sockaddr_in *) &virtual_addr;
+        entry = (struct aclmember *) NULL;
+        while (getaclentry("virtual", &entry)) {
+            if (!ARG0 || !ARG1 || !ARG2)
+                continue;
+            if (!strcmp(ARG0, inet_ntoa(virtual_ptr->sin_addr))) {
+                if(!strcmp(ARG1, "noretrieve")) {
+                    for (i = 2; i< MAXARGS &&
+                         (entry->arg[i] != (char *)NULL) && (*(entry->arg[i]) !='\0'); i++)
+                      if (strcmp (((*(entry->arg[i]) == '/') ? realname :
+                                    lbasename (realname)), entry->arg[i]) == 0)
+                      {
+                          reply (550, "%s is marked unretrievable", entry->arg[i]);
+                          return 1;
+                      }
+                }
+            }
+        }
+    }
+ #endif	/* VIRTUAL */
  
     while (getaclentry("noretrieve", &entry)) {
          if (ARG0 == (char *)NULL)
diff -c -r src.orig/ftpcmd.y src/ftpcmd.y
*** src.orig/ftpcmd.y	Sun Aug 10 19:44:44 1997
--- src/ftpcmd.y	Sun Aug 10 18:55:31 1997
***************
*** 61,66 ****
--- 61,73 ----
  #else
  #include <syslog.h>
  #endif
+ #ifdef VIRTUAL
+ #include <netinet/in.h>
+ #include <netinet/in_systm.h>
+ #include <netinet/ip.h>
+ #include <sys/socket.h>
+ #include <arpa/inet.h>
+ #endif
  #include <time.h>
  #include <string.h>
  #include <limits.h>
***************
*** 480,485 ****
--- 487,497 ----
              mode_t oldmask;
              struct aclmember *entry = NULL;
              int ok = 1;
+ #ifdef VIRTUAL
+             int virtual_len;
+             struct sockaddr_in virtual_addr;
+             struct sockaddr_in *virtual_ptr;
+ #endif	/* VIRTUAL */
  
              if (log_commands) syslog(LOG_INFO, "SITE UMASK %03o", $6);
              if ($4) {
***************
*** 488,493 ****
--- 500,522 ----
                      if (type_match(ARG1)) 
                          if (*ARG0 == 'n')  ok = 0;
                  }
+ #ifdef VIRTUAL
+                 virtual_len = sizeof(virtual_addr);
+                 if (getsockname(0, (struct sockaddr *) &virtual_addr, &virtual_len) == 0) {
+                     virtual_ptr = (struct sockaddr_in *) &virtual_addr;
+                     entry = (struct aclmember *) NULL;
+                     while (getaclentry("virtual", &entry)) {
+                         if (!ARG0 || !ARG1 || !ARG2 || !ARG3)
+                             continue;
+                         if (!strcmp(ARG0, inet_ntoa(virtual_ptr->sin_addr))) {
+                             if(!strcmp(ARG1, "umask")) {
+                                 if (type_match(ARG3))
+                                     if (*ARG2 == 'n')  ok = 0;
+                             }
+                         }
+                     }
+                 }
+ #endif	/* VIRTUAL */
                  if (ok) {
                      if (($6 < 0) || ($6 > 0777)) {
                          reply(501, "Bad UMASK value");
***************
*** 503,508 ****
--- 532,542 ----
          = {
              struct aclmember *entry = NULL;
              int ok = 1;
+ #ifdef VIRTUAL
+             int virtual_len;
+             struct sockaddr_in virtual_addr;
+             struct sockaddr_in *virtual_ptr;
+ #endif	/* VIRTUAL */
  
              if (log_commands) syslog(LOG_INFO, "SITE CHMOD %03o  %s", $6, $8);
              if ($4 && $8) {
***************
*** 511,516 ****
--- 545,567 ----
                      if (type_match(ARG1)) 
                          if (*ARG0 == 'n')  ok = 0;
                  }
+ #ifdef VIRTUAL
+                 virtual_len = sizeof(virtual_addr);
+                 if (getsockname(0, (struct sockaddr *) &virtual_addr, &virtual_len) == 0) {
+                     virtual_ptr = (struct sockaddr_in *) &virtual_addr;
+                     entry = (struct aclmember *) NULL;
+                     while (getaclentry("virtual", &entry)) {
+                         if (!ARG0 || !ARG1 || !ARG2 || !ARG3)
+                             continue;
+                         if (!strcmp(ARG0, inet_ntoa(virtual_ptr->sin_addr))) {
+                             if(!strcmp(ARG1, "chmod")) {
+                                 if (type_match(ARG3))
+                                     if (*ARG2 == 'n')  ok = 0;
+                             }
+                         }
+                     }
+                 }
+ #endif	/* VIRTUAL */
                  if (ok) {
                      if (($6 < 0) || ($6 > 0777))
                          reply(501, 
diff -c -r src.orig/ftpd.c src/ftpd.c
*** src.orig/ftpd.c	Sun Aug 10 19:44:44 1997
--- src/ftpd.c	Sun Aug 10 18:55:31 1997
***************
*** 1978,1983 ****
--- 1978,1988 ----
      char *gunique();
  #endif
      time_t start_time = time(NULL);
+ #ifdef VIRTUAL
+     int virtual_len;
+     struct sockaddr_in virtual_addr;
+     struct sockaddr_in *virtual_ptr;
+ #endif
  
      struct aclmember *entry = NULL;
  
***************
*** 2023,2029 ****
                  open_flags |= O_EXCL;
              }
      }
! 
  #ifdef PARANOID
      overwrite = 0;
  #endif
--- 2028,2055 ----
                  open_flags |= O_EXCL;
              }
      }
! #ifdef VIRTUAL
!     virtual_len = sizeof(virtual_addr);
!     if (getsockname(0, (struct sockaddr *) &virtual_addr, &virtual_len) == 0) {
!         virtual_ptr = (struct sockaddr_in *) &virtual_addr;
!         entry = (struct aclmember *) NULL;
!         while (getaclentry("virtual", &entry)) {
!             if (!ARG0 || !ARG1 || !ARG2 || !ARG3)
!                 continue;
!             if (!strcmp(ARG0, inet_ntoa(virtual_ptr->sin_addr))) {
!                 if(!strcmp(ARG1, "overwrite")) {
!                     if (type_match(ARG3)) {
!                         if (strcmp(ARG2, "yes") != 0) {
!                             overwrite = 0;
!                             open_flags |= O_EXCL;
!                         }
!                     }
!                 }
!             }
!         }
!     }
! #endif	/* VIRTUAL */
!         
  #ifdef PARANOID
      overwrite = 0;
  #endif
***************
*** 3059,3064 ****
--- 3085,3095 ----
  {
      struct stat st;
      struct aclmember *entry = NULL;	/* Added: fixes a bug.  _H*/
+ #ifdef VIRTUAL
+     int virtual_len;
+     struct sockaddr_in virtual_addr;
+     struct sockaddr_in *virtual_ptr;
+ #endif
  
      if (lstat(name, &st) < 0) {
          perror_reply(550, name);
***************
*** 3068,3073 ****
--- 3099,3126 ----
      /* if rename permission denied and file exists... then deny the user
       * permission to rename the file. 
       */
+ #ifdef VIRTUAL
+     virtual_len = sizeof(virtual_addr);
+     if (getsockname(0, (struct sockaddr *) &virtual_addr, &virtual_len) == 0) {
+         virtual_ptr = (struct sockaddr_in *) &virtual_addr;
+         entry = (struct aclmember *) NULL;
+         while (getaclentry("virtual", &entry)) {
+             if (!ARG0 || !ARG1 || !ARG2 || !ARG3)
+                 continue;
+             if (!strcmp(ARG0, inet_ntoa(virtual_ptr->sin_addr))) {
+                 if(!strcmp(ARG1, "rename")) {
+                     if (type_match(ARG3)) {
+                         if (strcmp(ARG2, "yes")) {
+                             reply(553, "%s: Permission denied. (rename)", name);
+                             return ((char *) 0);
+                         }
+                     }
+                 }
+             }
+         }
+     }
+ #endif	/* VIRTUAL */
+         
      while (getaclentry("rename", &entry) && ARG0 && ARG1 != NULL) {
          if (type_match(ARG1))
              if (strcmp(ARG0, "yes")) {



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?199708110257.TAA07795>